< prev index next >

src/java.base/share/classes/java/lang/module/ModuleFinder.java

Print this page

        

@@ -23,12 +23,10 @@
  * questions.
  */
 
 package java.lang.module;
 
-import java.io.File;
-import java.io.FilePermission;
 import java.nio.file.Files;
 import java.nio.file.Path;
 import java.nio.file.Paths;
 import java.security.AccessController;
 import java.security.Permission;

@@ -41,13 +39,13 @@
 import java.util.Objects;
 import java.util.Optional;
 import java.util.Set;
 
 import jdk.internal.module.ModuleBootstrap;
+import jdk.internal.module.ModulePatcher;
 import jdk.internal.module.ModulePath;
 import jdk.internal.module.SystemModuleFinder;
-import sun.security.action.GetPropertyAction;
 
 /**
  * A finder of modules. A {@code ModuleFinder} is used to find modules during
  * <a href="package-summary.html#resolution">resolution</a> or
  * <a href="package-summary.html#servicebinding">service binding</a>.

@@ -144,47 +142,70 @@
      * system modules are the modules in the Java run-time image.
      * The module finder will always find {@code java.base}.
      *
      * <p> If there is a security manager set then its {@link
      * SecurityManager#checkPermission(Permission) checkPermission} method is
-     * invoked to check that the caller has been granted {@link FilePermission}
-     * to recursively read the directory that is the value of the system
-     * property {@code java.home}. </p>
+     * invoked to check that the caller has been granted
+     * {@link RuntimePermission RuntimePermission("accessSystemModules")}
+     * to access the system modules. </p>
      *
      * @return A {@code ModuleFinder} that locates the system modules
      *
      * @throws SecurityException
      *         If denied by the security manager
      */
     static ModuleFinder ofSystem() {
-        String home;
-
         SecurityManager sm = System.getSecurityManager();
         if (sm != null) {
-            PrivilegedAction<String> pa = new GetPropertyAction("java.home");
-            home = AccessController.doPrivileged(pa);
-            Permission p = new FilePermission(home + File.separator + "-", "read");
-            sm.checkPermission(p);
+            sm.checkPermission(new RuntimePermission("accessSystemModules"));
+            PrivilegedAction<ModuleFinder> pa = ModuleFinder::privilegedOfSystem;
+            return AccessController.doPrivileged(pa);
         } else {
-            home = System.getProperty("java.home");
+            return privilegedOfSystem();
+        }
         }
 
+    /**
+     * Returns a module finder that locates the system modules. This method
+     * assumes it has permissions to access the runtime image.
+     */
+    private static ModuleFinder privilegedOfSystem() {
+        String home = System.getProperty("java.home");
         Path modules = Paths.get(home, "lib", "modules");
         if (Files.isRegularFile(modules)) {
             return SystemModuleFinder.getInstance();
         } else {
-            Path mlib = Paths.get(home, "modules");
-            if (Files.isDirectory(mlib)) {
-                // exploded build may be patched
-                return ModulePath.of(ModuleBootstrap.patcher(), mlib);
+            Path dir = Paths.get(home, "modules");
+            if (Files.isDirectory(dir)) {
+                return privilegedOf(ModuleBootstrap.patcher(), dir);
             } else {
                 throw new InternalError("Unable to detect the run-time image");
             }
         }
     }
 
     /**
+     * Returns a module finder that locates the system modules in an exploded
+     * image. The image may be patched.
+     */
+    private static ModuleFinder privilegedOf(ModulePatcher patcher, Path dir) {
+        ModuleFinder finder = ModulePath.of(patcher, dir);
+        return new ModuleFinder() {
+            @Override
+            public Optional<ModuleReference> find(String name) {
+                PrivilegedAction<Optional<ModuleReference>> pa = () -> finder.find(name);
+                return AccessController.doPrivileged(pa);
+            }
+            @Override
+            public Set<ModuleReference> findAll() {
+                PrivilegedAction<Set<ModuleReference>> pa = finder::findAll;
+                return AccessController.doPrivileged(pa);
+            }
+        };
+    }
+
+    /**
      * Returns a module finder that locates modules on the file system by
      * searching a sequence of directories and/or packaged modules.
      *
      * Each element in the given array is one of:
      * <ol>

@@ -199,11 +220,11 @@
      * occurrence of a module with a given name and ignores other modules of
      * that name that appear later in the sequence.
      *
      * <p> If an element is a path to a directory of modules then each entry in
      * the directory is a packaged module or the top-level directory of an
-     * exploded module. It it an error if a directory contains more than one
+     * exploded module. It is an error if a directory contains more than one
      * module with the same name. If an element is a path to a directory, and
      * that directory contains a file named {@code module-info.class}, then the
      * directory is treated as an exploded module rather than a directory of
      * modules. </p>
      *
< prev index next >