changeset 13562:9f4daaeff560

Move Layer to java.lang.reflect
author alanb
date Sat, 01 Aug 2015 21:57:25 +0100
parents 11021f518613
children 525e245debde
files make/src/classes/build/tools/jigsaw/GenGraphs.java make/src/classes/build/tools/jigsaw/ModuleSummary.java src/java.base/share/classes/java/lang/Class.java src/java.base/share/classes/java/lang/ClassLoader.java src/java.base/share/classes/java/lang/System.java src/java.base/share/classes/java/lang/module/Configuration.java src/java.base/share/classes/java/lang/module/Layer.java src/java.base/share/classes/java/lang/module/LayerInstantiationException.java src/java.base/share/classes/java/lang/module/ModuleDescriptor.java src/java.base/share/classes/java/lang/module/ModuleReference.java src/java.base/share/classes/java/lang/module/ResolutionException.java src/java.base/share/classes/java/lang/module/Resolver.java src/java.base/share/classes/java/lang/reflect/Layer.java src/java.base/share/classes/java/lang/reflect/LayerInstantiationException.java src/java.base/share/classes/java/lang/reflect/Module.java src/java.base/share/classes/java/util/ServiceLoader.java src/java.base/share/classes/jdk/internal/misc/BootLoader.java src/java.base/share/classes/jdk/internal/misc/Modules.java src/java.base/share/classes/jdk/internal/module/ModuleBootstrap.java src/java.base/share/classes/jdk/internal/module/ModuleLoaderMap.java src/java.base/share/classes/sun/launcher/LauncherHelper.java src/java.base/share/classes/sun/misc/JavaLangAccess.java src/java.base/share/classes/sun/misc/JavaLangModuleAccess.java src/java.base/share/classes/sun/misc/JavaLangReflectAccess.java src/java.base/share/classes/sun/misc/JavaLangReflectModuleAccess.java src/java.base/share/classes/sun/misc/SharedSecrets.java src/jdk.jlink/share/classes/jdk/tools/jlink/JlinkTask.java src/jdk.jlink/share/classes/jdk/tools/jlink/TaskHelper.java src/jdk.jlink/share/classes/jdk/tools/jlink/internal/ImagePluginConfiguration.java src/jdk.jlink/share/classes/jdk/tools/jlink/internal/ImagePluginProviderRepository.java test/java/lang/ModuleClassLoader/Basic.java test/jdk/jigsaw/etc/automaticmodules/AutomaticModulesTest.java test/jdk/jigsaw/etc/automaticmodules/src/basictest/test/Main.java test/jdk/jigsaw/etc/automaticmodules/src/sptest/test/Main.java test/jdk/jigsaw/functional/container/src/container/container/Main.java test/jdk/jigsaw/launcher/upgrademodulepath/src/test/jdk/test/Main.java test/jdk/jigsaw/module/ConfigurationTest.java test/jdk/jigsaw/module/LayerTest.java test/jdk/jigsaw/reflect/LayerTest.java test/jdk/jigsaw/reflect/ModuleTest.java test/jdk/jigsaw/reflect/TEST.properties test/jdk/jigsaw/resources/basic/Basic.java test/jdk/jigsaw/services/layer/BasicLayerTest.java test/jdk/jigsaw/services/layer/CustomLayerTest.java test/jdk/jigsaw/tools/jlink/JLinkTest.java test/jdk/jigsaw/tools/jlink/basic/src/test/jdk/test/Test.java test/jdk/jigsaw/tools/jlink/plugins/PluginsNegativeTest.java
diffstat 47 files changed, 1057 insertions(+), 1000 deletions(-) [+]
line wrap: on
line diff
--- a/make/src/classes/build/tools/jigsaw/GenGraphs.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/make/src/classes/build/tools/jigsaw/GenGraphs.java	Sat Aug 01 21:57:25 2015 +0100
@@ -38,9 +38,9 @@
 import java.util.TreeSet;
 import java.util.function.Function;
 import java.util.stream.Collectors;
-
+import java.lang.reflect.Layer;
+import java.lang.reflect.Module;
 import java.lang.module.Configuration;
-import java.lang.module.Layer;
 import java.lang.module.ModuleReference;
 import java.lang.module.ModuleFinder;
 import java.lang.module.ModuleDescriptor;
--- a/make/src/classes/build/tools/jigsaw/ModuleSummary.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/make/src/classes/build/tools/jigsaw/ModuleSummary.java	Sat Aug 01 21:57:25 2015 +0100
@@ -51,9 +51,8 @@
 import java.util.stream.Stream;
 import java.util.zip.ZipEntry;
 import java.util.zip.ZipFile;
-
+import java.lang.reflect.Layer;
 import java.lang.module.Configuration;
-import java.lang.module.Layer;
 import java.lang.module.ModuleReference;
 import java.lang.module.ModuleFinder;
 import java.lang.module.ModuleDescriptor;
--- a/src/java.base/share/classes/java/lang/Class.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/java.base/share/classes/java/lang/Class.java	Sat Aug 01 21:57:25 2015 +0100
@@ -25,7 +25,7 @@
 
 package java.lang;
 
-import java.io.IOException;
+import java.lang.annotation.Annotation;
 import java.lang.reflect.AnnotatedElement;
 import java.lang.reflect.Array;
 import java.lang.reflect.GenericArrayType;
@@ -41,7 +41,9 @@
 import java.lang.reflect.TypeVariable;
 import java.lang.reflect.InvocationTargetException;
 import java.lang.reflect.AnnotatedType;
+import java.lang.reflect.Proxy;
 import java.lang.ref.SoftReference;
+import java.io.IOException;
 import java.io.InputStream;
 import java.io.ObjectStreamField;
 import java.net.URL;
@@ -58,12 +60,11 @@
 import java.util.HashMap;
 import java.util.Objects;
 import java.util.StringJoiner;
-
 import jdk.internal.misc.BootLoader;
-import sun.misc.JavaLangReflectAccess;
+import jdk.internal.HotSpotIntrinsicCandidate;
+import sun.misc.JavaLangReflectModuleAccess;
+import sun.misc.Unsafe;
 import sun.misc.SharedSecrets;
-import sun.misc.Unsafe;
-import jdk.internal.HotSpotIntrinsicCandidate;
 import sun.reflect.CallerSensitive;
 import sun.reflect.ConstantPool;
 import sun.reflect.Reflection;
@@ -75,8 +76,6 @@
 import sun.reflect.generics.repository.ConstructorRepository;
 import sun.reflect.generics.scope.ClassScope;
 import sun.security.util.SecurityConstants;
-import java.lang.annotation.Annotation;
-import java.lang.reflect.Proxy;
 import sun.reflect.annotation.*;
 import sun.reflect.misc.ReflectUtil;
 
--- a/src/java.base/share/classes/java/lang/ClassLoader.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/java.base/share/classes/java/lang/ClassLoader.java	Sat Aug 01 21:57:25 2015 +0100
@@ -2326,8 +2326,8 @@
     public Module getUnnamedModule() {
         Module module = unnamedModule;
         if (module == null) {
-            module = SharedSecrets.getJavaLangReflectAccess()
-                    .defineUnnamedModule(this);
+            module = SharedSecrets.getJavaLangReflectModuleAccess()
+                                  .defineUnnamedModule(this);
             boolean set = trySetObjectField("unnamedModule", module);
             if (!set) {
                 // beaten by someone else
--- a/src/java.base/share/classes/java/lang/System.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/java.base/share/classes/java/lang/System.java	Sat Aug 01 21:57:25 2015 +0100
@@ -34,9 +34,10 @@
 import java.io.InputStream;
 import java.io.PrintStream;
 import java.io.UnsupportedEncodingException;
+import java.lang.annotation.Annotation;
 import java.lang.reflect.Constructor;
 import java.lang.reflect.Executable;
-import java.lang.annotation.Annotation;
+import java.lang.reflect.Layer;
 import java.lang.reflect.Modifier;
 import java.lang.reflect.Module;
 import java.security.AccessControlContext;
@@ -1228,13 +1229,16 @@
         sun.misc.VM.initLevel(1);
     }
 
+    // @see #initPhase2()
+    private static Layer bootLayer;
+
     /*
      * Invoked by VM.  Phase 2 module system initialization.
      * Only classes in java.base can be loaded in this phase.
      */
     private static void initPhase2() {
         // initialize the module system
-        ModuleBootstrap.boot();
+        System.bootLayer = ModuleBootstrap.boot();
 
         // base module needs to be loose
         Module base = Object.class.getModule();
@@ -1346,6 +1350,9 @@
             public void invokeFinalize(Object o) throws Throwable {
                 o.finalize();
             }
+            public Layer getBootLayer() {
+                return bootLayer;
+            }
             public ServicesCatalog getServicesCatalog(ClassLoader cl) {
                 return cl.getServicesCatalog();
             }
--- a/src/java.base/share/classes/java/lang/module/Configuration.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/java.base/share/classes/java/lang/module/Configuration.java	Sat Aug 01 21:57:25 2015 +0100
@@ -25,6 +25,7 @@
 
 package java.lang.module;
 
+import java.lang.reflect.Layer;
 import java.util.Arrays;
 import java.util.Collection;
 import java.util.Objects;
--- a/src/java.base/share/classes/java/lang/module/Layer.java	Sat Aug 01 20:33:01 2015 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,362 +0,0 @@
-/*
- * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.  Oracle designates this
- * particular file as subject to the "Classpath" exception as provided
- * by Oracle in the LICENSE file that accompanied this code.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package java.lang.module;
-
-import java.lang.reflect.Module;
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.Map;
-import java.util.Objects;
-import java.util.Optional;
-import java.util.Set;
-import java.util.stream.Collectors;
-
-import sun.misc.JavaLangModuleAccess;
-import sun.misc.JavaLangReflectAccess;
-import sun.misc.SharedSecrets;
-
-/**
- * Represents a layer of modules in the Java virtual machine.
- *
- * <p> The following example resolves a module named <em>myapp</em> and creates
- * a {@code Layer} with the resulting {@link Configuration}. In the example
- * then all modules are associated with the same class loader. </p>
- *
- * <pre>{@code
- *     ModuleFinder finder = ModuleFinder.of(dir1, dir2, dir3);
- *
- *     Configuration cf
- *         = Configuration.resolve(ModuleFinder.empty(),
- *                                 Layer.boot(),
- *                                 finder,
- *                                 "myapp");
- *
- *     ClassLoader loader = new ModuleClassLoader(cf);
- *
- *     Layer layer = Layer.create(cf, mn -> loader);
- *
- *     Class<?> c = layer.findLoader("myapp").loadClass("app.Main");
- * }</pre>
- *
- * @since 1.9
- */
-
-public final class Layer {
-
-    private static final JavaLangReflectAccess reflectAccess
-        = SharedSecrets.getJavaLangReflectAccess();
-
-    private static final Layer EMPTY_LAYER
-        = new Layer(null, Collections.emptyMap());
-
-    private final Configuration cf;
-    private final Map<String, Module> nameToModule;
-
-    /**
-     * Creates a new {@code Layer} object.
-     */
-    private Layer(Configuration cf, Map<String, Module> map) {
-        this.cf = cf;
-        this.nameToModule = map; // no need to create defensive copy
-    }
-
-
-    /**
-     * Finds the class loader for a module.
-     *
-     * @see Layer#create
-     * @since 1.9
-     */
-    @FunctionalInterface
-    public static interface ClassLoaderFinder {
-        /**
-         * Returns the class loader for the given module.
-         *
-         * <p> If this method is invoked several times to locate the same
-         * module (by name) then it will return the same result each time.
-         * Failure to do so will lead to unspecified behavior when creating
-         * a Layer. </p>
-         */
-        ClassLoader loaderForModule(String moduleName);
-    }
-
-
-    /**
-     * Creates a {@code Layer} by defining the modules, as described in the
-     * given {@code Configuration}, to the Java virtual machine.
-     *
-     * <p> Modules are mapped to module-capable class loaders by means of the
-     * given {@code ClassLoaderFinder} and defined to the Java virtual machine.
-     * The caller of this method must arrange for the class loaders to be
-     * ready to load from these modules before attempting to load classes or
-     * resources. This can be before or after the {@code Layer} is created. </p>
-     *
-     * <p> Creating a {@code Layer} may fail for several reasons: </p>
-     *
-     * <ul>
-     *
-     *     <li> Two or more modules with the same package (exported or
-     *          concealed) are mapped to the same class loader. </li>
-     *
-     *     <li> A module is mapped to a class loader that already has a module
-     *          of the same name defined to it. </li>
-     *
-     *     <li> A module is mapped to a class loader that has already defined
-     *          types in any of the packages in the module. </li>
-     *
-     * </ul>
-     *
-     * @apiNote Need to decide if there is a permission check needed here. We
-     * can't have an untrusted ClassLoaderFinder returning null and have this
-     * method define modules to the boot loader. For now, the built-in class
-     * loaders do a permission check to defend against this.
-     *
-     * @implNote Some of the failure reasons listed cannot be detected in
-     * advance, hence it is possible for Layer.create to fail with some of the
-     * modules in the configuration defined to the run-time.
-     *
-     * @throws LayerInstantiationException
-     *         If creating the {@code Layer} fails for any of the reasons
-     *         listed above
-     */
-    public static Layer create(Configuration cf, ClassLoaderFinder clf) {
-        Objects.requireNonNull(cf);
-        Objects.requireNonNull(clf);
-
-        // For now, no two modules in the boot Layer may contain the same
-        // package so we use a simple check for the boot Layer to keep
-        // the overhead at startup to a minimum
-        if (bootLayer == null) {
-            checkBootModulesForDuplicatePkgs(cf);
-        } else {
-            checkForDuplicatePkgs(cf, clf);
-        }
-
-        Layer layer;
-        try {
-            layer = new Layer(cf, reflectAccess.defineModules(cf, clf));
-        } catch (Exception | Error e) {
-            throw new LayerInstantiationException(e);
-        }
-
-        return layer;
-    }
-
-    /**
-     * Checks a configuration for the boot Layer to ensure that no two modules
-     * have the same package.
-     *
-     * @throws LayerInstantiationException
-     */
-    private static void checkBootModulesForDuplicatePkgs(Configuration cf) {
-        Map<String, String> packageToModule = new HashMap<>();
-        for (ModuleDescriptor md : cf.descriptors()) {
-            String name = md.name();
-            for (String p : md.packages()) {
-                String other = packageToModule.putIfAbsent(p, name);
-                if (other != null) {
-                    throw fail("Package " + p + " in both module "
-                               + name + " and module " + other);
-                }
-            }
-        }
-    }
-
-    /**
-     * Checks a configuration and the module-to-loader mapping to ensure that
-     * no two modules mapped to the same class loader have the same package.
-     * It also checks that no two automatic modules have the same package.
-     *
-     * @throws LayerInstantiationException
-     */
-    private static void checkForDuplicatePkgs(Configuration cf,
-                                              ClassLoaderFinder clf)
-    {
-        // HashMap allows null keys
-        Map<ClassLoader, Set<String>> loaderToPackages = new HashMap<>();
-
-        for (ModuleDescriptor descriptor : cf.descriptors()) {
-            ClassLoader loader = clf.loaderForModule(descriptor.name());
-
-            Set<String> loaderPackages
-                = loaderToPackages.computeIfAbsent(loader, k -> new HashSet<>());
-
-            for (String pkg : descriptor.packages()) {
-                boolean added = loaderPackages.add(pkg);
-                if (!added) {
-                    throw fail("More than one module with package %s mapped" +
-                               " to the same class loader", pkg);
-                }
-            }
-        }
-    }
-
-    /**
-     * Creates a LayerInstantiationException with the a message formatted from
-     * the given format string and arguments.
-     */
-    private static LayerInstantiationException fail(String fmt, Object ... args) {
-        return new LayerInstantiationException(fmt, args);
-    }
-
-    /**
-     * Returns the {@code Configuration} used to create this layer unless this
-     * is the {@linkplain #empty empty layer}, which has no configuration.
-     */
-    public Optional<Configuration> configuration() {
-        return Optional.ofNullable(cf);
-    }
-
-    /**
-     * Returns this layer's parent unless this is the {@linkplain #empty empty
-     * layer}, which has no parent.
-     */
-    public Optional<Layer> parent() {
-        if (cf == null) {
-            return Optional.empty();
-        } else {
-            return Optional.of(cf.layer());
-        }
-    }
-
-    /**
-     * Returns a set of the {@code Module}s in this layer.
-     */
-    public Set<Module> modules() {
-        return nameToModule.values().stream().collect(Collectors.toSet());
-    }
-
-    /**
-     * Returns the {@code Module} with the given name in this layer, or if not
-     * in this layer, the {@linkplain #parent parent} layer.
-     */
-    public Optional<Module> findModule(String name) {
-        Module m = nameToModule.get(Objects.requireNonNull(name));
-        if (m != null)
-            return Optional.of(m);
-        return parent().flatMap(l -> l.findModule(name));
-    }
-
-    /**
-     * Returns the {@code ModuleReference} that was used to define the module
-     * with the given name.  If a module of the given name is not in this layer
-     * then the {@linkplain #parent parent} layer is checked.
-     */
-    Optional<ModuleReference> findReference(String name) {
-        if (cf == null)
-            return Optional.empty();
-        Optional<ModuleReference> omref = cf.findModule(name);
-        if (omref.isPresent())
-            return omref;
-        return parent().flatMap(l -> l.findReference(name));
-    }
-
-    /**
-     * Returns the {@code ClassLoader} for the {@code Module} with the given
-     * name. If a module of the given name is not in this layer then the {@link
-     * #parent} layer is checked.
-     *
-     * <p> If there is a security manager then its {@code checkPermission}
-     * method is called with a {@code RuntimePermission("getClassLoader")}
-     * permission to check that the caller is allowed to get access to the
-     * class loader. </p>
-     *
-     * @apiNote This method does not return an {@code Optional<ClassLoader>}
-     * because `null` must be used to represent the bootstrap class loader.
-     *
-     * @throws IllegalArgumentException if a module of the given name is not
-     * defined in this layer or any parent of this layer
-     *
-     * @throws SecurityException if denied by the security manager
-     */
-    public ClassLoader findLoader(String name) {
-        Module m = nameToModule.get(name);
-        if (m != null)
-            return m.getClassLoader();
-        Optional<Layer> ol = parent();
-        if (ol.isPresent())
-            return ol.get().findLoader(name);
-        throw new IllegalArgumentException("Module " + name
-                                           + " not known to this layer");
-    }
-
-    /**
-     * Returns the set of module descriptors in this layer and all
-     * parent layers.
-     */
-    Set<ModuleDescriptor> allModuleDescriptors() {
-        Set<ModuleDescriptor> result = new HashSet<>();
-        Optional<Layer> ol = parent();
-        if (ol.isPresent())
-            result.addAll(ol.get().allModuleDescriptors());
-        if (cf != null)
-            result.addAll(cf.descriptors());
-        return result;
-    }
-
-    /**
-     * Returns the <em>empty</em> layer.
-     */
-    public static Layer empty() {
-        return EMPTY_LAYER;
-    }
-
-    /**
-     * Returns the boot layer. Returns {@code null} if the boot layer has not
-     * been set.
-     *
-     * <p> If there is a security manager then its {@code checkPermission}
-     * method if first called with a {@code RuntimePermission("getBootLayer")}
-     * permission to check that the caller is allowed access to the boot
-     * {@code Layer}. </p>
-     *
-     * @throws SecurityException if denied by the security manager
-     */
-    public static Layer boot() {
-        SecurityManager sm = System.getSecurityManager();
-        if (sm != null)
-            sm.checkPermission(new RuntimePermission("getBootLayer"));
-        return bootLayer;
-    }
-
-    // the boot Layer
-    private static Layer bootLayer;
-
-    static {
-        SharedSecrets.setJavaLangModuleAccess(new JavaLangModuleAccess() {
-            @Override
-            public void setBootLayer(Layer layer) {
-                bootLayer = layer;
-            }
-            @Override
-            public boolean isAutomatic(ModuleDescriptor descriptor) {
-                return descriptor.isAutomatic();
-            }
-        });
-    }
-
-}
--- a/src/java.base/share/classes/java/lang/module/LayerInstantiationException.java	Sat Aug 01 20:33:01 2015 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,54 +0,0 @@
-/*
- * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.  Oracle designates this
- * particular file as subject to the "Classpath" exception as provided
- * by Oracle in the LICENSE file that accompanied this code.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package java.lang.module;
-
-/**
- * Thrown when creating a Layer fails.
- *
- * @see Layer#create
- *
- * @since 1.9
- */
-public class LayerInstantiationException extends RuntimeException {
-
-    private static final long serialVersionUID = 0L;
-
-    /**
-     * Constructs an instance of this exception with the given cause.
-     */
-    public LayerInstantiationException(Throwable cause) {
-        super(cause);
-    }
-
-    /**
-     * Constructs an instance of this exception.
-     */
-    public LayerInstantiationException(String fmt, Object... args) {
-        super(String.format(fmt, args));
-    }
-
-}
-
--- a/src/java.base/share/classes/java/lang/module/ModuleDescriptor.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/java.base/share/classes/java/lang/module/ModuleDescriptor.java	Sat Aug 01 21:57:25 2015 +0100
@@ -1103,4 +1103,20 @@
         return ModuleInfo.read(bb, null);
     }
 
+
+    static {
+        /**
+         * Setup the shared secret to allow code in other packages know if a
+         * module is an automatic module. If isAutomatic becomes part of the
+         * API then this setup can go away.
+         */
+        sun.misc.SharedSecrets
+            .setJavaLangModuleAccess(new sun.misc.JavaLangModuleAccess() {
+                @Override
+                public boolean isAutomatic(ModuleDescriptor descriptor) {
+                    return descriptor.isAutomatic();
+                }
+            });
+    }
+
 }
--- a/src/java.base/share/classes/java/lang/module/ModuleReference.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/java.base/share/classes/java/lang/module/ModuleReference.java	Sat Aug 01 21:57:25 2015 +0100
@@ -81,7 +81,7 @@
     /**
      * Returns the module descriptor.
      */
-    public ModuleDescriptor descriptor() {
+    public final ModuleDescriptor descriptor() {
         return descriptor;
     }
 
@@ -94,7 +94,7 @@
      * granted specific permissions when loaded by a {@link
      * java.security.SecureClassLoader SecureClassLoader}.
      */
-    public Optional<URI> location() {
+    public final Optional<URI> location() {
         return location;
     }
 
--- a/src/java.base/share/classes/java/lang/module/ResolutionException.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/java.base/share/classes/java/lang/module/ResolutionException.java	Sat Aug 01 21:57:25 2015 +0100
@@ -42,6 +42,14 @@
     public ResolutionException() { }
 
     /**
+     * Constructs a {@code ResolutionException} with the given detail
+     * message.
+     */
+    public ResolutionException(String msg) {
+        super(msg);
+    }
+
+    /**
      * Constructs an instance of this exception with the given cause.
      */
     public ResolutionException(Throwable cause) {
@@ -56,11 +64,4 @@
         super(msg, cause);
     }
 
-    /**
-     * Constructs an instance of this exception.
-     */
-    public ResolutionException(String fmt, Object... args) {
-        super(String.format(fmt, args));
-    }
-
 }
--- a/src/java.base/share/classes/java/lang/module/Resolver.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/java.base/share/classes/java/lang/module/Resolver.java	Sat Aug 01 21:57:25 2015 +0100
@@ -27,6 +27,8 @@
 
 import java.lang.module.ModuleDescriptor.Provides;
 import java.lang.module.ModuleDescriptor.Requires;
+import java.lang.reflect.Layer;
+import java.lang.reflect.Module;
 import java.util.ArrayDeque;
 import java.util.ArrayList;
 import java.util.Collection;
@@ -338,8 +340,7 @@
         if (layer == null) {
             candidateConsumers = selected;
         } else {
-            candidateConsumers = new HashSet<>();
-            candidateConsumers.addAll(layer.allModuleDescriptors());
+            candidateConsumers = allModuleDescriptorsInLayer(layer);
             candidateConsumers.addAll(selected);
         }
 
@@ -382,7 +383,7 @@
         // For debugging purposes, print out the service consumers in the
         // selected set that use providers in a parent layer
         if (TRACE) {
-            Set<ModuleDescriptor> allModules = layer.allModuleDescriptors();
+            Set<ModuleDescriptor> allModules = allModuleDescriptorsInLayer(layer);
             for (ModuleDescriptor descriptor : selected) {
                 if (!descriptor.uses().isEmpty()) {
                     for (String service : descriptor.uses()) {
@@ -452,6 +453,23 @@
         return r;
     }
 
+    /**
+     * Returns the set of module descriptors in this layer and all parent
+     * layers. There may be several modules with the same name in the returned
+     * set.
+     */
+    private static Set<ModuleDescriptor> allModuleDescriptorsInLayer(Layer l) {
+        Set<ModuleDescriptor> result = new HashSet<>();
+        Optional<Layer> ol = l.parent();
+        if (ol.isPresent())
+            result.addAll( allModuleDescriptorsInLayer(ol.get()) );
+        Optional<Configuration> ocf = l.configuration();
+        if (ocf.isPresent())
+            result.addAll(ocf.get().descriptors());
+        return result;
+    }
+
+
 
     /**
      * Computes and sets the readability graph for the modules in the given
@@ -493,9 +511,9 @@
                         if (nameToDescriptor.get(dn) == null
                             && d.modifiers().contains(Requires.Modifier.PUBLIC))
                         {
-                            ModuleReference mref = l.findReference(dn).orElse(null);
+                            ModuleReference mref = findInLayer(l, dn);
                             if (mref == null)
-                                throw new InternalError();
+                                throw new InternalError(dn + " not found");
                             requiresPublic.add(mref.descriptor());
                         }
                     }
@@ -516,10 +534,12 @@
             for (Requires d: m.requires()) {
                 String dn = d.name();
                 ModuleDescriptor other = nameToDescriptor.get(dn);
-                if (other == null && layer != null)
-                    other = layer.findReference(dn)
-                                 .map(ModuleReference::descriptor)
-                                 .orElse(null);
+                if (other == null && layer != null) {
+                    ModuleReference mref = findInLayer(layer, dn);
+                    if (mref != null)
+                        other = mref.descriptor();
+                }
+
                 if (other == null)
                     throw new InternalError(dn + " not found??");
 
@@ -624,7 +644,8 @@
                 if (recordedHash != null) {
                     ModuleReference mref = nameToReference.get(dn);
                     if (mref == null)
-                        mref = layer.findReference(dn).orElse(null);
+                        mref = findInLayer(layer, dn);
+
                     if (mref == null)
                         throw new InternalError(dn + " not found");
 
@@ -700,6 +721,7 @@
     }
 
 
+
     /**
      * Returns true if a module of the given module's name is in a parent Layer
      */
@@ -746,6 +768,25 @@
         }
     }
 
+    /**
+     * Returns the {@code ModuleReference} that was used to define the module
+     * with the given name.  If a module of the given name is not in the layer
+     * then the parent layer is searched.
+     */
+    private static ModuleReference findInLayer(Layer layer, String name) {
+        Optional<Configuration> ocf = layer.configuration();
+        if (!ocf.isPresent())
+            return null;
+
+        Optional<ModuleReference> omref = ocf.get().findModule(name);
+        if (omref.isPresent()) {
+            return omref.get();
+        } else {
+            return findInLayer(layer.parent().get(), name);
+        }
+    }
+
+
 
     /**
      * Checks the readability graph to ensure that no two modules export the
@@ -823,7 +864,8 @@
 
 
     private static void fail(String fmt, Object ... args) {
-        throw new ResolutionException(fmt, args);
+        String msg = String.format(fmt, args);
+        throw new ResolutionException(msg);
     }
 
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/java.base/share/classes/java/lang/reflect/Layer.java	Sat Aug 01 21:57:25 2015 +0100
@@ -0,0 +1,351 @@
+/*
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package java.lang.reflect;
+
+import java.lang.module.Configuration;
+import java.lang.module.ModuleDescriptor;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Map;
+import java.util.Objects;
+import java.util.Optional;
+import java.util.Set;
+import java.util.stream.Collectors;
+
+import sun.misc.SharedSecrets;
+
+
+/**
+ * Represents a layer of modules in the Java virtual machine.
+ *
+ * <p> The following example resolves a module named <em>myapp</em> and creates
+ * a {@code Layer} with the resulting {@link Configuration}. In the example
+ * then all modules are associated with the same class loader. </p>
+ *
+ * <pre>{@code
+ *     ModuleFinder finder = ModuleFinder.of(dir1, dir2, dir3);
+ *
+ *     Configuration cf
+ *         = Configuration.resolve(ModuleFinder.empty(),
+ *                                 Layer.boot(),
+ *                                 finder,
+ *                                 "myapp");
+ *
+ *     ClassLoader loader = new ModuleClassLoader(cf);
+ *
+ *     Layer layer = Layer.create(cf, mn -> loader);
+ *
+ *     Class<?> c = layer.findLoader("myapp").loadClass("app.Main");
+ * }</pre>
+ *
+ * @apiNote As Layer is in java.lang.reflect then its method names may
+ * need to follow the convention in this package.
+ *
+ * @since 1.9
+ */
+
+public final class Layer {
+
+
+    /**
+     * Finds the class loader for a module.
+     *
+     * @see Layer#create
+     * @since 1.9
+     */
+    @FunctionalInterface
+    public static interface ClassLoaderFinder {
+        /**
+         * Returns the class loader for the given module.
+         *
+         * <p> If this method is invoked several times to locate the same
+         * module (by name) then it will return the same result each time.
+         * Failure to do so will lead to unspecified behavior when creating
+         * a Layer. </p>
+         */
+        ClassLoader loaderForModule(String moduleName);
+    }
+
+
+    // the empty Layer
+    private static final Layer EMPTY_LAYER = new Layer(null, null);
+
+    // the configuration from which this Layer was created
+    private final Configuration cf;
+
+    // maps module name to jlr.Module
+    private final Map<String, Module> nameToModule;
+
+
+    /**
+     * Creates a new Layer from the modules in the given configuration.
+     */
+    private Layer(Configuration cf, ClassLoaderFinder clf) {
+
+        Map<String, Module> map;
+        if (cf == null) {
+            map = Collections.emptyMap();
+        } else {
+            map = Module.defineModules(cf, clf, this);
+        }
+
+        this.cf = cf;
+        this.nameToModule = map; // no need to do defensive copy
+    }
+
+
+    /**
+     * Creates a {@code Layer} by defining the modules, as described in the
+     * given {@code Configuration}, to the Java virtual machine.
+     *
+     * <p> Modules are mapped to module-capable class loaders by means of the
+     * given {@code ClassLoaderFinder} and defined to the Java virtual machine.
+     * The caller of this method must arrange for the class loaders to be
+     * ready to load from these modules before attempting to load classes or
+     * resources. This can be before or after the {@code Layer} is created. </p>
+     *
+     * <p> Creating a {@code Layer} may fail for several reasons: </p>
+     *
+     * <ul>
+     *
+     *     <li> Two or more modules with the same package (exported or
+     *          concealed) are mapped to the same class loader. </li>
+     *
+     *     <li> A module is mapped to a class loader that already has a module
+     *          of the same name defined to it. </li>
+     *
+     *     <li> A module is mapped to a class loader that has already defined
+     *          types in any of the packages in the module. </li>
+     *
+     * </ul>
+     *
+     * @apiNote Need to decide if there is a permission check needed here. We
+     * can't have an untrusted ClassLoaderFinder returning null and have this
+     * method define modules to the boot loader. For now, the built-in class
+     * loaders do a permission check to defend against this.
+     *
+     * @implNote Some of the failure reasons listed cannot be detected in
+     * advance, hence it is possible for Layer.create to fail with some of the
+     * modules in the configuration defined to the run-time.
+     *
+     * @throws LayerInstantiationException
+     *         If creating the {@code Layer} fails for any of the reasons
+     *         listed above
+     */
+    public static Layer create(Configuration cf, ClassLoaderFinder clf) {
+        Objects.requireNonNull(cf);
+        Objects.requireNonNull(clf);
+
+        // For now, no two modules in the boot Layer may contain the same
+        // package so we use a simple check for the boot Layer to keep
+        // the overhead at startup to a minimum
+        if (bootLayer() == null) {
+            checkBootModulesForDuplicatePkgs(cf);
+        } else {
+            checkForDuplicatePkgs(cf, clf);
+        }
+
+        Layer layer;
+        try {
+            layer = new Layer(cf, clf);
+        } catch (SecurityException se) {
+            throw se;
+        } catch (Exception | Error e) {
+            // FIXME: Need to reduce the range of exceptions that need
+            // to be caught here
+            throw new LayerInstantiationException(e);
+        }
+
+        return layer;
+    }
+
+    /**
+     * Checks a configuration for the boot Layer to ensure that no two modules
+     * have the same package.
+     *
+     * @throws LayerInstantiationException
+     */
+    private static void checkBootModulesForDuplicatePkgs(Configuration cf) {
+        Map<String, String> packageToModule = new HashMap<>();
+        for (ModuleDescriptor md : cf.descriptors()) {
+            String name = md.name();
+            for (String p : md.packages()) {
+                String other = packageToModule.putIfAbsent(p, name);
+                if (other != null) {
+                    throw fail("Package " + p + " in both module "
+                               + name + " and module " + other);
+                }
+            }
+        }
+    }
+
+    /**
+     * Checks a configuration and the module-to-loader mapping to ensure that
+     * no two modules mapped to the same class loader have the same package.
+     * It also checks that no two automatic modules have the same package.
+     *
+     * @throws LayerInstantiationException
+     */
+    private static void checkForDuplicatePkgs(Configuration cf,
+                                              ClassLoaderFinder clf)
+    {
+        // HashMap allows null keys
+        Map<ClassLoader, Set<String>> loaderToPackages = new HashMap<>();
+
+        for (ModuleDescriptor descriptor : cf.descriptors()) {
+            ClassLoader loader = clf.loaderForModule(descriptor.name());
+
+            Set<String> loaderPackages
+                = loaderToPackages.computeIfAbsent(loader, k -> new HashSet<>());
+
+            for (String pkg : descriptor.packages()) {
+                boolean added = loaderPackages.add(pkg);
+                if (!added) {
+                    throw fail("More than one module with package %s mapped" +
+                               " to the same class loader", pkg);
+                }
+            }
+        }
+    }
+
+    /**
+     * Creates a LayerInstantiationException with the a message formatted from
+     * the given format string and arguments.
+     */
+    private static LayerInstantiationException fail(String fmt, Object ... args) {
+        String msg = String.format(fmt, args);
+        return new LayerInstantiationException(msg);
+    }
+
+
+    /**
+     * Returns the {@code Configuration} used to create this layer unless this
+     * is the {@linkplain #empty empty layer}, which has no configuration.
+     */
+    public Optional<Configuration> configuration() {
+        return Optional.ofNullable(cf);
+    }
+
+
+    /**
+     * Returns this layer's parent unless this is the {@linkplain #empty empty
+     * layer}, which has no parent.
+     */
+    public Optional<Layer> parent() {
+        if (cf == null) {
+            return Optional.empty();
+        } else {
+            return Optional.of(cf.layer());
+        }
+    }
+
+
+    /**
+     * Returns a set of the {@code Module}s in this layer.
+     */
+    public Set<Module> modules() {
+        return nameToModule.values().stream().collect(Collectors.toSet());
+    }
+
+
+    /**
+     * Returns the {@code Module} with the given name in this layer, or if not
+     * in this layer, the {@linkplain #parent parent} layer.
+     */
+    public Optional<Module> findModule(String name) {
+        Module m = nameToModule.get(Objects.requireNonNull(name));
+        if (m != null)
+            return Optional.of(m);
+        return parent().flatMap(l -> l.findModule(name));
+    }
+
+
+    /**
+     * Returns the {@code ClassLoader} for the {@code Module} with the given
+     * name. If a module of the given name is not in this layer then the {@link
+     * #parent} layer is checked.
+     *
+     * <p> If there is a security manager then its {@code checkPermission}
+     * method is called with a {@code RuntimePermission("getClassLoader")}
+     * permission to check that the caller is allowed to get access to the
+     * class loader. </p>
+     *
+     * @apiNote This method does not return an {@code Optional<ClassLoader>}
+     * because `null` must be used to represent the bootstrap class loader.
+     *
+     * @throws IllegalArgumentException if a module of the given name is not
+     * defined in this layer or any parent of this layer
+     *
+     * @throws SecurityException if denied by the security manager
+     */
+    public ClassLoader findLoader(String name) {
+        Module m = nameToModule.get(name);
+        if (m != null)
+            return m.getClassLoader();
+        Optional<Layer> ol = parent();
+        if (ol.isPresent())
+            return ol.get().findLoader(name);
+        throw new IllegalArgumentException("Module " + name
+                                           + " not known to this layer");
+    }
+
+
+    /**
+     * Returns the <em>empty</em> layer.
+     */
+    public static Layer empty() {
+        return EMPTY_LAYER;
+    }
+
+
+    /**
+     * Returns the boot layer. Returns {@code null} if the boot layer has not
+     * been set.
+     *
+     * <p> If there is a security manager then its {@code checkPermission}
+     * method if first called with a {@code RuntimePermission("getBootLayer")}
+     * permission to check that the caller is allowed access to the boot
+     * {@code Layer}. </p>
+     *
+     * @throws SecurityException if denied by the security manager
+     */
+    public static Layer boot() {
+        SecurityManager sm = System.getSecurityManager();
+        if (sm != null)
+            sm.checkPermission(new RuntimePermission("getBootLayer"));
+        return bootLayer();
+    }
+
+    /**
+     * Returns the boot layer. Returns {@code null} if the boot layer has not
+     * been set.
+     */
+    private static Layer bootLayer() {
+        return SharedSecrets.getJavaLangAccess().getBootLayer();
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/java.base/share/classes/java/lang/reflect/LayerInstantiationException.java	Sat Aug 01 21:57:25 2015 +0100
@@ -0,0 +1,68 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package java.lang.reflect;
+
+/**
+ * Thrown when creating a Layer fails.
+ *
+ * @see Layer#create
+ *
+ * @since 1.9
+ */
+public class LayerInstantiationException extends RuntimeException {
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * Constructs a {@code LayerInstantiationException} with no detail message.
+     */
+    public LayerInstantiationException() {
+    }
+
+    /**
+     * Constructs a {@code LayerInstantiationException} with the given detail
+     * message.
+     */
+    public LayerInstantiationException(String msg) {
+        super(msg);
+    }
+
+    /**
+     * Constructs a {@code LayerInstantiationException} with the given cause.
+     */
+    public LayerInstantiationException(Throwable cause) {
+        super(cause);
+    }
+
+    /**
+     * Constructs a {@code FindException} with the given detail message
+     * and cause.
+     */
+    public LayerInstantiationException(String msg, Throwable cause) {
+        super(msg, cause);
+    }
+
+}
+
--- a/src/java.base/share/classes/java/lang/reflect/Module.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/java.base/share/classes/java/lang/reflect/Module.java	Sat Aug 01 21:57:25 2015 +0100
@@ -28,8 +28,6 @@
 import java.io.IOException;
 import java.io.InputStream;
 import java.lang.module.Configuration;
-import java.lang.module.Layer;
-import java.lang.module.Layer.ClassLoaderFinder;
 import java.lang.module.ModuleReference;
 import java.lang.module.ModuleDescriptor;
 import java.lang.module.ModuleDescriptor.Exports;
@@ -51,7 +49,7 @@
 
 import jdk.internal.module.ServicesCatalog;
 import jdk.internal.misc.BootLoader;
-import sun.misc.JavaLangReflectAccess;
+import sun.misc.JavaLangReflectModuleAccess;
 import sun.misc.SharedSecrets;
 import sun.misc.Unsafe;
 import sun.reflect.CallerSensitive;
@@ -63,8 +61,7 @@
  *
  * <p> Named modules have a {@link #getName() name} and are constructed by the
  * Java Virtual Machine when a {@link java.lang.module.Configuration
- * Configuration} is reified by creating a module {@link java.lang.module.Layer
- * Layer}. </p>
+ * Configuration} is reified by creating a module {@link Layer Layer}. </p>
  *
  * <p> An unnamed module does not have a name. There is an unnamed module
  * per {@link ClassLoader ClassLoader} that is obtained by invoking the class
@@ -84,6 +81,9 @@
 
 public final class Module {
 
+    private static final String JAVA_BASE = "java.base";
+
+
     // module name and loader, these fields are read by VM
     private final String name;
     private final ClassLoader loader;
@@ -91,13 +91,13 @@
     // the module descriptor
     private final ModuleDescriptor descriptor;
 
+
     /**
      * Invoked by the VM to create java.base early in the startup.
      */
     private Module(ClassLoader loader, String name) {
-        if (name == null)
-            throw new Error();
-
+        if (!name.equals(JAVA_BASE))
+            throw new InternalError();
         this.name = name;
         this.loader = loader;
         this.descriptor = null;
@@ -128,6 +128,7 @@
         this.loose = true;
     }
 
+
     /**
      * Returns {@code true} if this module is a named module.
      *
@@ -722,15 +723,17 @@
      * exports. This method does not register the module with its class
      * loader or register the module in the service catalog.
      */
-    static Module defineModule(ClassLoader loader, ModuleReference mref) {
+    static Module defineModule(ClassLoader loader,
+                               ModuleDescriptor descriptor,
+                               URI uri)
+    {
         Module m;
 
-        ModuleDescriptor descriptor = mref.descriptor();
         Set<String> packages = descriptor.packages();
 
         // define module to VM, except java.base as it is defined by VM
         String name = descriptor.name();
-        if (loader == null && name.equals("java.base")) {
+        if (loader == null && name.equals(JAVA_BASE)) {
             m = Object.class.getModule();
 
             // set descriptor and packages fields
@@ -759,7 +762,6 @@
             Version version = descriptor.version().orElse(null);
             String vs = Objects.toString(version, "");
 
-            URI uri = mref.location().orElse(null);
             String loc = Objects.toString(uri, null);
 
             defineModule0(m, vs, loc, array);
@@ -774,17 +776,20 @@
      * @return a map of module name to runtime {@code Module}
      */
     static Map<String, Module> defineModules(Configuration cf,
-                                             Layer.ClassLoaderFinder clf)
+                                             Layer.ClassLoaderFinder clf,
+                                             Layer layer)
     {
+
         Map<String, Module> modules = new HashMap<>();
         Map<String, ClassLoader> loaders = new HashMap<>();
 
-        // define each module in the configuration to the VM and register
-        // with each class loader.
+        // define each module in the configuration to the VM
         for (ModuleReference mref : cf.modules()) {
-            String name = mref.descriptor().name();
+            ModuleDescriptor descriptor = mref.descriptor();
+            String name = descriptor.name();
             ClassLoader loader = clf.loaderForModule(name);
-            Module m = defineModule(loader, mref);
+            URI uri = mref.location().orElse(null);
+            Module m = defineModule(loader, descriptor, uri);
             modules.put(name, m);
             loaders.put(name, loader);
         }
@@ -962,19 +967,17 @@
      * Register shared secret to provide access to package-private methods
      */
     static {
-        SharedSecrets.setJavaLangReflectAccess(
-            new JavaLangReflectAccess() {
+        SharedSecrets.setJavaLangReflectModuleAccess(
+            new JavaLangReflectModuleAccess() {
                 @Override
                 public Module defineUnnamedModule(ClassLoader loader) {
                     return new Module(loader);
                 }
                 @Override
-                public Module defineModule(ClassLoader loader, ModuleReference mref) {
-                   return Module.defineModule(loader, mref);
-                }
-                @Override
-                public Map<String, Module> defineModules(Configuration cf, ClassLoaderFinder clf) {
-                    return Module.defineModules(cf, clf);
+                public Module defineModule(ClassLoader loader,
+                                           ModuleDescriptor descriptor,
+                                           URI uri) {
+                   return Module.defineModule(loader, descriptor, uri);
                 }
                 @Override
                 public void addReads(Module m1, Module m2) {
--- a/src/java.base/share/classes/java/util/ServiceLoader.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/java.base/share/classes/java/util/ServiceLoader.java	Sat Aug 01 21:57:25 2015 +0100
@@ -30,11 +30,11 @@
 import java.io.InputStream;
 import java.io.InputStreamReader;
 import java.lang.module.Configuration;
-import java.lang.module.Layer;
 import java.lang.module.ModuleDescriptor;
 import java.lang.module.ModuleDescriptor.Provides;
 import java.lang.reflect.Constructor;
 import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Layer;
 import java.lang.reflect.Modifier;
 import java.lang.reflect.Module;
 import java.net.URL;
--- a/src/java.base/share/classes/jdk/internal/misc/BootLoader.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/java.base/share/classes/jdk/internal/misc/BootLoader.java	Sat Aug 01 21:57:25 2015 +0100
@@ -47,7 +47,7 @@
 
     // The unnamed module for the boot loader
     private static final Module UNNAMED_MODULE
-        = SharedSecrets.getJavaLangReflectAccess().defineUnnamedModule(null);
+        = SharedSecrets.getJavaLangReflectModuleAccess().defineUnnamedModule(null);
 
     // ServiceCatalog for the boot class loader
     private static final ServicesCatalog SERVICES_CATALOG = new ServicesCatalog();
--- a/src/java.base/share/classes/jdk/internal/misc/Modules.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/java.base/share/classes/jdk/internal/misc/Modules.java	Sat Aug 01 21:57:25 2015 +0100
@@ -25,13 +25,11 @@
 
 package jdk.internal.misc;
 
-import java.io.IOException;
-import java.lang.module.ModuleReference;
 import java.lang.module.ModuleDescriptor;
-import java.lang.module.ModuleReader;
 import java.lang.reflect.Module;
 import java.util.Set;
 
+import sun.misc.JavaLangReflectModuleAccess;
 import sun.misc.SharedSecrets;
 
 
@@ -47,23 +45,21 @@
 public class Modules {
     private Modules() { }
 
+    private static final JavaLangReflectModuleAccess JLRMA
+        = SharedSecrets.getJavaLangReflectModuleAccess();
+
     /**
-     * Define a new module of the given name to be associated with the
-     * given class loader.
+     * Define a new module to the VM. The module has the given set of
+     * concealed packages and is defined to the given class loader.
      */
-    public static Module defineModule(ClassLoader loader, String name,
+    public static Module defineModule(ClassLoader loader,
+                                      String name,
                                       Set<String> packages)
     {
         ModuleDescriptor descriptor
             = new ModuleDescriptor.Builder(name).conceals(packages).build();
-        ModuleReference mref = new ModuleReference(descriptor, null) {
-            @Override
-            public ModuleReader open() throws IOException {
-                throw new IOException("No reader for module " +
-                                      descriptor().toNameAndVersion());
-            }
-        };
-        return SharedSecrets.getJavaLangReflectAccess().defineModule(loader, mref);
+
+        return JLRMA.defineModule(loader, descriptor, null);
     }
 
     /**
@@ -71,7 +67,7 @@
      * Same as m1.addReads(m2) but without a permission check.
      */
     public static void addReads(Module m1, Module m2) {
-        SharedSecrets.getJavaLangReflectAccess().addReads(m1, m2);
+        JLRMA.addReads(m1, m2);
     }
 
     /**
@@ -79,21 +75,21 @@
      * Same as m1.addExports(pkg, m2) but without a permission check.
      */
     public static void addExports(Module m1, String pn, Module m2) {
-        SharedSecrets.getJavaLangReflectAccess().addExports(m1, pn, m2);
+        JLRMA.addExports(m1, pn, m2);
     }
 
     /**
      * Updates a module m to export a package to all modules.
      */
     public static void addExportsToAll(Module m, String pn) {
-        SharedSecrets.getJavaLangReflectAccess().addExportsToAll(m, pn);
+        JLRMA.addExportsToAll(m, pn);
     }
 
     /**
      * Updates module m to export a package to all unnamed modules.
      */
     public static void addExportsToAllUnnamed(Module m, String pn) {
-        SharedSecrets.getJavaLangReflectAccess().addExportsToAllUnnamed(m, pn);
+        JLRMA.addExportsToAllUnnamed(m, pn);
     }
 
     /**
@@ -102,7 +98,7 @@
      * This method is a no-op if the module already contains the package.
      */
     public static void addPackage(Module m, String pn) {
-        SharedSecrets.getJavaLangReflectAccess().addPackage(m, pn);
+        JLRMA.addPackage(m, pn);
     }
 
     /**
--- a/src/java.base/share/classes/jdk/internal/module/ModuleBootstrap.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/java.base/share/classes/jdk/internal/module/ModuleBootstrap.java	Sat Aug 01 21:57:25 2015 +0100
@@ -27,10 +27,10 @@
 
 import java.io.File;
 import java.lang.module.Configuration;
-import java.lang.module.Layer;
-import java.lang.module.Layer.ClassLoaderFinder;
 import java.lang.module.ModuleReference;
 import java.lang.module.ModuleFinder;
+import java.lang.reflect.Layer;
+import java.lang.reflect.Layer.ClassLoaderFinder;
 import java.lang.reflect.Module;
 import java.nio.file.Path;
 import java.nio.file.Paths;
@@ -45,7 +45,6 @@
 import jdk.internal.misc.BuiltinClassLoader;
 import jdk.internal.misc.Modules;
 import sun.misc.PerfCounter;
-import sun.misc.SharedSecrets;
 
 /**
  * Initializes/boots the module system.
@@ -66,11 +65,12 @@
     private static final String JAVA_BASE = "java.base";
 
     /**
-     * Initialize the module system.
+     * Initialize the module system, returning the boot Layer.
      *
-     * @see java.lang.System#initPhase2
+     * @see java.lang.System#initPhase2()
      */
-    public static void boot() {
+    public static Layer boot() {
+
         long t0 = System.nanoTime();
 
         // system module path, aka the installed modules
@@ -224,11 +224,10 @@
         // time to reify modules
         PerfCounters.bootLayerTime.addElapsedTimeFrom(t2);
 
-        // set the boot Layer
-        SharedSecrets.getJavaLangModuleAccess().setBootLayer(bootLayer);
-
         // total time to initialize
         PerfCounters.bootstrapTime.addElapsedTimeFrom(t0);
+
+        return bootLayer;
     }
 
     /**
--- a/src/java.base/share/classes/jdk/internal/module/ModuleLoaderMap.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/java.base/share/classes/jdk/internal/module/ModuleLoaderMap.java	Sat Aug 01 21:57:25 2015 +0100
@@ -25,8 +25,8 @@
 
 package jdk.internal.module;
 
+import java.lang.reflect.Layer;
 import java.lang.module.Configuration;
-import java.lang.module.Layer;
 import java.lang.module.ModuleDescriptor;
 import java.util.HashMap;
 import java.util.HashSet;
--- a/src/java.base/share/classes/sun/launcher/LauncherHelper.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/java.base/share/classes/sun/launcher/LauncherHelper.java	Sat Aug 01 21:57:25 2015 +0100
@@ -43,6 +43,13 @@
 import java.io.IOException;
 import java.io.PrintStream;
 import java.io.UnsupportedEncodingException;
+import java.lang.module.Configuration;
+import java.lang.module.ModuleReference;
+import java.lang.module.ModuleDescriptor;
+import java.lang.module.ModuleDescriptor.Requires;
+import java.lang.module.ModuleDescriptor.Exports;
+import java.lang.module.ModuleDescriptor.Provides;
+import java.lang.reflect.Layer;
 import java.lang.reflect.Method;
 import java.lang.reflect.Modifier;
 import java.math.BigDecimal;
@@ -76,13 +83,6 @@
 import java.util.jar.JarFile;
 import java.util.jar.Manifest;
 
-import java.lang.module.Configuration;
-import java.lang.module.Layer;
-import java.lang.module.ModuleReference;
-import java.lang.module.ModuleDescriptor;
-import java.lang.module.ModuleDescriptor.Requires;
-import java.lang.module.ModuleDescriptor.Exports;
-import java.lang.module.ModuleDescriptor.Provides;
 
 public enum LauncherHelper {
     INSTANCE;
--- a/src/java.base/share/classes/sun/misc/JavaLangAccess.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/java.base/share/classes/sun/misc/JavaLangAccess.java	Sat Aug 01 21:57:25 2015 +0100
@@ -29,6 +29,7 @@
 import java.io.InputStream;
 import java.lang.annotation.Annotation;
 import java.lang.reflect.Executable;
+import java.lang.reflect.Layer;
 import java.security.AccessControlContext;
 import java.util.Map;
 import java.util.stream.Stream;
@@ -138,6 +139,11 @@
     void invokeFinalize(Object o) throws Throwable;
 
     /**
+     * Returns the boot Layer
+     */
+    Layer getBootLayer();
+
+    /**
      * Returns the ServicesCatalog for the given class loader.
      */
     ServicesCatalog getServicesCatalog(ClassLoader cl);
--- a/src/java.base/share/classes/sun/misc/JavaLangModuleAccess.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/java.base/share/classes/sun/misc/JavaLangModuleAccess.java	Sat Aug 01 21:57:25 2015 +0100
@@ -25,7 +25,6 @@
 
 package sun.misc;
 
-import java.lang.module.Layer;
 import java.lang.module.ModuleDescriptor;
 
 
@@ -36,12 +35,6 @@
 public interface JavaLangModuleAccess {
 
     /**
-     * Sets the boot Layer.
-     * @see Layer#boot()
-     */
-    void setBootLayer(Layer layer);
-
-    /**
      * Returns {@code true} if the module descriptor is for an
      * automatic module.
      */
--- a/src/java.base/share/classes/sun/misc/JavaLangReflectAccess.java	Sat Aug 01 20:33:01 2015 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,87 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.  Oracle designates this
- * particular file as subject to the "Classpath" exception as provided
- * by Oracle in the LICENSE file that accompanied this code.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package sun.misc;
-
-import java.lang.reflect.Module;
-import java.util.Map;
-
-import java.lang.module.Configuration;
-import java.lang.module.Layer.ClassLoaderFinder;
-import java.lang.module.ModuleReference;
-
-/**
- * Provides access to package-private methods in java.lang.reflect.
- */
-
-public interface JavaLangReflectAccess {
-
-    /**
-     * Defines the unnamed module for the given class loader.
-     */
-    Module defineUnnamedModule(ClassLoader loader);
-
-    /**
-     * Defines a new module to the Java virtual machine. The module
-     * is defined to the given class loader.
-     */
-    Module defineModule(ClassLoader loader, ModuleReference mref);
-
-    /**
-     * Defines the modules in the given {@code Configuration} to the Java
-     * virtual machine. The modules are mapped to class loaders using the
-     * given {@code ClassLoaderFinder}.
-     */
-    Map<String, Module> defineModules(Configuration cf, ClassLoaderFinder clf);
-
-    /**
-     * Updates the readability so that module m1 reads m2. The new read edge
-     * does not result in a strong reference to m2 (m2 can be GC'ed).
-     *
-     * This method is the same as m1.addReads(m2) but without a permission check.
-     */
-    void addReads(Module m1, Module m2);
-
-    /**
-     * Updates module m1 to export a package to module m2. The export does
-     * not result in a strong reference to m2 (m2 can be GC'ed).
-     */
-    void addExports(Module m1, String pkg, Module m2);
-
-    /**
-     * Updates a module m to export a package to all modules.
-     */
-    void addExportsToAll(Module m, String pkg);
-
-    /**
-     * Updates a module m to export a package to all unnamed modules.
-     */
-    void addExportsToAllUnnamed(Module m, String pkg);
-
-    /**
-     * Add a package to the given module.
-     */
-    void addPackage(Module m, String pkg);
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/java.base/share/classes/sun/misc/JavaLangReflectModuleAccess.java	Sat Aug 01 21:57:25 2015 +0100
@@ -0,0 +1,79 @@
+/*
+ * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package sun.misc;
+
+import java.lang.module.ModuleDescriptor;
+import java.lang.reflect.Module;
+import java.net.URI;
+
+/**
+ * Provides access to non-public methods in java.lang.reflect.Module
+ */
+
+public interface JavaLangReflectModuleAccess {
+
+    /**
+     * Defines the unnamed module for the given class loader.
+     */
+    Module defineUnnamedModule(ClassLoader loader);
+
+    /**
+     * Defines a new module to the Java virtual machine. The module
+     * is defined to the given class loader.
+     *
+     * The URI is for information purposes only, it can be {@code null}.
+     */
+    Module defineModule(ClassLoader loader, ModuleDescriptor descriptor, URI uri);
+
+    /**
+     * Updates the readability so that module m1 reads m2. The new read edge
+     * does not result in a strong reference to m2 (m2 can be GC'ed).
+     *
+     * This method is the same as m1.addReads(m2) but without a permission check.
+     */
+    void addReads(Module m1, Module m2);
+
+    /**
+     * Updates module m1 to export a package to module m2. The export does
+     * not result in a strong reference to m2 (m2 can be GC'ed).
+     */
+    void addExports(Module m1, String pkg, Module m2);
+
+    /**
+     * Updates a module m to export a package to all modules.
+     */
+    void addExportsToAll(Module m, String pkg);
+
+    /**
+     * Updates a module m to export a package to all unnamed modules.
+     */
+    void addExportsToAllUnnamed(Module m, String pkg);
+
+    /**
+     * Add a package to the given module.
+     */
+    void addPackage(Module m, String pkg);
+}
--- a/src/java.base/share/classes/sun/misc/SharedSecrets.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/java.base/share/classes/sun/misc/SharedSecrets.java	Sat Aug 01 21:57:25 2015 +0100
@@ -46,7 +46,7 @@
     private static JavaUtilJarAccess javaUtilJarAccess;
     private static JavaLangAccess javaLangAccess;
     private static JavaLangModuleAccess javaLangModuleAccess;
-    private static JavaLangReflectAccess javaLangReflectAccess;
+    private static JavaLangReflectModuleAccess javaLangReflectModuleAccess;
     private static JavaLangRefAccess javaLangRefAccess;
     private static JavaIOAccess javaIOAccess;
     private static JavaNetAccess javaNetAccess;
@@ -82,22 +82,22 @@
         return javaLangAccess;
     }
 
-    public static void setJavaLangModuleAccess(JavaLangModuleAccess jlma) {
-        javaLangModuleAccess = jlma;
+    public static void setJavaLangModuleAccess(JavaLangModuleAccess jlrma) {
+        javaLangModuleAccess = jlrma;
     }
 
     public static JavaLangModuleAccess getJavaLangModuleAccess() {
         return javaLangModuleAccess;
     }
 
-    public static void setJavaLangReflectAccess(JavaLangReflectAccess jlfa) {
-        javaLangReflectAccess = jlfa;
+    public static void setJavaLangReflectModuleAccess(JavaLangReflectModuleAccess jlrma) {
+        javaLangReflectModuleAccess = jlrma;
     }
 
-    public static JavaLangReflectAccess getJavaLangReflectAccess() {
-        if (javaLangReflectAccess == null)
+    public static JavaLangReflectModuleAccess getJavaLangReflectModuleAccess() {
+        if (javaLangReflectModuleAccess == null)
             unsafe.ensureClassInitialized(java.lang.reflect.Module.class);
-        return javaLangReflectAccess;
+        return javaLangReflectModuleAccess;
     }
 
     public static void setJavaLangRefAccess(JavaLangRefAccess jlra) {
--- a/src/jdk.jlink/share/classes/jdk/tools/jlink/JlinkTask.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/jdk.jlink/share/classes/jdk/tools/jlink/JlinkTask.java	Sat Aug 01 21:57:25 2015 +0100
@@ -36,11 +36,11 @@
 import java.io.PrintWriter;
 import java.io.Writer;
 import java.lang.module.Configuration;
-import java.lang.module.Layer;
 import java.lang.module.ModuleReference;
 import java.lang.module.ModuleFinder;
 import java.lang.module.ModuleDescriptor;
 import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Layer;
 import java.net.URI;
 import java.nio.file.Files;
 import java.nio.file.Path;
--- a/src/jdk.jlink/share/classes/jdk/tools/jlink/TaskHelper.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/jdk.jlink/share/classes/jdk/tools/jlink/TaskHelper.java	Sat Aug 01 21:57:25 2015 +0100
@@ -32,8 +32,8 @@
 import java.io.IOException;
 import java.io.PrintWriter;
 import java.lang.module.Configuration;
-import java.lang.module.Layer;
 import java.lang.module.ModuleFinder;
+import java.lang.reflect.Layer;
 import java.nio.file.NoSuchFileException;
 import java.nio.file.Path;
 import java.nio.file.Paths;
--- a/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/ImagePluginConfiguration.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/ImagePluginConfiguration.java	Sat Aug 01 21:57:25 2015 +0100
@@ -28,7 +28,7 @@
 import jdk.tools.jlink.plugins.Plugin;
 import java.io.File;
 import java.io.IOException;
-import java.lang.module.Layer;
+import java.lang.reflect.Layer;
 import java.net.MalformedURLException;
 import java.net.URL;
 import java.net.URLClassLoader;
--- a/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/ImagePluginProviderRepository.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/ImagePluginProviderRepository.java	Sat Aug 01 21:57:25 2015 +0100
@@ -27,7 +27,7 @@
 import jdk.tools.jlink.plugins.PluginProvider;
 import jdk.tools.jlink.plugins.Plugin;
 import java.io.IOException;
-import java.lang.module.Layer;
+import java.lang.reflect.Layer;
 import java.nio.file.Path;
 import java.util.ArrayList;
 import java.util.Collections;
--- a/test/java/lang/ModuleClassLoader/Basic.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/test/java/lang/ModuleClassLoader/Basic.java	Sat Aug 01 21:57:25 2015 +0100
@@ -30,8 +30,8 @@
  */
 
 import java.io.FilePermission;
+import java.lang.reflect.Layer;
 import java.lang.module.Configuration;
-import java.lang.module.Layer;
 import java.lang.module.ModuleFinder;
 import java.net.URL;
 import java.security.AccessControlException;
--- a/test/jdk/jigsaw/etc/automaticmodules/AutomaticModulesTest.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/test/jdk/jigsaw/etc/automaticmodules/AutomaticModulesTest.java	Sat Aug 01 21:57:25 2015 +0100
@@ -33,11 +33,11 @@
 import java.io.IOException;
 import java.io.OutputStream;
 import java.lang.module.Configuration;
-import java.lang.module.Layer;
 import java.lang.module.ModuleDescriptor;
 import java.lang.module.ModuleDescriptor.Exports;
 import java.lang.module.ModuleFinder;
 import java.lang.module.ModuleReference;
+import java.lang.reflect.Layer;
 import java.lang.reflect.Module;
 import java.nio.file.Files;
 import java.nio.file.Path;
@@ -50,7 +50,7 @@
 import java.util.jar.Manifest;
 import java.util.stream.Collectors;
 
-import static java.lang.module.Layer.boot;
+import static java.lang.reflect.Layer.boot;
 import static java.lang.module.ModuleFinder.empty;
 
 import org.testng.annotations.DataProvider;
--- a/test/jdk/jigsaw/etc/automaticmodules/src/basictest/test/Main.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/test/jdk/jigsaw/etc/automaticmodules/src/basictest/test/Main.java	Sat Aug 01 21:57:25 2015 +0100
@@ -23,7 +23,8 @@
 
 package test;
 
-import java.lang.module.*;
+import java.lang.module.ModuleDescriptor;
+import java.lang.reflect.Layer;
 import java.lang.reflect.Module;
 
 import http.HttpServer;
--- a/test/jdk/jigsaw/etc/automaticmodules/src/sptest/test/Main.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/test/jdk/jigsaw/etc/automaticmodules/src/sptest/test/Main.java	Sat Aug 01 21:57:25 2015 +0100
@@ -23,10 +23,10 @@
 
 package test;
 
-import java.lang.module.Layer;
 import java.lang.module.ModuleDescriptor;
 import java.lang.module.ModuleDescriptor.Requires;
 import java.lang.module.ModuleDescriptor.Provides;
+import java.lang.reflect.Layer;
 import java.lang.reflect.Module;
 import java.util.Map;
 import java.util.Optional;
--- a/test/jdk/jigsaw/functional/container/src/container/container/Main.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/test/jdk/jigsaw/functional/container/src/container/container/Main.java	Sat Aug 01 21:57:25 2015 +0100
@@ -25,9 +25,9 @@
 
 import java.io.File;
 import java.lang.module.Configuration;
-import java.lang.module.Layer;
 import java.lang.module.ModuleFinder;
 import java.lang.module.ModuleDescriptor;
+import java.lang.reflect.Layer;
 import java.lang.reflect.Method;
 import java.nio.file.Path;
 import java.nio.file.Paths;
--- a/test/jdk/jigsaw/launcher/upgrademodulepath/src/test/jdk/test/Main.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/test/jdk/jigsaw/launcher/upgrademodulepath/src/test/jdk/test/Main.java	Sat Aug 01 21:57:25 2015 +0100
@@ -23,13 +23,12 @@
 
 package jdk.test;
 
+import java.lang.reflect.Layer;
 import java.lang.reflect.Module;
+import java.lang.module.Configuration;
 import javax.annotation.Resource;
 import javax.annotation.more.BigResource;
 
-import java.lang.module.Configuration;
-import java.lang.module.Layer;
-
 public class Main {
     public static void main(String[] args) {
         Module m1 = Resource.class.getModule();
--- a/test/jdk/jigsaw/module/ConfigurationTest.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/test/jdk/jigsaw/module/ConfigurationTest.java	Sat Aug 01 21:57:25 2015 +0100
@@ -30,16 +30,16 @@
  */
 
 import java.lang.module.Configuration;
-import java.lang.module.Layer;
 import java.lang.module.ModuleDescriptor;
 import java.lang.module.ModuleDescriptor.Requires.Modifier;
 import java.lang.module.ModuleFinder;
 import java.lang.module.ModuleReference;
 import java.lang.module.ResolutionException;
+import java.lang.reflect.Layer;
 import java.util.stream.Collectors;
 
-import static java.lang.module.Layer.*;
 import static java.lang.module.ModuleFinder.empty;
+import static java.lang.reflect.Layer.*;
 
 import org.testng.annotations.Test;
 import static org.testng.Assert.*;
--- a/test/jdk/jigsaw/module/LayerTest.java	Sat Aug 01 20:33:01 2015 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,361 +0,0 @@
-/*
- * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-/**
- * @test
- * @library ../lib
- * @build LayerTest ModuleUtils
- * @run testng LayerTest
- * @summary Basic tests for java.lang.module.Layer
- */
-
-import java.lang.module.Configuration;
-import java.lang.module.Layer;
-import java.lang.module.LayerInstantiationException;
-import java.lang.module.ModuleDescriptor;
-import java.lang.module.ModuleFinder;
-import java.lang.reflect.Module;
-import java.util.HashMap;
-import java.util.Map;
-import java.util.Set;
-import java.util.stream.Collectors;
-
-import org.testng.annotations.Test;
-import static org.testng.Assert.*;
-
-@Test
-public class LayerTest {
-
-    /**
-     * Exercise Layer.boot()
-     */
-    public void testBoot() {
-        Layer bootLayer = Layer.boot();
-
-        // configuration
-        Configuration cf = bootLayer.configuration().get();
-        assertTrue(cf.findDescriptor("java.base").get().exports()
-                   .stream().anyMatch(e -> (e.source().equals("java.lang")
-                                            && !e.targets().isPresent())));
-
-        // modules
-        Set<Module> modules = bootLayer.modules();
-        assertTrue(modules.contains(Object.class.getModule()));
-        int count = (int) modules.stream().map(Module::getName).count();
-        assertEquals(count, modules.size()); // module names are unique
-
-        // findModule
-        Module base = Object.class.getModule();
-        assertTrue(bootLayer.findModule("java.base").get() == base);
-
-        // findLoader
-        assertTrue(bootLayer.findLoader("java.base") == null);
-
-        // parent
-        assertTrue(bootLayer.parent().get() == Layer.empty());
-    }
-
-
-    /**
-     * Exercise Layer.empty()
-     */
-    public void testEmpty() {
-        Layer emptyLayer = Layer.empty();
-
-        // configuration
-        assertFalse(emptyLayer.configuration().isPresent());
-
-        // modules
-        assertTrue(emptyLayer.modules().isEmpty());
-
-        // findModule
-        assertFalse(emptyLayer.findModule("java.base").isPresent());
-
-        // findLoader
-        try {
-            ClassLoader loader = emptyLayer.findLoader("java.base");
-            assertTrue(false);
-        } catch (IllegalArgumentException ignore) { }
-
-        // parent
-        assertTrue(!emptyLayer.parent().isPresent());
-    }
-
-
-    /**
-     * Exercise Layer.create, created on an empty layer
-     */
-    public void testLayerOnEmpty() {
-        ModuleDescriptor descriptor1
-            = new ModuleDescriptor.Builder("m1")
-                .requires("m2")
-                .exports("p1")
-                .build();
-
-        ModuleDescriptor descriptor2
-            = new ModuleDescriptor.Builder("m2")
-                .requires("m3")
-                .build();
-
-        ModuleDescriptor descriptor3
-            = new ModuleDescriptor.Builder("m3")
-                .build();
-
-        ModuleFinder finder
-            = ModuleUtils.finderOf(descriptor1, descriptor2, descriptor3);
-
-        Configuration cf = Configuration.resolve(finder,
-                                                 Layer.empty(),
-                                                 ModuleFinder.empty(),
-                                                 "m1");
-
-        // map each module to its own class loader for this test
-        ClassLoader loader1 = new ModuleClassLoader(cf, "m1");
-        ClassLoader loader2 = new ModuleClassLoader(cf, "m2");
-        ClassLoader loader3 = new ModuleClassLoader(cf, "m3");
-        Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", loader1);
-        map.put("m2", loader2);
-        map.put("m3", loader3);
-
-        Layer layer = Layer.create(cf, map::get);
-
-        // configuration
-        assertTrue(layer.configuration().get() == cf);
-        assertTrue(layer.configuration().get().descriptors().size() == 3);
-
-        // modules
-        Set<Module> modules = layer.modules();
-        assertTrue(modules.size() == 3);
-        Set<String> names = modules.stream()
-            .map(Module::getName)
-            .collect(Collectors.toSet());
-        assertTrue(names.contains("m1"));
-        assertTrue(names.contains("m2"));
-        assertTrue(names.contains("m3"));
-
-        // findModule
-        Module m1 = layer.findModule("m1").get();
-        Module m2 = layer.findModule("m2").get();
-        Module m3 = layer.findModule("m3").get();
-        assertEquals(m1.getName(), "m1");
-        assertEquals(m2.getName(), "m2");
-        assertEquals(m3.getName(), "m3");
-        assertTrue(modules.contains(m1));
-        assertTrue(modules.contains(m2));
-        assertTrue(modules.contains(m3));
-        assertFalse(layer.findModule("godot").isPresent());
-
-        // findLoader
-        assertTrue(layer.findLoader("m1") == loader1);
-        assertTrue(layer.findLoader("m2") == loader2);
-        assertTrue(layer.findLoader("m3") == loader3);
-        try {
-            ClassLoader loader = layer.findLoader("godot");
-            assertTrue(false);
-        } catch (IllegalArgumentException ignore) { }
-
-        // parent
-        assertTrue(layer.parent().get() == Layer.empty());
-    }
-
-
-    /**
-     * Exercise Layer.create, created over the boot layer
-     */
-    public void testLayerOnBoot() {
-        ModuleDescriptor descriptor1
-            = new ModuleDescriptor.Builder("m1")
-                .requires("m2")
-                .requires("java.base")
-                .exports("p1")
-                .build();
-
-        ModuleDescriptor descriptor2
-            = new ModuleDescriptor.Builder("m2")
-                .requires("java.base")
-                .build();
-
-        ModuleFinder finder
-            = ModuleUtils.finderOf(descriptor1, descriptor2);
-
-        Configuration cf = Configuration.resolve(finder,
-                                                 Layer.boot(),
-                                                 ModuleFinder.empty(),
-                                                 "m1");
-
-        ClassLoader loader = new ModuleClassLoader(cf);
-
-        Layer layer = Layer.create(cf, mn -> loader);
-
-        // configuration
-        assertTrue(layer.configuration().get() == cf);
-        assertTrue(layer.configuration().get().descriptors().size() == 2);
-
-        // modules
-        Set<Module> modules = layer.modules();
-        assertTrue(modules.size() == 2);
-        Set<String> names = modules.stream()
-            .map(Module::getName)
-            .collect(Collectors.toSet());
-        assertTrue(names.contains("m1"));
-        assertTrue(names.contains("m2"));
-
-        // findModule
-        Module m1 = layer.findModule("m1").get();
-        Module m2 = layer.findModule("m2").get();
-        assertEquals(m1.getName(), "m1");
-        assertEquals(m2.getName(), "m2");
-        assertTrue(modules.contains(m1));
-        assertTrue(modules.contains(m2));
-        assertTrue(layer.findModule("java.base").get() == Object.class.getModule());
-        assertFalse(layer.findModule("godot").isPresent());
-
-        // findLoader
-        assertTrue(layer.findLoader("m1") == loader);
-        assertTrue(layer.findLoader("m2") == loader);
-        assertTrue(layer.findLoader("java.base") == null);
-
-        // parent
-        assertTrue(layer.parent().get() == Layer.boot());
-    }
-
-
-    /**
-     * Layer.create with a configuration of two modules that have the same
-     * module-private package.
-     */
-    public void testSameConcealedPackage() {
-        ModuleDescriptor descriptor1
-            =  new ModuleDescriptor.Builder("m1")
-                .requires("m2")
-                .conceals("p")
-                .build();
-
-        ModuleDescriptor descriptor2
-            = new ModuleDescriptor.Builder("m2")
-                .conceals("p")
-                .build();
-
-        ModuleFinder finder
-            = ModuleUtils.finderOf(descriptor1, descriptor2);
-
-        Configuration cf
-            = Configuration.resolve(finder, Layer.empty(), ModuleFinder.empty(), "m1");
-        assertTrue(cf.descriptors().size() == 2);
-
-        // one loader per module, should be okay
-        Layer.create(cf, mn -> new ModuleClassLoader(cf, mn));
-
-        // same class loader
-        try {
-            ClassLoader loader = new ModuleClassLoader(cf);
-            Layer.create(cf, mn -> loader);
-            assertTrue(false);
-        } catch (LayerInstantiationException expected) { }
-    }
-
-
-    /**
-     * Layer.create with a configuration with a partitioned graph. The same
-     * package is exported in both partitions.
-     */
-    public void testSameExportInPartitionedGraph() {
-
-        // m1 reads m2, m2 exports p to m1
-        ModuleDescriptor descriptor1
-            =  new ModuleDescriptor.Builder("m1")
-                .requires("m2")
-                .build();
-        ModuleDescriptor descriptor2
-            =  new ModuleDescriptor.Builder("m2")
-                .exports("p", "m1")
-                .build();
-
-        // m3 reads m4, m4 exports p to m3
-        ModuleDescriptor descriptor3
-            =  new ModuleDescriptor.Builder("m3")
-                .requires("m4")
-                .build();
-        ModuleDescriptor descriptor4
-            =  new ModuleDescriptor.Builder("m4")
-                .exports("p", "m3")
-                .build();
-
-        ModuleFinder finder
-            = ModuleUtils.finderOf(descriptor1,
-                                   descriptor2,
-                                   descriptor3,
-                                   descriptor4);
-
-        Configuration cf
-            = Configuration.resolve(finder, Layer.empty(), ModuleFinder.empty(),
-                                    "m1", "m3");
-        assertTrue(cf.descriptors().size() == 4);
-
-        // one loader per module
-        Layer.create(cf, mn -> new ModuleClassLoader(cf, mn));
-
-        // m1 & m2 in one loader, m3 & m4 in another loader
-        ClassLoader loader1 = new ModuleClassLoader(cf, "m1");
-        ClassLoader loader2 = new ModuleClassLoader(cf, "m2");
-        Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", loader1);
-        map.put("m2", loader1);
-        map.put("m3", loader2);
-        map.put("m3", loader2);
-        Layer.create(cf, map::get);
-
-        // same loader
-        try {
-            ClassLoader loader = new ModuleClassLoader(cf);
-            Layer.create(cf, mn -> loader);
-            assertTrue(false);
-        } catch (LayerInstantiationException expected) { }
-    }
-
-
-    /**
-     * Layer.create with a configuration that contains a module that has a
-     * concealed package that is the same name as a non-exported package
-     * in a parent layer.
-     */
-    public void testConcealSamePackageAsBootLayer() {
-        ModuleDescriptor descriptor
-            = new ModuleDescriptor.Builder("m1")
-               .requires("java.base")
-               .conceals("sun.launcher")
-               .build();
-
-        ModuleFinder finder = ModuleUtils.finderOf(descriptor);
-
-        Configuration cf
-            = Configuration.resolve(finder, Layer.boot(), ModuleFinder.empty(), "m1");
-        assertTrue(cf.descriptors().size() == 1);
-
-        ClassLoader loader = new ModuleClassLoader(cf);
-        Layer layer = Layer.create(cf, mn -> loader);
-        assertTrue(layer.modules().size() == 1);
-   }
-
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/jdk/jigsaw/reflect/LayerTest.java	Sat Aug 01 21:57:25 2015 +0100
@@ -0,0 +1,361 @@
+/*
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/**
+ * @test
+ * @library ../lib
+ * @build LayerTest ModuleUtils
+ * @run testng LayerTest
+ * @summary Basic tests for java.lang.reflect.Layer;
+ */
+
+import java.lang.module.Configuration;
+import java.lang.module.ModuleDescriptor;
+import java.lang.module.ModuleFinder;
+import java.lang.reflect.Layer;
+import java.lang.reflect.LayerInstantiationException;
+import java.lang.reflect.Module;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.Set;
+import java.util.stream.Collectors;
+
+import org.testng.annotations.Test;
+import static org.testng.Assert.*;
+
+@Test
+public class LayerTest {
+
+    /**
+     * Exercise Layer.boot()
+     */
+    public void testBoot() {
+        Layer bootLayer = Layer.boot();
+
+        // configuration
+        Configuration cf = bootLayer.configuration().get();
+        assertTrue(cf.findDescriptor("java.base").get().exports()
+                   .stream().anyMatch(e -> (e.source().equals("java.lang")
+                                            && !e.targets().isPresent())));
+
+        // modules
+        Set<Module> modules = bootLayer.modules();
+        assertTrue(modules.contains(Object.class.getModule()));
+        int count = (int) modules.stream().map(Module::getName).count();
+        assertEquals(count, modules.size()); // module names are unique
+
+        // findModule
+        Module base = Object.class.getModule();
+        assertTrue(bootLayer.findModule("java.base").get() == base);
+
+        // findLoader
+        assertTrue(bootLayer.findLoader("java.base") == null);
+
+        // parent
+        assertTrue(bootLayer.parent().get() == Layer.empty());
+    }
+
+
+    /**
+     * Exercise Layer.empty()
+     */
+    public void testEmpty() {
+        Layer emptyLayer = Layer.empty();
+
+        // configuration
+        assertFalse(emptyLayer.configuration().isPresent());
+
+        // modules
+        assertTrue(emptyLayer.modules().isEmpty());
+
+        // findModule
+        assertFalse(emptyLayer.findModule("java.base").isPresent());
+
+        // findLoader
+        try {
+            ClassLoader loader = emptyLayer.findLoader("java.base");
+            assertTrue(false);
+        } catch (IllegalArgumentException ignore) { }
+
+        // parent
+        assertTrue(!emptyLayer.parent().isPresent());
+    }
+
+
+    /**
+     * Exercise Layer.create, created on an empty layer
+     */
+    public void testLayerOnEmpty() {
+        ModuleDescriptor descriptor1
+            = new ModuleDescriptor.Builder("m1")
+                .requires("m2")
+                .exports("p1")
+                .build();
+
+        ModuleDescriptor descriptor2
+            = new ModuleDescriptor.Builder("m2")
+                .requires("m3")
+                .build();
+
+        ModuleDescriptor descriptor3
+            = new ModuleDescriptor.Builder("m3")
+                .build();
+
+        ModuleFinder finder
+            = ModuleUtils.finderOf(descriptor1, descriptor2, descriptor3);
+
+        Configuration cf = Configuration.resolve(finder,
+                                                 Layer.empty(),
+                                                 ModuleFinder.empty(),
+                                                 "m1");
+
+        // map each module to its own class loader for this test
+        ClassLoader loader1 = new ModuleClassLoader(cf, "m1");
+        ClassLoader loader2 = new ModuleClassLoader(cf, "m2");
+        ClassLoader loader3 = new ModuleClassLoader(cf, "m3");
+        Map<String, ClassLoader> map = new HashMap<>();
+        map.put("m1", loader1);
+        map.put("m2", loader2);
+        map.put("m3", loader3);
+
+        Layer layer = Layer.create(cf, map::get);
+
+        // configuration
+        assertTrue(layer.configuration().get() == cf);
+        assertTrue(layer.configuration().get().descriptors().size() == 3);
+
+        // modules
+        Set<Module> modules = layer.modules();
+        assertTrue(modules.size() == 3);
+        Set<String> names = modules.stream()
+            .map(Module::getName)
+            .collect(Collectors.toSet());
+        assertTrue(names.contains("m1"));
+        assertTrue(names.contains("m2"));
+        assertTrue(names.contains("m3"));
+
+        // findModule
+        Module m1 = layer.findModule("m1").get();
+        Module m2 = layer.findModule("m2").get();
+        Module m3 = layer.findModule("m3").get();
+        assertEquals(m1.getName(), "m1");
+        assertEquals(m2.getName(), "m2");
+        assertEquals(m3.getName(), "m3");
+        assertTrue(modules.contains(m1));
+        assertTrue(modules.contains(m2));
+        assertTrue(modules.contains(m3));
+        assertFalse(layer.findModule("godot").isPresent());
+
+        // findLoader
+        assertTrue(layer.findLoader("m1") == loader1);
+        assertTrue(layer.findLoader("m2") == loader2);
+        assertTrue(layer.findLoader("m3") == loader3);
+        try {
+            ClassLoader loader = layer.findLoader("godot");
+            assertTrue(false);
+        } catch (IllegalArgumentException ignore) { }
+
+        // parent
+        assertTrue(layer.parent().get() == Layer.empty());
+    }
+
+
+    /**
+     * Exercise Layer.create, created over the boot layer
+     */
+    public void testLayerOnBoot() {
+        ModuleDescriptor descriptor1
+            = new ModuleDescriptor.Builder("m1")
+                .requires("m2")
+                .requires("java.base")
+                .exports("p1")
+                .build();
+
+        ModuleDescriptor descriptor2
+            = new ModuleDescriptor.Builder("m2")
+                .requires("java.base")
+                .build();
+
+        ModuleFinder finder
+            = ModuleUtils.finderOf(descriptor1, descriptor2);
+
+        Configuration cf = Configuration.resolve(finder,
+                                                 Layer.boot(),
+                                                 ModuleFinder.empty(),
+                                                 "m1");
+
+        ClassLoader loader = new ModuleClassLoader(cf);
+
+        Layer layer = Layer.create(cf, mn -> loader);
+
+        // configuration
+        assertTrue(layer.configuration().get() == cf);
+        assertTrue(layer.configuration().get().descriptors().size() == 2);
+
+        // modules
+        Set<Module> modules = layer.modules();
+        assertTrue(modules.size() == 2);
+        Set<String> names = modules.stream()
+            .map(Module::getName)
+            .collect(Collectors.toSet());
+        assertTrue(names.contains("m1"));
+        assertTrue(names.contains("m2"));
+
+        // findModule
+        Module m1 = layer.findModule("m1").get();
+        Module m2 = layer.findModule("m2").get();
+        assertEquals(m1.getName(), "m1");
+        assertEquals(m2.getName(), "m2");
+        assertTrue(modules.contains(m1));
+        assertTrue(modules.contains(m2));
+        assertTrue(layer.findModule("java.base").get() == Object.class.getModule());
+        assertFalse(layer.findModule("godot").isPresent());
+
+        // findLoader
+        assertTrue(layer.findLoader("m1") == loader);
+        assertTrue(layer.findLoader("m2") == loader);
+        assertTrue(layer.findLoader("java.base") == null);
+
+        // parent
+        assertTrue(layer.parent().get() == Layer.boot());
+    }
+
+
+    /**
+     * Layer.create with a configuration of two modules that have the same
+     * module-private package.
+     */
+    public void testSameConcealedPackage() {
+        ModuleDescriptor descriptor1
+            =  new ModuleDescriptor.Builder("m1")
+                .requires("m2")
+                .conceals("p")
+                .build();
+
+        ModuleDescriptor descriptor2
+            = new ModuleDescriptor.Builder("m2")
+                .conceals("p")
+                .build();
+
+        ModuleFinder finder
+            = ModuleUtils.finderOf(descriptor1, descriptor2);
+
+        Configuration cf
+            = Configuration.resolve(finder, Layer.empty(), ModuleFinder.empty(), "m1");
+        assertTrue(cf.descriptors().size() == 2);
+
+        // one loader per module, should be okay
+        Layer.create(cf, mn -> new ModuleClassLoader(cf, mn));
+
+        // same class loader
+        try {
+            ClassLoader loader = new ModuleClassLoader(cf);
+            Layer.create(cf, mn -> loader);
+            assertTrue(false);
+        } catch (LayerInstantiationException expected) { }
+    }
+
+
+    /**
+     * Layer.create with a configuration with a partitioned graph. The same
+     * package is exported in both partitions.
+     */
+    public void testSameExportInPartitionedGraph() {
+
+        // m1 reads m2, m2 exports p to m1
+        ModuleDescriptor descriptor1
+            =  new ModuleDescriptor.Builder("m1")
+                .requires("m2")
+                .build();
+        ModuleDescriptor descriptor2
+            =  new ModuleDescriptor.Builder("m2")
+                .exports("p", "m1")
+                .build();
+
+        // m3 reads m4, m4 exports p to m3
+        ModuleDescriptor descriptor3
+            =  new ModuleDescriptor.Builder("m3")
+                .requires("m4")
+                .build();
+        ModuleDescriptor descriptor4
+            =  new ModuleDescriptor.Builder("m4")
+                .exports("p", "m3")
+                .build();
+
+        ModuleFinder finder
+            = ModuleUtils.finderOf(descriptor1,
+                                   descriptor2,
+                                   descriptor3,
+                                   descriptor4);
+
+        Configuration cf
+            = Configuration.resolve(finder, Layer.empty(), ModuleFinder.empty(),
+                                    "m1", "m3");
+        assertTrue(cf.descriptors().size() == 4);
+
+        // one loader per module
+        Layer.create(cf, mn -> new ModuleClassLoader(cf, mn));
+
+        // m1 & m2 in one loader, m3 & m4 in another loader
+        ClassLoader loader1 = new ModuleClassLoader(cf, "m1");
+        ClassLoader loader2 = new ModuleClassLoader(cf, "m2");
+        Map<String, ClassLoader> map = new HashMap<>();
+        map.put("m1", loader1);
+        map.put("m2", loader1);
+        map.put("m3", loader2);
+        map.put("m3", loader2);
+        Layer.create(cf, map::get);
+
+        // same loader
+        try {
+            ClassLoader loader = new ModuleClassLoader(cf);
+            Layer.create(cf, mn -> loader);
+            assertTrue(false);
+        } catch (LayerInstantiationException expected) { }
+    }
+
+
+    /**
+     * Layer.create with a configuration that contains a module that has a
+     * concealed package that is the same name as a non-exported package
+     * in a parent layer.
+     */
+    public void testConcealSamePackageAsBootLayer() {
+        ModuleDescriptor descriptor
+            = new ModuleDescriptor.Builder("m1")
+               .requires("java.base")
+               .conceals("sun.launcher")
+               .build();
+
+        ModuleFinder finder = ModuleUtils.finderOf(descriptor);
+
+        Configuration cf
+            = Configuration.resolve(finder, Layer.boot(), ModuleFinder.empty(), "m1");
+        assertTrue(cf.descriptors().size() == 1);
+
+        ClassLoader loader = new ModuleClassLoader(cf);
+        Layer layer = Layer.create(cf, mn -> loader);
+        assertTrue(layer.modules().size() == 1);
+   }
+
+}
--- a/test/jdk/jigsaw/reflect/ModuleTest.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/test/jdk/jigsaw/reflect/ModuleTest.java	Sat Aug 01 21:57:25 2015 +0100
@@ -21,9 +21,9 @@
  * questions.
  */
 
-import java.lang.module.Layer;
 import java.lang.module.ModuleDescriptor;
 import java.lang.module.ModuleDescriptor.Exports;
+import java.lang.reflect.Layer;
 import java.lang.reflect.Module;
 import java.util.function.Predicate;
 import java.util.stream.Stream;
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/jdk/jigsaw/reflect/TEST.properties	Sat Aug 01 21:57:25 2015 +0100
@@ -0,0 +1,1 @@
+modules = java.base/jdk.internal.module
--- a/test/jdk/jigsaw/resources/basic/Basic.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/test/jdk/jigsaw/resources/basic/Basic.java	Sat Aug 01 21:57:25 2015 +0100
@@ -22,9 +22,8 @@
  */
 
 import java.lang.module.Configuration;
-import java.lang.module.Layer;
 import java.lang.module.ModuleReference;
-
+import java.lang.reflect.Layer;
 import java.io.ByteArrayOutputStream;
 import java.io.IOException;
 import java.io.InputStream;
--- a/test/jdk/jigsaw/services/layer/BasicLayerTest.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/test/jdk/jigsaw/services/layer/BasicLayerTest.java	Sat Aug 01 21:57:25 2015 +0100
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import java.lang.module.Layer;
+import java.lang.reflect.Layer;
 import java.security.Provider;
 import java.util.ServiceLoader;
 
--- a/test/jdk/jigsaw/services/layer/CustomLayerTest.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/test/jdk/jigsaw/services/layer/CustomLayerTest.java	Sat Aug 01 21:57:25 2015 +0100
@@ -22,9 +22,9 @@
  */
 
 import java.lang.module.Configuration;
-import java.lang.module.Layer;
 import java.lang.module.ModuleReference;
 import java.lang.module.ModuleFinder;
+import java.lang.reflect.Layer;
 import java.nio.file.Path;
 import java.nio.file.Paths;
 import java.util.ServiceLoader;
--- a/test/jdk/jigsaw/tools/jlink/JLinkTest.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/test/jdk/jigsaw/tools/jlink/JLinkTest.java	Sat Aug 01 21:57:25 2015 +0100
@@ -22,7 +22,7 @@
  */
 import java.io.PrintWriter;
 import java.io.StringWriter;
-import java.lang.module.Layer;
+import java.lang.reflect.Layer;
 import java.nio.file.Files;
 import java.nio.file.Path;
 import java.nio.file.Paths;
--- a/test/jdk/jigsaw/tools/jlink/basic/src/test/jdk/test/Test.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/test/jdk/jigsaw/tools/jlink/basic/src/test/jdk/test/Test.java	Sat Aug 01 21:57:25 2015 +0100
@@ -24,7 +24,7 @@
 package jdk.test;
 
 import java.lang.reflect.Module;
-import java.lang.module.Layer;
+import java.lang.reflect.Layer;
 
 public class Test {
     public static void main(String[] args) {
--- a/test/jdk/jigsaw/tools/jlink/plugins/PluginsNegativeTest.java	Sat Aug 01 20:33:01 2015 +0100
+++ b/test/jdk/jigsaw/tools/jlink/plugins/PluginsNegativeTest.java	Sat Aug 01 21:57:25 2015 +0100
@@ -30,7 +30,7 @@
  */
 
 import java.io.IOException;
-import java.lang.module.Layer;
+import java.lang.reflect.Layer;
 import java.nio.ByteBuffer;
 import java.nio.ByteOrder;
 import java.util.List;