X-Git-Url: http://source.jalview.org/gitweb/?a=blobdiff_plain;f=src%2Forg%2Fvamsas%2Fclient%2Fsimpleclient%2FSessionFile.java;h=c9f9e67116021f554db2ce495e6b4c9ee35ed761;hb=5156a824b13ecd091af9f84870f41d83eb59bd71;hp=d33f2f8f123b90e92f9cd41cec300e956f663068;hpb=d3c6dfdbb5e6d268c45ddf261f941af1309649ba;p=vamsas.git diff --git a/src/org/vamsas/client/simpleclient/SessionFile.java b/src/org/vamsas/client/simpleclient/SessionFile.java index d33f2f8..c9f9e67 100644 --- a/src/org/vamsas/client/simpleclient/SessionFile.java +++ b/src/org/vamsas/client/simpleclient/SessionFile.java @@ -1,9 +1,14 @@ package org.vamsas.client.simpleclient; +import java.io.BufferedInputStream; +import java.io.BufferedOutputStream; import java.io.File; +import java.io.FileInputStream; import java.io.FileNotFoundException; import java.io.FileOutputStream; import java.io.IOException; +import java.io.RandomAccessFile; +import java.nio.channels.ReadableByteChannel; import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; @@ -29,24 +34,11 @@ public class SessionFile { fileLock.release();// tidy up invalid lock fileLock=null; } - if (extantlock!=null) - fileLock=extantlock; + if (extantlock!=null && extantlock.isLocked()) + fileLock=extantlock; // THIS IS BROKEN - lockFile then nulls the lock. return lockFile(); } - - /** - * Get a lock for the SessionFile - * - * @return true if lock was made - */ - protected boolean lockFile() { - if (fileLock != null) - if (fileLock.isLocked()) - return true; - else - // lock failed for some reason. - fileLock.release(); - fileLock = null; + private boolean ensureSessionFile() { if (sessionFile != null) { if (!sessionFile.exists()) { // create new file @@ -60,25 +52,46 @@ public class SessionFile { return false; } } - // TODO: see if we need to loop-wait for locks or they just block until - // lock is made... - long tries=500; - do { - tries--; - if (fileLock!=null && !fileLock.isLocked()) - fileLock.release(); - fileLock = new Lock(sessionFile); // TODO: wait around if we can't get the lock. - } while (tries>0 && !fileLock.isLocked()); - if (!fileLock.isLocked()) - log.error("Failed to get lock for "+sessionFile); - // fileLock = new Lock(sessionFile); - return fileLock.isLocked(); - } else - log.error("lockFile called for non-initialised SessionFile!"); - - // no lock possible + return true; + } + log.error("ensureSessionFile called for non-initialised SessionFile!"); return false; } + /** + * Get a lock for the SessionFile + * + * @return true if lock was made + */ + protected boolean lockFile() { + if (fileLock != null) { + if (fileLock.isLocked()) { + if (!ensureSessionFile()) + return false; + return true; + } else { + // lock failed for some reason. + fileLock.release(); + log.info("Unexpected session file lock failure. Trying to get it again."); + fileLock=null; + } + } + if (!ensureSessionFile()) + return false; + // TODO: see if we need to loop-wait for locks or they just block until + // lock is made... + long tries=5000; + do { + tries--; + if (fileLock==null || !fileLock.isLocked()) { + //try { Thread.sleep(1); } catch (Exception e) {}; + fileLock = LockFactory.getLock(sessionFile,true); // TODO: wait around if we can't get the lock. + } + } while (tries>0 && !fileLock.isLocked()); + if (!fileLock.isLocked()) + log.error("Failed to get lock for "+sessionFile); + // fileLock = new Lock(sessionFile); + return fileLock.isLocked(); + } /** * Explicitly release the SessionFile's lock. @@ -105,10 +118,18 @@ public class SessionFile { if (lockFile(extantLock)) { try { tempfile = File.createTempFile(backupPrefix, backupSuffix, backupDir); - FileOutputStream tos = new FileOutputStream(tempfile); - tos.getChannel().transferFrom(fileLock.rafile.getChannel(), 0, - fileLock.rafile.length()); - tos.close(); + if (fileLock.length()>0) { + FileOutputStream tos = new FileOutputStream(tempfile); + ReadableByteChannel channel; + tos.getChannel().transferFrom(channel=fileLock.getRaChannel(), 0, + fileLock.length()); + tos.close(); + if (!channel.isOpen()) + throw new Error(tos.getChannel().getClass()+".transferFrom closes source channel!"); + if (!lockFile(extantLock)) + throw new Error("Lost lock for "+sessionFile.getName()+" after backup."); + + } } catch (FileNotFoundException e1) { log.warn("Can't create temp file for "+sessionFile.getName(),e1); tempfile=null; @@ -131,10 +152,22 @@ public class SessionFile { if (newData.sessionFile==null) throw new IOException("Null SessionFile in newData."); - lockFile(extantLock); - newData.lockFile(); - fileLock.rafile.getChannel().transferFrom(newData.fileLock.rafile.getChannel(), 0, - newData.fileLock.rafile.length()); + if (!lockFile(extantLock)) + throw new IOException("Failed to get write lock for "+sessionFile); + if (!newData.lockFile()) + throw new IOException("Failed to get lock for updateFrom "+newData.sessionFile); + RandomAccessFile nrafile = newData.fileLock.getRaFile(); + nrafile.seek(0); + RandomAccessFile trafile = fileLock.getRaFile(); + /*long tries=5000; + while (trafile==null && --tries>0) { + log.debug("Lost lock on "+sessionFile+"! Re-trying for a transfer."); + lockFile(); + trafile = fileLock.getRaFile(); + }*/ + trafile.seek(0); + trafile.getChannel().transferFrom(nrafile.getChannel(), 0, + nrafile.length()); } /** * remove all trace of the sessionFile file @@ -147,4 +180,36 @@ public class SessionFile { sessionFile = null; } } + /* (non-Javadoc) + * @see org.vamsas.client.simpleclient.Lock#getBufferedInputStream(boolean) + */ + public BufferedInputStream getBufferedInputStream(boolean atStart) throws IOException { + lockFile(); + return fileLock.getBufferedInputStream(atStart); + } + + /* (non-Javadoc) + * @see org.vamsas.client.simpleclient.Lock#getBufferedOutputStream(boolean) + */ + public BufferedOutputStream getBufferedOutputStream(boolean clear) throws IOException { + lockFile(); + return fileLock.getBufferedOutputStream(clear); + } + + /* (non-Javadoc) + * @see org.vamsas.client.simpleclient.Lock#getFileInputStream(boolean) + */ + public FileInputStream getFileInputStream(boolean atStart) throws IOException { + lockFile(); + return fileLock.getFileInputStream(atStart); + } + + /* (non-Javadoc) + * @see org.vamsas.client.simpleclient.Lock#getFileOutputStream(boolean) + */ + public FileOutputStream getFileOutputStream(boolean clear) throws IOException { + lockFile(); + return fileLock.getFileOutputStream(clear); + } + }