[vassalengine-svn] SF.net SVN: vassalengine:[6188] VASSAL-src/branches/nio-fs/src/com/sun/nio/ zipf
Brought to you by:
rodneykinney,
uckelman
From: <uck...@us...> - 2009-10-22 22:05:47
|
Revision: 6188 http://vassalengine.svn.sourceforge.net/vassalengine/?rev=6188&view=rev Author: uckelman Date: 2009-10-22 22:05:18 +0000 (Thu, 22 Oct 2009) Log Message: ----------- Beginning of modifications for read/write locking. Modified Paths: -------------- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/JarEntryInfo.java VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/JarFileAttributeView.java VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/JarFileAttributes.java VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ReadableAttributeViewByName.java VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipEntryInfo.java VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileAttributeView.java VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileAttributes.java VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileBasicAttributeView.java VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileBasicAttributes.java VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFilePath.java VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileStore.java VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileStream.java VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileSystem.java VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileSystemProvider.java VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipHeaderConstants.java VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipPathParser.java VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipUtils.java Added Paths: ----------- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipIO.java VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipLock.java VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipNode.java Modified: VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/JarEntryInfo.java =================================================================== --- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/JarEntryInfo.java 2009-10-22 21:18:50 UTC (rev 6187) +++ VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/JarEntryInfo.java 2009-10-22 22:05:18 UTC (rev 6188) @@ -29,7 +29,7 @@ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package com.sun.nio.zipfs; +package VASSAL.tools.nio.file.zipfs; import java.util.Map; import java.util.Set; Modified: VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/JarFileAttributeView.java =================================================================== --- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/JarFileAttributeView.java 2009-10-22 21:18:50 UTC (rev 6187) +++ VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/JarFileAttributeView.java 2009-10-22 22:05:18 UTC (rev 6188) @@ -28,7 +28,7 @@ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package com.sun.nio.zipfs; +package VASSAL.tools.nio.file.zipfs; import VASSAL.tools.nio.file.*; @@ -38,7 +38,7 @@ public class JarFileAttributeView extends ZipFileAttributeView { /** Creates a new instance of JarFileAttributeView */ - public JarFileAttributeView(FileRef file) { + public JarFileAttributeView(ZipFilePath file) { super(file); } Modified: VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/JarFileAttributes.java =================================================================== --- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/JarFileAttributes.java 2009-10-22 21:18:50 UTC (rev 6187) +++ VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/JarFileAttributes.java 2009-10-22 22:05:18 UTC (rev 6188) @@ -28,9 +28,8 @@ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ +package VASSAL.tools.nio.file.zipfs; -package com.sun.nio.zipfs; - import VASSAL.tools.nio.file.*; //import java.nio.file.*; @@ -41,7 +40,7 @@ public class JarFileAttributes extends ZipFileAttributes { /** Creates a new instance of JarFileAttributes */ - public JarFileAttributes(FileRef file) throws IOException { + public JarFileAttributes(ZipFilePath file) throws IOException { super(file); } Modified: VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ReadableAttributeViewByName.java =================================================================== --- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ReadableAttributeViewByName.java 2009-10-22 21:18:50 UTC (rev 6187) +++ VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ReadableAttributeViewByName.java 2009-10-22 22:05:18 UTC (rev 6188) @@ -28,9 +28,8 @@ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ +package VASSAL.tools.nio.file.zipfs; -package com.sun.nio.zipfs; - import java.io.IOException; public interface ReadableAttributeViewByName { Modified: VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipEntryInfo.java =================================================================== --- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipEntryInfo.java 2009-10-22 21:18:50 UTC (rev 6187) +++ VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipEntryInfo.java 2009-10-22 22:05:18 UTC (rev 6188) @@ -28,9 +28,8 @@ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ +package VASSAL.tools.nio.file.zipfs; -package com.sun.nio.zipfs; - public class ZipEntryInfo { byte[] filename; Modified: VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileAttributeView.java =================================================================== --- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileAttributeView.java 2009-10-22 21:18:50 UTC (rev 6187) +++ VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileAttributeView.java 2009-10-22 22:05:18 UTC (rev 6188) @@ -28,7 +28,7 @@ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package com.sun.nio.zipfs; +package VASSAL.tools.nio.file.zipfs; import VASSAL.tools.nio.file.*; @@ -38,7 +38,7 @@ public class ZipFileAttributeView extends ZipFileBasicAttributeView { /** Creates a new instance of ZipFileAttributeView */ - public ZipFileAttributeView(FileRef file) { + public ZipFileAttributeView(ZipFilePath file) { super(file); } Modified: VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileAttributes.java =================================================================== --- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileAttributes.java 2009-10-22 21:18:50 UTC (rev 6187) +++ VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileAttributes.java 2009-10-22 22:05:18 UTC (rev 6188) @@ -28,9 +28,8 @@ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ +package VASSAL.tools.nio.file.zipfs; -package com.sun.nio.zipfs; - import VASSAL.tools.nio.file.*; //import java.nio.file.*; @@ -60,11 +59,10 @@ "Tandem" }; - public ZipFileAttributes(FileRef file) throws IOException { + public ZipFileAttributes(ZipFilePath file) throws IOException { super(file); } - public byte[] comment() { return ze.comment; } Modified: VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileBasicAttributeView.java =================================================================== --- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileBasicAttributeView.java 2009-10-22 21:18:50 UTC (rev 6187) +++ VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileBasicAttributeView.java 2009-10-22 22:05:18 UTC (rev 6188) @@ -28,7 +28,7 @@ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package com.sun.nio.zipfs; +package VASSAL.tools.nio.file.zipfs; import VASSAL.tools.nio.file.attribute.*; import VASSAL.tools.nio.file.*; @@ -41,10 +41,10 @@ public class ZipFileBasicAttributeView implements BasicFileAttributeView, ReadableAttributeViewByName { // encapsulates the object that we are bound too - protected final FileRef file; + protected final ZipFilePath file; /** Creates a new instance of ZipFileAttributeView */ - public ZipFileBasicAttributeView(FileRef file) { + public ZipFileBasicAttributeView(ZipFilePath file) { this.file = file; } Modified: VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileBasicAttributes.java =================================================================== --- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileBasicAttributes.java 2009-10-22 21:18:50 UTC (rev 6187) +++ VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileBasicAttributes.java 2009-10-22 22:05:18 UTC (rev 6188) @@ -28,7 +28,7 @@ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package com.sun.nio.zipfs; +package VASSAL.tools.nio.file.zipfs; import VASSAL.tools.nio.file.*; import VASSAL.tools.nio.file.attribute.*; @@ -38,17 +38,23 @@ import java.io.IOException; import java.util.Calendar; -public class ZipFileBasicAttributes implements - BasicFileAttributes { +public class ZipFileBasicAttributes implements BasicFileAttributes { ZipEntryInfo ze; /** Creates a new instance of ZipFileAttributes */ - public ZipFileBasicAttributes(FileRef file) throws IOException { - if (file instanceof ZipFilePath && !((ZipFilePath) file).getFileSystem().isOpen()) { + public ZipFileBasicAttributes(ZipFilePath file) throws IOException { + if (!file.getFileSystem().isOpen()) { throw new ClosedFileSystemException(); } - ze = ZipUtils.getEntry(file); + + try { + ZipIO.readLock(file); + ze = ZipUtils.getEntry(file); + } + finally { + ZipIO.readUnlock(file); + } } public FileTime creationTime() { Modified: VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFilePath.java =================================================================== --- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFilePath.java 2009-10-22 21:18:50 UTC (rev 6187) +++ VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFilePath.java 2009-10-22 22:05:18 UTC (rev 6188) @@ -28,7 +28,7 @@ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package com.sun.nio.zipfs; +package VASSAL.tools.nio.file.zipfs; import java.io.File; import java.io.FilterInputStream; @@ -271,7 +271,6 @@ int position = offsets.get(count - 1); String parent = subString(0, position - 1); return new ZipFilePath(this.fileSystem, parent.getBytes()); - } public ZipFilePath getParentEntry() { @@ -417,7 +416,7 @@ return this; } else { - //add / bofore the existing path + // add / bofore the existing path byte[] defaultdir = fileSystem.getDefaultDir().getBytes(); int defaultlen = defaultdir.length; boolean endsWith = (defaultdir[defaultlen - 1] == '/'); @@ -725,6 +724,7 @@ throw new UnsupportedOperationException("Not supported."); } +// FIXME: write lock @Override public Path createDirectory( FileAttribute<?>... attrs) throws IOException { @@ -747,87 +747,22 @@ } } +// FIXME: why is this under a lock? try { begin(); + ZipFilePath realPath = getResolvedPathForZip(); if (realPath.getNameCount() == 0) { throw new IOException("entry missing in the path"); } - else { - String zf = getZipFile(); - ZipFile zfile = new ZipFile(zf); - String entryStr = realPath.getEntryName(realPath.getEntryNameCount() - 1).toString(); - ZipEntry entry = zfile.getEntry(entryStr); - if (entry == null) { - zfile.close(); - throw new IOException("entry not found" + entryStr); - } - return new ZipFilePathInputStream(zfile.getInputStream(entry)); - } + return ZipIO.in(this, options); } finally { end(); } } - private class ZipFilePathInputStream extends FilterInputStream { - public ZipFilePathInputStream(InputStream in) { - super(in); - fileSystem.addCloseable(this); - } - - @Override - public void close() throws IOException { - in.close(); - fileSystem.removeCloseable(this); - } - } - - private class ZipFilePathSeekableByteChannel implements SeekableByteChannel { - private final SeekableByteChannel ch; - - public ZipFilePathSeekableByteChannel(SeekableByteChannel ch) { - this.ch = ch; - fileSystem.addCloseable(this); - } - - public long position() throws IOException { - return ch.position(); - } - - public SeekableByteChannel position(long newPosition) throws IOException { - ch.position(newPosition); - return this; - } - - public int read(ByteBuffer dst) throws IOException { - return ch.read(dst); - } - - public long size() throws IOException { - return ch.size(); - } - - public SeekableByteChannel truncate(long size) throws IOException { - ch.truncate(size); - return this; - } - - public int write(ByteBuffer src) throws IOException { - return ch.write(src); - } - - public boolean isOpen() { - return ch.isOpen(); - } - - public void close() throws IOException { - ch.close(); - fileSystem.removeCloseable(this); - } - } - @Override public DirectoryStream<Path> newDirectoryStream( Filter<? super Path> filter) throws IOException @@ -869,11 +804,13 @@ return newDirectoryStream(filter); } +// FIXME: write lock @Override public void delete() throws IOException { throw new ReadOnlyFileSystemException(); } +// FIXME: write lock @Override public void deleteIfExists() throws IOException { throw new ReadOnlyFileSystemException(); @@ -910,9 +847,9 @@ return new JarFileAttributeView(this); } return null; - } +// FIXME: write lock public void setAttribute(String attribute, Object value, LinkOption... options) { throw new UnsupportedOperationException(); } @@ -938,6 +875,7 @@ return fileView.getAttribute(attr); } +// FIXME: read lock public Map<String,?> readAttributes(String attribute, LinkOption... options) throws IOException { @@ -1027,12 +965,13 @@ }; } +// FIXME: read lock +// FIXME: write lock @Override public SeekableByteChannel newByteChannel( Set<? extends OpenOption> options, FileAttribute<?>... attrs) throws IOException { // check for options of null type and option is an intance of StandardOpenOption - for (OpenOption option : options) { if (option == null) { throw new NullPointerException(); @@ -1041,11 +980,13 @@ throw new IllegalArgumentException(); } } + boolean openedForWriteOrAppend = options.contains(StandardOpenOption.WRITE) || options.contains(StandardOpenOption.APPEND); if (openedForWriteOrAppend) { throw new ReadOnlyFileSystemException(); } + boolean openedForRead = options.contains(StandardOpenOption.READ); openedForRead = openedForRead || true; // if not opened for read then set openedForRed to true; @@ -1055,29 +996,13 @@ try { begin(); + ZipFilePath realPath = getResolvedPathForZip(); if (realPath.getNameCount() == 0) { throw new IOException("entry Not Found"); } - else { - String zf = getZipFile(); - ZipFile zfile = new ZipFile(zf); - String entryStr = realPath.getEntryName(realPath.getEntryNameCount() - 1).toString(); - ZipEntry entry = zfile.getEntry(entryStr); - if (entry == null) { - throw new IOException("entry not found" + entryStr); - } - InputStream in = zfile.getInputStream(entry); - Path pathtoZip = Paths.get(ZipUtils.readFileInZip(in)); - zfile.close(); - - return new ZipFilePathSeekableByteChannel( - new FileChannelAdapter( - fileSystem.provider().newFileChannel(pathToZip, options) - ) - ); - } + return ZipIO.channel(this, options); } finally { end(); @@ -1092,7 +1017,7 @@ return newByteChannel(set); } - private String getZipFile() throws IOException { + String getZipFile() throws IOException { String pathtoZip = null; ZipFilePath realPath = getResolvedPathForZip(); @@ -1139,16 +1064,27 @@ if (nameCount == 0) { throw new NoSuchFileException(toString()); } - ZipEntryInfo ze = ZipUtils.getEntry(resolvedZipPath); - if (w) { - throw new AccessDeniedException("write access denied for the file: " + this.toString()); - } - if (x) { - long attrs = ze.extAttrs; - if (!((((attrs << 4) >> 24) & 0x04) == 0x04)) { - throw new AccessDeniedException("execute access denied for the file: " + this.toString()); + + try { + ZipIO.readLock(resolvedZipPath); + + ZipEntryInfo ze = ZipUtils.getEntry(resolvedZipPath); + if (w) { + throw new AccessDeniedException( + "write access denied for the file: " + this.toString()); } + + if (x) { + long attrs = ze.extAttrs; + if (!((((attrs << 4) >> 24) & 0x04) == 0x04)) { + throw new AccessDeniedException( + "execute access denied for the file: " + this.toString()); + } + } } + finally { + ZipIO.readUnlock(resolvedZipPath); + } } finally { end(); @@ -1200,22 +1136,26 @@ return new ZipFilePath(fileSystem, pathForZip, pathForZip); } +// FIXME: write lock @Override public Path createFile(FileAttribute<?>... attrs) { throw new ReadOnlyFileSystemException(); } +// FIXME: write lock @Override public OutputStream newOutputStream(OpenOption... options) { throw new ReadOnlyFileSystemException(); } - +// FIXME: write lock @Override public Path moveTo(Path target, CopyOption... options) { throw new ReadOnlyFileSystemException(); } +// FIXME: read lock +// FIXME: write lock @Override public Path copyTo(Path target, CopyOption... options) throws IOException { if ((getFileSystem().provider() == target.getFileSystem().provider())) Modified: VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileStore.java =================================================================== --- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileStore.java 2009-10-22 21:18:50 UTC (rev 6187) +++ VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileStore.java 2009-10-22 22:05:18 UTC (rev 6188) @@ -28,7 +28,7 @@ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package com.sun.nio.zipfs; +package VASSAL.tools.nio.file.zipfs; import java.io.IOException; /* Modified: VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileStream.java =================================================================== --- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileStream.java 2009-10-22 21:18:50 UTC (rev 6187) +++ VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileStream.java 2009-10-22 22:05:18 UTC (rev 6188) @@ -28,7 +28,7 @@ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package com.sun.nio.zipfs; +package VASSAL.tools.nio.file.zipfs; import VASSAL.tools.nio.file.*; Modified: VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileSystem.java =================================================================== --- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileSystem.java 2009-10-22 21:18:50 UTC (rev 6187) +++ VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileSystem.java 2009-10-22 22:05:18 UTC (rev 6188) @@ -28,7 +28,7 @@ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package com.sun.nio.zipfs; +package VASSAL.tools.nio.file.zipfs; import VASSAL.tools.nio.file.*; import VASSAL.tools.nio.file.attribute.*; @@ -56,7 +56,7 @@ private final ReadWriteLock closeLock = new ReentrantReadWriteLock(); private boolean open = true; - private Set<Closeable> closeables = + private final Set<Closeable> closeables = Collections.synchronizedSet(new HashSet<Closeable>()); ZipFileSystem(ZipFileSystemProvider provider, FileRef fref) { @@ -118,7 +118,6 @@ closeLock.readLock().unlock(); } -// FIXME: closeables needs to be synchronized or concurrent // FIXME // Free all cached Zip/Jar files private void implClose(URI root) throws IOException { @@ -136,11 +135,11 @@ } } - boolean addCloseable(Closeable obj) { + boolean registerCloseable(Closeable obj) { return closeables.add(obj); } - boolean removeCloseable(Closeable obj) { + boolean unregisterCloseable(Closeable obj) { return closeables.remove(obj); } Modified: VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileSystemProvider.java =================================================================== --- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileSystemProvider.java 2009-10-22 21:18:50 UTC (rev 6187) +++ VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipFileSystemProvider.java 2009-10-22 22:05:18 UTC (rev 6188) @@ -28,7 +28,7 @@ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package com.sun.nio.zipfs; +package VASSAL.tools.nio.file.zipfs; import VASSAL.tools.nio.file.*; import VASSAL.tools.nio.file.attribute.*; @@ -42,6 +42,7 @@ import java.io.IOException; import java.net.URISyntaxException; import java.nio.channels.FileChannel; +import java.util.Collections; import java.util.HashMap; import java.util.Map; import java.util.Set; @@ -49,8 +50,10 @@ public class ZipFileSystemProvider extends FileSystemProvider { private String scheme = "zip"; - private Map<URI, ZipFileSystem> fileSystems = new HashMap<URI, ZipFileSystem>(); + private Map<URI,ZipFileSystem> fileSystems = + Collections.synchronizedMap(new HashMap<URI,ZipFileSystem>()); + public ZipFileSystemProvider() { } @@ -215,6 +218,7 @@ return path; } +// FIXME: It's weird that this uses the default fs! @Override public FileChannel newFileChannel(Path path, Set<? extends OpenOption> options, Modified: VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipHeaderConstants.java =================================================================== --- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipHeaderConstants.java 2009-10-22 21:18:50 UTC (rev 6187) +++ VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipHeaderConstants.java 2009-10-22 22:05:18 UTC (rev 6188) @@ -28,9 +28,8 @@ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ +package VASSAL.tools.nio.file.zipfs; -package com.sun.nio.zipfs; - public class ZipHeaderConstants { public static final int LOCAL_FILE_HDR_SIG = 0x04034b50; Added: VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipIO.java =================================================================== --- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipIO.java (rev 0) +++ VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipIO.java 2009-10-22 22:05:18 UTC (rev 6188) @@ -0,0 +1,324 @@ +package VASSAL.tools.nio.file.zipfs; + +import java.io.FilterInputStream; +import java.io.FilterOutputStream; +import java.io.IOException; +import java.io.InputStream; +import java.io.OutputStream; +import java.nio.ByteBuffer; +import java.util.Set; +import java.util.concurrent.ConcurrentMap; +import java.util.concurrent.ConcurrentHashMap; +import java.util.zip.ZipEntry; +import java.util.zip.ZipFile; + +import VASSAL.tools.nio.channels.FileChannelAdapter; +import VASSAL.tools.nio.channels.SeekableByteChannel; +import VASSAL.tools.nio.file.OpenOption; +import VASSAL.tools.nio.file.Path; +import VASSAL.tools.nio.file.Paths; + +class ZipIO { + private ZipIO() {} + + private static final ZipNode roots = new ZipNode(null, ""); + + static void readLock(ZipFilePath path) { + lockSubtree(path); + } + + static void writeLock(ZipFilePath path) { + ZipNode zn = lockSubtree(path.getParent()); + zn = buildNode(zn, path.getName().toString()); + zn.lock.writeLock().lock(); + } + + private static ZipNode lockSubtree(ZipFilePath path) { + + ZipNode zn = buildNode(roots, path.getFileSystem().getZipFileSystemFile()); + zn.lock.readLock().lock(); + + for (Path part : path) { + zn = buildNode(zn, part.toString()); + zn.lock.readLock().lock(); + } + + return zn; + } + + private static ZipNode buildNode(ZipNode parent, String name) { + final ZipNode n0 = new ZipNode(parent, name); + final ZipNode n1 = parent.children.putIfAbsent(name, n0); + return n1 == null ? n0 : n1; + } + + static void readUnlock(ZipFilePath path) { + unlockSubtree(path); + } + + static void writeUnlock(ZipFilePath path) { + ZipNode zn = + roots.children.get(path.getFileSystem().getZipFileSystemFile()); + + for (Path part : path) zn = zn.children.get(part.toString()); + zn.lock.writeLock().unlock(); + + readUnlock(path.getParent()); + } + + private static void unlockSubtree(ZipFilePath path) { + ZipNode zn = + roots.children.get(path.getFileSystem().getZipFileSystemFile()); + + for (Path part : path) zn = zn.children.get(part.toString()); + while (zn != null) { + zn.lock.readLock().unlock(); + zn = zn.parent; + } + } + + static InputStream wrap(ZipFilePath path, InputStream in) { + return new RegisteredInputStream(path.getFileSystem(), in); + } + + static OutputStream wrap(ZipFilePath path, OutputStream in) { + return new RegisteredOutputStream(path.getFileSystem(), in); + } + + static SeekableByteChannel wrap(ZipFilePath path, SeekableByteChannel ch) { + return new RegisteredChannel(path.getFileSystem(), ch); + } + + static InputStream wrapLocked(ZipFilePath path, InputStream in) { + return new LockedInputStream(path, in); + } + + static OutputStream wrapLocked(ZipFilePath path, OutputStream in) { + return new LockedOutputStream(path, in); + } + + static SeekableByteChannel wrapReadLocked(ZipFilePath path, + SeekableByteChannel ch) { + return new ReadLockedChannel(path, ch); + } + + static SeekableByteChannel wrapWriteLocked(ZipFilePath path, + SeekableByteChannel ch) { + return new WriteLockedChannel(path, ch); + } + + private static class RegisteredInputStream extends FilterInputStream { + private final ZipFileSystem fs; + + public RegisteredInputStream(ZipFileSystem fs, InputStream in) { + super(in); + this.fs = fs; + fs.registerCloseable(this); + } + + @Override + public void close() throws IOException { + try { + in.close(); + } + finally { + fs.unregisterCloseable(this); + } + } + } + + private static class LockedInputStream extends RegisteredInputStream { + private final ZipFilePath path; + + public LockedInputStream(ZipFilePath path, InputStream in) { + super(path.getFileSystem(), in); + this.path = path; + readLock(path); + } + + @Override + public void close() throws IOException { + try { + super.close(); + } + finally { + readUnlock(path); + } + } + } + + private static class RegisteredOutputStream extends FilterOutputStream { + private final ZipFileSystem fs; + + public RegisteredOutputStream(ZipFileSystem fs, OutputStream out) { + super(out); + this.fs = fs; + fs.registerCloseable(this); + } + + @Override + public void close() throws IOException { + try { + out.close(); + } + finally { + fs.unregisterCloseable(this); + } + } + } + + private static class LockedOutputStream extends RegisteredOutputStream { + private final ZipFilePath path; + + public LockedOutputStream(ZipFilePath path, OutputStream out) { + super(path.getFileSystem(), out); + this.path = path; + writeLock(path); + } + + @Override + public void close() throws IOException { + try { + super.close(); + } + finally { + writeUnlock(path); + } + } + } + + private static class RegisteredChannel implements SeekableByteChannel { + private final ZipFileSystem fs; + private final SeekableByteChannel ch; + + public RegisteredChannel(ZipFileSystem fs, SeekableByteChannel ch) { + this.fs = fs; + this.ch = ch; + fs.registerCloseable(this); + } + + public long position() throws IOException { + return ch.position(); + } + + public SeekableByteChannel position(long newPosition) throws IOException { + ch.position(newPosition); + return this; + } + + public int read(ByteBuffer dst) throws IOException { + return ch.read(dst); + } + + public long size() throws IOException { + return ch.size(); + } + + public SeekableByteChannel truncate(long size) throws IOException { + ch.truncate(size); + return this; + } + + public int write(ByteBuffer src) throws IOException { + return ch.write(src); + } + + public boolean isOpen() { + return ch.isOpen(); + } + + public void close() throws IOException { + try { + ch.close(); + } + finally { + fs.unregisterCloseable(this); + } + } + } + + private static class ReadLockedChannel extends RegisteredChannel { + private final ZipFilePath path; + + public ReadLockedChannel(ZipFilePath path, SeekableByteChannel ch) { + super(path.getFileSystem(), ch); + this.path = path; + } + + @Override + public void close() throws IOException { + try { + super.close(); + } + finally { + readUnlock(path); + } + } + } + + private static class WriteLockedChannel extends RegisteredChannel { + private final ZipFilePath path; + + public WriteLockedChannel(ZipFilePath path, SeekableByteChannel ch) { + super(path.getFileSystem(), ch); + this.path = path; + } + + @Override + public void close() throws IOException { + try { + super.close(); + } + finally { + writeUnlock(path); + } + } + } + + static InputStream in(ZipFilePath path, OpenOption... opts) + throws IOException { + final String zf = path.getZipFile(); + final ZipFile zfile = new ZipFile(zf); + final String entryStr = + path.getEntryName(path.getEntryNameCount() - 1).toString(); + +// FIXME: zfile not closed along some paths!!! + final ZipEntry entry = zfile.getEntry(entryStr); + if (entry == null) { + zfile.close(); + throw new IOException("entry not found" + entryStr); + } + + return wrap(path, zfile.getInputStream(entry)); + } + +/* + static OutputStream out(ZipFilePath path, OpenOption... opts) + throws IOException { + } +*/ + + static SeekableByteChannel channel(ZipFilePath path, + Set<? extends OpenOption> opts) + throws IOException { + final String zf = path.getZipFile(); + final ZipFile zfile = new ZipFile(zf); + final String entryStr = + path.getEntryName(path.getEntryNameCount() - 1).toString(); + +// FIXME: zfile not closed along some paths!!! + final ZipEntry entry = zfile.getEntry(entryStr); + if (entry == null) { + throw new IOException("entry not found" + entryStr); + } + + final InputStream in = zfile.getInputStream(entry); + final Path pathToZip = Paths.get(ZipUtils.readFileInZip(in)); + zfile.close(); + + final ZipFileSystem fs = path.getFileSystem(); + return wrap(path, + new FileChannelAdapter(fs.provider().newFileChannel(pathToZip, opts)) + ); + } +} Added: VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipLock.java =================================================================== --- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipLock.java (rev 0) +++ VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipLock.java 2009-10-22 22:05:18 UTC (rev 6188) @@ -0,0 +1,88 @@ +package VASSAL.tools.nio.file.zipfs; + +import java.util.concurrent.TimeUnit; +import java.util.concurrent.locks.AbstractQueuedSynchronizer; +import java.util.concurrent.locks.Condition; +import java.util.concurrent.locks.Lock; +import java.util.concurrent.locks.ReadWriteLock; + +// Yellow and blue make green. Now it's sealed! +class ZipLock implements ReadWriteLock { + public Lock readLock() { return new ReadLock(); } + public Lock writeLock() { return new WriteLock(); } + + private final Sync sync = new Sync(); + + private class ReadLock implements Lock { + public void lock() { sync.acquireShared(0); } + public void unlock() { sync.releaseShared(0); } + + public void lockInterruptibly() { + throw new UnsupportedOperationException(); + } + + public Condition newCondition() { + throw new UnsupportedOperationException(); + } + + public boolean tryLock() { + throw new UnsupportedOperationException(); + } + + public boolean tryLock(long time, TimeUnit unit) { + throw new UnsupportedOperationException(); + } + } + + private class WriteLock implements Lock { + public void lock() { sync.acquire(0); } + public void unlock() { sync.release(0); } + + public void lockInterruptibly() { + throw new UnsupportedOperationException(); + } + + public Condition newCondition() { + throw new UnsupportedOperationException(); + } + + public boolean tryLock() { + throw new UnsupportedOperationException(); + } + + public boolean tryLock(long time, TimeUnit unit) { + throw new UnsupportedOperationException(); + } + } + + // Read states are positive, the write state is -1. + // State 0 means that no locks are held. + + private static class Sync extends AbstractQueuedSynchronizer { + private static final long serialVersionUID = 1L; + + @Override + protected boolean tryAcquire(int dummy) { + return compareAndSetState(0, -1); + } + + @Override + protected boolean tryRelease(int dummy) { + if (getState() != -1) throw new IllegalMonitorStateException(); + return compareAndSetState(-1, 0); + } + + @Override + protected int tryAcquireShared(int dummy) { + final int s = getState(); + return s >= 0 && compareAndSetState(s, s+1) ? 1 : -1; + } + + @Override + protected boolean tryReleaseShared(int dummy) { + final int s = getState(); + if (s < 1) throw new IllegalMonitorStateException(); + return compareAndSetState(s, s-1); + } + } +} Added: VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipNode.java =================================================================== --- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipNode.java (rev 0) +++ VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipNode.java 2009-10-22 22:05:18 UTC (rev 6188) @@ -0,0 +1,31 @@ +package VASSAL.tools.nio.file.zipfs; + +import java.util.concurrent.ConcurrentMap; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.locks.ReadWriteLock; + +class ZipNode { + + final String name; + final ZipNode parent; + + final ReadWriteLock lock = new ZipLock(); + + final ConcurrentMap<String,ZipNode> children = + new ConcurrentHashMap<String,ZipNode>(); + + public ZipNode(ZipNode parent, String name) { + this.name = name; + this.parent = parent; + } + + @Override + public boolean equals(Object o) { + return name.equals(o); + } + + @Override + public int hashCode() { + return name.hashCode(); + } +} Modified: VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipPathParser.java =================================================================== --- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipPathParser.java 2009-10-22 21:18:50 UTC (rev 6187) +++ VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipPathParser.java 2009-10-22 22:05:18 UTC (rev 6188) @@ -28,9 +28,8 @@ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ +package VASSAL.tools.nio.file.zipfs; -package com.sun.nio.zipfs; - import VASSAL.tools.nio.file.*; //import java.nio.file.*; import java.util.LinkedList; Modified: VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipUtils.java =================================================================== --- VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipUtils.java 2009-10-22 21:18:50 UTC (rev 6187) +++ VASSAL-src/branches/nio-fs/src/com/sun/nio/zipfs/ZipUtils.java 2009-10-22 22:05:18 UTC (rev 6188) @@ -28,7 +28,7 @@ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -package com.sun.nio.zipfs; +package VASSAL.tools.nio.file.zipfs; import VASSAL.tools.nio.file.*; import VASSAL.tools.nio.channels.SeekableByteChannel; @@ -271,7 +271,6 @@ public static boolean isJar(String path) { String lowerCase = path.toLowerCase(); return (lowerCase.endsWith(".jar")); - } public static void extractZip(ZipFilePath f) @@ -469,8 +468,7 @@ static String readFileInZip(InputStream entry) throws IOException { File tmpFile = null; try { - BufferedInputStream zipStream = new BufferedInputStream( - entry); + BufferedInputStream zipStream = new BufferedInputStream(entry); // unzip the file contents to a temp directory String prefix = "zipfs"; This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |