]> source.dussan.org Git - javassist.git/commitdiff
adds ModuleClassPath.java
authorchibash <chiba@javassist.org>
Sun, 31 Jul 2016 02:03:51 +0000 (11:03 +0900)
committerchibash <chiba@javassist.org>
Sun, 31 Jul 2016 02:03:51 +0000 (11:03 +0900)
src/main/javassist/ClassClassPath.java
src/main/javassist/ClassPool.java
src/main/javassist/ClassPoolTail.java
src/main/javassist/LoaderClassPath.java
src/main/javassist/ModuleClassPath.java [new file with mode: 0644]

index 334d61e0f433dceef673f8038c0972666c90819d..8602963058f349204bbaaea94bc211b1c8c52127 100644 (file)
@@ -40,15 +40,20 @@ import javassist.bytecode.ClassFile;
  * <code>ClassClassPath</code> uses a class object representing
  * the class including the code snippet above.
  *
+ * <p>Class files in a named module are private to that module.
+ * This method cannot obtain class files in named modules.
+ * </p>
+ * 
  * @see ClassPool#insertClassPath(ClassPath)
  * @see ClassPool#appendClassPath(ClassPath)
  * @see LoaderClassPath
+ * @see ModuleClassPath
  */
 public class ClassClassPath implements ClassPath {
-       private static final boolean useJigsaw
-               = ClassFile.MAJOR_VERSION >= ClassFile.JAVA_9;
+    private static final boolean useJigsaw
+        = ClassFile.MAJOR_VERSION >= ClassFile.JAVA_9;
 
-               private Class thisClass;
+    private Class thisClass;
 
     /** Creates a search path.
      *
@@ -76,16 +81,8 @@ public class ClassClassPath implements ClassPath {
      * Obtains a class file by <code>getResourceAsStream()</code>.
      */
     public InputStream openClassfile(String classname) throws NotFoundException {
-        String jarname = classname.replace('.', '/') + ".class";
-        if (useJigsaw)
-               try {
-                       return thisClass.getModule().getResourceAsStream(jarname);
-               }
-               catch (java.io.IOException e) {
-                       throw new NotFoundException(classname, e);
-               }
-        else
-               return thisClass.getResourceAsStream('/' + jarname);
+        String filename = '/' + classname.replace('.', '/') + ".class";
+        return thisClass.getResourceAsStream('/' + filename);
     }
 
     /**
@@ -94,22 +91,8 @@ public class ClassClassPath implements ClassPath {
      * @return null if the class file could not be found. 
      */
     public URL find(String classname) {
-        String jarname = classname.replace('.', '/') + ".class";
-        if (useJigsaw)
-               try {
-                       InputStream is = thisClass.getModule().getResourceAsStream(jarname);
-                       if (is == null)
-                               return null;
-                       else {
-                               is.close();
-                               return new URL("jar:file:unknown.jar!/" + jarname);
-                       }
-               }
-               catch (java.io.IOException e) {
-                       return null;
-               }
-        else
-               return thisClass.getResource('/' + jarname);
+        String filename = '/' + classname.replace('.', '/') + ".class";
+        return thisClass.getResource(filename);
     }
 
     /**
index c90c2c7408ffb6f8be30e4453323877342909f89..11f226f1cf2d55e08150584ecc1ed49b807f6dfa 100644 (file)
@@ -220,10 +220,12 @@ public class ClassPool {
      * </pre>
      *
      * <p>If the default class pool cannot find any class files,
-     * try <code>ClassClassPath</code> and <code>LoaderClassPath</code>.
+     * try <code>ClassClassPath</code>, <code>ModuleClassPath</code>,
+     * or <code>LoaderClassPath</code>.
      *
      * @see ClassClassPath
      * @see LoaderClassPath
+     * @see ModuleClassPath
      */
     public static synchronized ClassPool getDefault() {
         if (defaultPool == null) {
index e2ace76ee0852b7d561abd37577d56281e6aca09..7e62a8614f0e992560b15efebe64a99a7a707ce9 100644 (file)
@@ -234,8 +234,9 @@ final class ClassPoolTail {
     }
 
     public ClassPath appendSystemPath() {
-       appendClassPath(new ClassClassPath());
-       return appendClassPath(new ClassClassPath(CtClass.class));
+        ClassLoader cl = Thread.currentThread().getContextClassLoader();
+        appendClassPath(new LoaderClassPath(cl));
+       return appendClassPath(new ModuleClassPath());
     }
 
     public ClassPath insertClassPath(String pathname)
index a1580537a026982508fe72ce61236b0e97f43cf5..d516323e9ba6d278d056fec30bc6c30b7ef7b01b 100644 (file)
@@ -31,6 +31,10 @@ import java.lang.ref.WeakReference;
  *
  * <p>The given class loader must have both <code>getResourceAsStream()</code>
  * and <code>getResource()</code>.
+ * 
+ * <p>Class files in a named module are private to that module.
+ * This method cannot obtain class files in named modules.
+ * </p>
  *
  * @author <a href="mailto:bill@jboss.org">Bill Burke</a>
  * @author Shigeru Chiba
@@ -38,6 +42,7 @@ import java.lang.ref.WeakReference;
  * @see ClassPool#insertClassPath(ClassPath)
  * @see ClassPool#appendClassPath(ClassPath)
  * @see ClassClassPath
+ * @see ModuleClassPath
  */
 public class LoaderClassPath implements ClassPath {
     private WeakReference clref;
diff --git a/src/main/javassist/ModuleClassPath.java b/src/main/javassist/ModuleClassPath.java
new file mode 100644 (file)
index 0000000..c41161f
--- /dev/null
@@ -0,0 +1,126 @@
+/*
+ * Javassist, a Java-bytecode translator toolkit.
+ * Copyright (C) 1999- Shigeru Chiba. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License.  Alternatively, the contents of this file may be used under
+ * the terms of the GNU Lesser General Public License Version 2.1 or later,
+ * or the Apache License Version 2.0.
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ */
+
+package javassist;
+
+import java.io.InputStream;
+import java.lang.reflect.Layer;
+import java.lang.reflect.Module;
+import java.net.URL;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.Set;
+
+/**
+ * A search-path for obtaining a class file
+ * by <code>getResourceAsStream()</code> in <code>java.lang.reflect.Module</code>.
+ *
+ * @see ClassPool#insertClassPath(ClassPath)
+ * @see ClassPool#appendClassPath(ClassPath)
+ * @see LoaderClassPath
+ * @see ClassClassPath
+ */
+public class ModuleClassPath implements ClassPath {
+    private HashMap packages = new HashMap();
+
+    ModuleClassPath() { this(Layer.boot()); }
+
+    /**
+     * Constructs a search path.
+     *
+     * @param layer         the layer used to obtain a class file.
+     */
+    public ModuleClassPath(Layer layer) {
+        while (layer != null) {
+            Set modules = layer.modules();
+            Iterator it = modules.iterator();
+            while (it.hasNext())
+                addPackages((Module)it.next());
+
+            layer = layer.parent().orElse(null);
+        }
+    }
+
+    /**
+     * Constructs a search path.
+     *
+     * @param m         the module used to obtain a class file.
+     */
+    public ModuleClassPath(Module m) {
+        addPackages(m);
+    }
+
+    private void addPackages(Module m) {
+        String[] names = m.getPackages();
+        for (int i = 0; i < names.length; i++)
+            packages.put(names[i], m);
+    }
+
+    /**
+     * Obtains a class file by <code>getResourceAsStream()</code>.
+     */
+    public InputStream openClassfile(String classname) throws NotFoundException {
+        String filename = classname.replace('.', '/') + ".class";
+        Module m = (Module)packages.get(getPackageName(classname));
+        if (m == null)
+            return null;
+        else
+            try {
+                return m.getResourceAsStream(filename);
+            }
+            catch (java.io.IOException e) {
+                throw new NotFoundException(classname, e);
+            }
+    }
+
+    /**
+     * Obtains the URL of the specified class file.
+     *
+     * @return null if the class file could not be found. 
+     */
+    public URL find(String classname) {
+        String filename = classname.replace('.', '/') + ".class";
+        Module m = (Module)packages.get(getPackageName(classname));
+        if (m == null)
+            return null;
+        else
+            try {
+                InputStream is = m.getResourceAsStream(filename);
+                if (is == null)
+                    return null;
+                else {
+                    is.close();
+                    return new URL("jar:file:unknown.jar!/" + filename);
+                }
+            }
+            catch (java.io.IOException e) {
+                return null;
+            }
+    }
+
+    private static String getPackageName(String name) {
+        int i = name.lastIndexOf('.');
+        if (i > 0)
+            return name.substring(0, i);
+        else
+            return "";
+    }
+
+    /**
+     * Does nothing.
+     */
+    public void close() {}
+}