001: /*
002: * @(#)JarFileFactory.java 1.14 06/10/10
003: *
004: * Copyright 1990-2006 Sun Microsystems, Inc. All Rights Reserved.
005: * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER
006: *
007: * This program is free software; you can redistribute it and/or
008: * modify it under the terms of the GNU General Public License version
009: * 2 only, as published by the Free Software Foundation.
010: *
011: * This program is distributed in the hope that it will be useful, but
012: * WITHOUT ANY WARRANTY; without even the implied warranty of
013: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
014: * General Public License version 2 for more details (a copy is
015: * included at /legal/license.txt).
016: *
017: * You should have received a copy of the GNU General Public License
018: * version 2 along with this work; if not, write to the Free Software
019: * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
020: * 02110-1301 USA
021: *
022: * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa
023: * Clara, CA 95054 or visit www.sun.com if you need additional
024: * information or have any questions.
025: *
026: */
027:
028: package sun.net.www.protocol.jar;
029:
030: import java.io.*;
031: import java.net.*;
032: import java.util.*;
033: import java.util.jar.*;
034: import java.util.zip.ZipFile;
035: import java.security.Permission;
036:
037: /* A factory for cached JAR file. This class is used to both retrieve
038: * and cache Jar files.
039: *
040: * @author Benjamin Renaud
041: * @since JDK1.2
042: */
043: class JarFileFactory {
044:
045: /* the url to file cache */
046: private static HashMap fileCache = new HashMap();
047:
048: /* the file to url cache */
049: private static HashMap urlCache = new HashMap();
050:
051: URLConnection getConnection(JarFile jarFile) throws IOException {
052: URL u = (URL) urlCache.get(jarFile);
053: if (u != null)
054: return u.openConnection();
055:
056: return null;
057: }
058:
059: public JarFile get(URL url) throws IOException {
060: return get(url, true);
061: }
062:
063: JarFile get(URL url, boolean useCaches) throws IOException {
064: if (url.getProtocol().equalsIgnoreCase("file")) {
065: // Deal with UNC pathnames specially. See 4180841
066:
067: String host = url.getHost();
068: if (host != null && !host.equals("")
069: && !host.equals("localhost")) {
070:
071: url = new URL("file", "", "//" + host + url.getPath());
072: }
073: }
074:
075: JarFile result = null;
076: JarFile local_result = null;
077:
078: if (useCaches) {
079: synchronized (this ) {
080: result = getCachedJarFile(url);
081: }
082: if (result == null) {
083: local_result = URLJarFile.getJarFile(url);
084: synchronized (this ) {
085: result = getCachedJarFile(url);
086: if (result == null) {
087: fileCache.put(url, local_result);
088: urlCache.put(local_result, url);
089: result = local_result;
090: } else {
091: if (local_result != null) {
092: local_result.close();
093: }
094: }
095: }
096: }
097: } else {
098: result = URLJarFile.getJarFile(url);
099: }
100: if (result == null)
101: throw new FileNotFoundException(url.toString());
102:
103: return result;
104: }
105:
106: private JarFile getCachedJarFile(URL url) {
107: JarFile result = (JarFile) fileCache.get(url);
108:
109: /* if the JAR file is cached, the permission will always be there */
110: if (result != null) {
111: Permission perm = getPermission(result);
112: if (perm != null) {
113: SecurityManager sm = System.getSecurityManager();
114: if (sm != null) {
115: try {
116: sm.checkPermission(perm);
117: } catch (SecurityException se) {
118: // fallback to checkRead/checkConnect for pre 1.2
119: // security managers
120: if ((perm instanceof java.io.FilePermission)
121: && perm.getActions().indexOf("read") != -1) {
122: sm.checkRead(perm.getName());
123: } else if ((perm instanceof java.net.SocketPermission)
124: && perm.getActions().indexOf("connect") != -1) {
125: sm.checkConnect(url.getHost(), url
126: .getPort());
127: } else {
128: throw se;
129: }
130: }
131: }
132: }
133: }
134: return result;
135: }
136:
137: private Permission getPermission(JarFile jarFile) {
138: try {
139: URLConnection uc = (URLConnection) getConnection(jarFile);
140: if (uc != null)
141: return uc.getPermission();
142: } catch (IOException ioe) {
143: // gulp
144: }
145:
146: return null;
147: }
148: }
|