Merge jdk-9+157
authorduke
Wed, 05 Jul 2017 22:52:01 +0200
changeset 43774 fa3e76b47782
parent 43773 8d8593871575 (current diff)
parent 43753 acab82802f8a (diff)
child 43775 73a0b9362c98
Merge
jdk/src/java.base/share/classes/sun/security/provider/certpath/PKIXTimestampParameters.java
jdk/src/java.base/share/classes/sun/security/util/CertConstraintParameters.java
jdk/src/jdk.desktop/share/classes/jdk/awt/AWTUtils.java
jdk/src/jdk.desktop/share/classes/module-info.java
jdk/test/java/awt/jdk/TestJDKAWTUtils.java
jdk/test/java/lang/StackWalker/CountLocalSlots.java
jdk/test/java/lang/StackWalker/LocalsCrash.java
jdk/test/java/lang/invoke/lambda/MetafactorySamReturnTest.java
jdk/test/java/lang/invoke/modules/ModuleAccessControlTest.java
jdk/test/java/lang/invoke/modules/src/m1/module-info.java
jdk/test/java/lang/invoke/modules/src/m1/p1/Main.java
jdk/test/java/lang/invoke/modules/src/m1/p1/Type1.java
jdk/test/java/lang/invoke/modules/src/m1/p2/Type2.java
jdk/test/java/lang/invoke/modules/src/m2/module-info.java
jdk/test/java/lang/invoke/modules/src/m2/q1/Type1.java
jdk/test/java/lang/invoke/modules/src/m2/q2/Type2.java
jdk/test/javax/xml/jaxp/common/8035437/Document.java
jdk/test/javax/xml/jaxp/common/8035437/DocumentImpl.java
jdk/test/javax/xml/jaxp/common/8035437/Node.java
jdk/test/sun/text/IntHashtable/Bug4170614Test.java
--- a/.hgtags	Mon Feb 13 11:57:56 2017 +0100
+++ b/.hgtags	Wed Jul 05 22:52:01 2017 +0200
@@ -399,3 +399,4 @@
 8c70d170e62c0c58b5bc3ba666bd140399b98c9c jdk-10+0
 45b751afd11e6c05991cf4913c5a0ac3304fcc4e jdk-9+154
 f4aff695ffe05cfdb69d8af25a4ddc6a029754ea jdk-9+155
+06bce0388880b5ff8e040e4a9d72a3ea11dac321 jdk-9+156
--- a/.hgtags-top-repo	Mon Feb 13 11:57:56 2017 +0100
+++ b/.hgtags-top-repo	Wed Jul 05 22:52:01 2017 +0200
@@ -398,3 +398,4 @@
 816a6d03a7c44edfbd8780110529f1bdc3964fb9 jdk-9+153
 8d26916eaa21b689835ffc1c0dbf12470aa9be61 jdk-9+154
 688a3863c00ebc089ab17ee1fc46272cbbd96815 jdk-9+155
+783ec7542cf7154e5d2b87f55bb97d28f81e9ada jdk-9+156
--- a/common/autoconf/basics.m4	Mon Feb 13 11:57:56 2017 +0100
+++ b/common/autoconf/basics.m4	Wed Jul 05 22:52:01 2017 +0200
@@ -1202,6 +1202,18 @@
 # Check for support for specific options in bash
 AC_DEFUN_ONCE([BASIC_CHECK_BASH_OPTIONS],
 [
+  # Check bash version
+  # Extra [ ] to stop m4 mangling
+  [ BASH_VER=`$BASH --version | $SED -n  -e 's/^.*bash.*ersion *\([0-9.]*\).*$/\1/ p'` ]
+  AC_MSG_CHECKING([bash version])
+  AC_MSG_RESULT([$BASH_VER])
+
+  BASH_MAJOR=`$ECHO $BASH_VER | $CUT -d . -f 1`
+  BASH_MINOR=`$ECHO $BASH_VER | $CUT -d . -f 2`
+  if test $BASH_MAJOR -lt 3 || (test $BASH_MAJOR -eq 3 && test $BASH_MINOR -lt 2); then
+    AC_MSG_ERROR([bash version 3.2 or better is required])
+  fi
+
   # Test if bash supports pipefail.
   AC_MSG_CHECKING([if bash supports pipefail])
   if ${BASH} -c 'set -o pipefail'; then
--- a/common/autoconf/generated-configure.sh	Mon Feb 13 11:57:56 2017 +0100
+++ b/common/autoconf/generated-configure.sh	Wed Jul 05 22:52:01 2017 +0200
@@ -5170,7 +5170,7 @@
 #CUSTOM_AUTOCONF_INCLUDE
 
 # Do not change or remove the following line, it is needed for consistency checks:
-DATE_WHEN_GENERATED=1486175373
+DATE_WHEN_GENERATED=1486679715
 
 ###############################################################################
 #
@@ -24092,6 +24092,20 @@
   fi
 
 
+  # Check bash version
+  # Extra [ ] to stop m4 mangling
+   BASH_VER=`$BASH --version | $SED -n  -e 's/^.*bash.*ersion *\([0-9.]*\).*$/\1/ p'`
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking bash version" >&5
+$as_echo_n "checking bash version... " >&6; }
+  { $as_echo "$as_me:${as_lineno-$LINENO}: result: $BASH_VER" >&5
+$as_echo "$BASH_VER" >&6; }
+
+  BASH_MAJOR=`$ECHO $BASH_VER | $CUT -d . -f 1`
+  BASH_MINOR=`$ECHO $BASH_VER | $CUT -d . -f 2`
+  if test $BASH_MAJOR -lt 3 || (test $BASH_MAJOR -eq 3 && test $BASH_MINOR -lt 2); then
+    as_fn_error $? "bash version 3.2 or better is required" "$LINENO" 5
+  fi
+
   # Test if bash supports pipefail.
   { $as_echo "$as_me:${as_lineno-$LINENO}: checking if bash supports pipefail" >&5
 $as_echo_n "checking if bash supports pipefail... " >&6; }
--- a/corba/.hgtags	Mon Feb 13 11:57:56 2017 +0100
+++ b/corba/.hgtags	Wed Jul 05 22:52:01 2017 +0200
@@ -398,3 +398,4 @@
 68a8e8658511093b322a46ed04b2a321e1da2a43 jdk-9+153
 078ebe23b584466dc8346e620d7821d91751e5a9 jdk-9+154
 a545f54babfa31aa7eb611f36031609acd617cbc jdk-9+155
+907c26240cd481579e919bfd23740797ff8ce1c8 jdk-9+156
--- a/corba/src/java.corba/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/corba/src/java.corba/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Defines the Java binding of the OMG CORBA APIs, and the RMI-IIOP API.
+ *
+ * @since 9
  */
 @Deprecated(since="9", forRemoval=true)
 module java.corba {
--- a/corba/src/java.corba/share/classes/org/omg/CORBA/ORB.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/corba/src/java.corba/share/classes/org/omg/CORBA/ORB.java	Wed Jul 05 22:52:01 2017 +0200
@@ -106,13 +106,13 @@
  *
  *     <LI>check in properties parameter, if any
  *
- *     <LI>check in the System properties
+ *     <LI>check in the System properties, if any
  *
  *     <LI>check in the orb.properties file located in the user.home
- *         directory (if any)
+ *         directory, if any
  *
- *     <LI>check in the orb.properties file located in the java.home/lib
- *         directory (if any)
+ *     <LI>check in the orb.properties file located in the run-time image,
+ *         if any
  *
  *     <LI>fall back on a hardcoded default behavior (use the Java&nbsp;IDL
  *         implementation)
@@ -170,9 +170,15 @@
  * Thus, where appropriate, it is necessary that
  * the classes for this alternative ORBSingleton are available on the application's class path.
  * It should be noted that the singleton ORB is system wide.
- *
+ * <P>
  * When a per-application ORB is created via the 2-arg init methods,
  * then it will be located using the thread context class loader.
+ * <P>
+ * The IDL to Java Language OMG specification documents the ${java.home}/lib directory as the location,
+ * in the Java run-time image, to search for orb.properties.
+ * This location is not intended for user editable configuration files.
+ * Therefore, the implementation first checks the ${java.home}/conf directory for orb.properties,
+ * and thereafter the ${java.home}/lib directory.
  *
  * @since   JDK1.2
  */
@@ -271,14 +277,25 @@
                     }
 
                     String javaHome = System.getProperty("java.home");
-                    fileName = javaHome + File.separator
-                        + "lib" + File.separator + "orb.properties";
-                    props = getFileProperties( fileName ) ;
+
+                    fileName = javaHome + File.separator + "conf"
+                            + File.separator + "orb.properties";
+                    props = getFileProperties(fileName);
+
+                    if (props != null) {
+                        String value = props.getProperty(name);
+                        if (value != null)
+                            return value;
+                    }
+
+                    fileName = javaHome + File.separator + "lib"
+                            + File.separator + "orb.properties";
+                    props = getFileProperties(fileName);
 
                     if (props == null)
-                        return null ;
+                        return null;
                     else
-                        return props.getProperty( name ) ;
+                        return props.getProperty(name);
                 }
             }
         );
--- a/hotspot/.hgtags	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/.hgtags	Wed Jul 05 22:52:01 2017 +0200
@@ -558,3 +558,4 @@
 217ba81b9a4ce8698200370175aa2db86a39f66c jdk-9+153
 a9fdfd55835ef9dccb7f317b07249bd66653b874 jdk-9+154
 f3b3d77a1751897413aae43ac340a130b6fa2ae1 jdk-9+155
+43139c588ea48b6504e52b6c3dec530b17b1fdb4 jdk-9+156
--- a/hotspot/src/cpu/aarch64/vm/c1_LIRAssembler_aarch64.cpp	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/cpu/aarch64/vm/c1_LIRAssembler_aarch64.cpp	Wed Jul 05 22:52:01 2017 +0200
@@ -1922,12 +1922,17 @@
     }
 
     if (opr2->is_constant()) {
+      bool is_32bit = false; // width of register operand
       jlong imm;
+
       switch(opr2->type()) {
+      case T_INT:
+        imm = opr2->as_constant_ptr()->as_jint();
+        is_32bit = true;
+        break;
       case T_LONG:
         imm = opr2->as_constant_ptr()->as_jlong();
         break;
-      case T_INT:
       case T_ADDRESS:
         imm = opr2->as_constant_ptr()->as_jint();
         break;
@@ -1942,14 +1947,14 @@
       }
 
       if (Assembler::operand_valid_for_add_sub_immediate(imm)) {
-        if (type2aelembytes(opr1->type()) <= 4)
+        if (is_32bit)
           __ cmpw(reg1, imm);
         else
           __ cmp(reg1, imm);
         return;
       } else {
         __ mov(rscratch1, imm);
-        if (type2aelembytes(opr1->type()) <= 4)
+        if (is_32bit)
           __ cmpw(reg1, rscratch1);
         else
           __ cmp(reg1, rscratch1);
--- a/hotspot/src/jdk.aot/share/classes/jdk.tools.jaotc/src/jdk/tools/jaotc/AOTStub.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/jdk.aot/share/classes/jdk.tools.jaotc/src/jdk/tools/jaotc/AOTStub.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,7 @@
 
 import org.graalvm.compiler.code.CompilationResult;
 import org.graalvm.compiler.core.target.Backend;
+import org.graalvm.compiler.hotspot.HotSpotCompiledCodeBuilder;
 import org.graalvm.compiler.hotspot.stubs.Stub;
 
 import jdk.vm.ci.hotspot.HotSpotCompiledCode;
@@ -48,7 +49,7 @@
     }
 
     public HotSpotCompiledCode compiledCode(CompilationResult result) {
-        return stub.getCompiledCode(backend);
+        return HotSpotCompiledCodeBuilder.createCompiledCode(null, null, result);
     }
 
 }
--- a/hotspot/src/jdk.hotspot.agent/linux/native/libsaproc/libproc_impl.c	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/jdk.hotspot.agent/linux/native/libsaproc/libproc_impl.c	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 2017, 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
@@ -50,7 +50,7 @@
   }
 
 
-  if (strlen(alt_root) + strlen(name) < PATH_MAX) {
+  if (strlen(alt_root) + strlen(name) > PATH_MAX) {
     // Buffer too small.
     return -1;
   }
--- a/hotspot/src/jdk.hotspot.agent/share/classes/sun/jvm/hotspot/utilities/AbstractHeapGraphWriter.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/jdk.hotspot.agent/share/classes/sun/jvm/hotspot/utilities/AbstractHeapGraphWriter.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 2017, 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
@@ -114,6 +114,8 @@
                     }
                 });
 
+                writeHeapRecordPrologue();
+
                 // write JavaThreads
                 writeJavaThreads();
 
--- a/hotspot/src/jdk.hotspot.agent/share/classes/sun/jvm/hotspot/utilities/HeapHprofBinWriter.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/jdk.hotspot.agent/share/classes/sun/jvm/hotspot/utilities/HeapHprofBinWriter.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 2017, 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
@@ -45,8 +45,8 @@
  * WARNING: This format is still under development, and is subject to
  * change without notice.
  *
- * header    "JAVA PROFILE 1.0.1" or "JAVA PROFILE 1.0.2" (0-terminated)
- * u4        size of identifiers. Identifiers are used to represent
+ * header     "JAVA PROFILE 1.0.2" (0-terminated)
+ * u4         size of identifiers. Identifiers are used to represent
  *            UTF8 strings, objects, stack traces, etc. They usually
  *            have the same size as host pointers. For example, on
  *            Solaris and Win32, the size is 4.
@@ -294,10 +294,9 @@
  *                u2        stack trace depth
  *
  *
- * When the header is "JAVA PROFILE 1.0.2" a heap dump can optionally
- * be generated as a sequence of heap dump segments. This sequence is
- * terminated by an end record. The additional tags allowed by format
- * "JAVA PROFILE 1.0.2" are:
+ * A heap dump can optionally be generated as a sequence of heap dump
+ * segments. This sequence is terminated by an end record. The additional
+ * tags allowed by format "JAVA PROFILE 1.0.2" are:
  *
  * HPROF_HEAP_DUMP_SEGMENT  denote a heap dump segment
  *
@@ -310,8 +309,6 @@
 
 public class HeapHprofBinWriter extends AbstractHeapGraphWriter {
 
-    // The heap size threshold used to determine if segmented format
-    // ("JAVA PROFILE 1.0.2") should be used.
     private static final long HPROF_SEGMENTED_HEAP_DUMP_THRESHOLD = 2L * 0x40000000;
 
     // The approximate size of a heap segment. Used to calculate when to create
@@ -319,7 +316,6 @@
     private static final long HPROF_SEGMENTED_HEAP_DUMP_SEGMENT_SIZE = 1L * 0x40000000;
 
     // hprof binary file header
-    private static final String HPROF_HEADER_1_0_1 = "JAVA PROFILE 1.0.1";
     private static final String HPROF_HEADER_1_0_2 = "JAVA PROFILE 1.0.2";
 
     // constants in enum HprofTag
@@ -380,6 +376,7 @@
     private static final int JVM_SIGNATURE_ARRAY   = '[';
     private static final int JVM_SIGNATURE_CLASS   = 'L';
 
+    private static final long MAX_U4_VALUE = 0xFFFFFFFFL;
     int serialNum = 1;
 
     public synchronized void write(String fileName) throws IOException {
@@ -469,7 +466,6 @@
             // length later - hprof format requires length.
             out.flush();
             currentSegmentStart = fos.getChannel().position();
-
             // write dummy length of 0 and we'll fix it later.
             out.writeInt(0);
         }
@@ -479,7 +475,7 @@
     protected void writeHeapRecordEpilogue() throws IOException {
         if (useSegmentedHeapDump) {
             out.flush();
-            if ((fos.getChannel().position() - currentSegmentStart - 4) >= HPROF_SEGMENTED_HEAP_DUMP_SEGMENT_SIZE) {
+            if ((fos.getChannel().position() - currentSegmentStart - 4L) >= HPROF_SEGMENTED_HEAP_DUMP_SEGMENT_SIZE) {
                 fillInHeapRecordLength();
                 currentSegmentStart = 0;
             }
@@ -488,14 +484,14 @@
 
     private void fillInHeapRecordLength() throws IOException {
 
-        // now get current position to calculate length
+        // now get the current position to calculate length
         long dumpEnd = fos.getChannel().position();
 
-        // calculate length of heap data
+        // calculate the length of heap data
         long dumpLenLong = (dumpEnd - currentSegmentStart - 4L);
 
         // Check length boundary, overflow could happen but is _very_ unlikely
-        if(dumpLenLong >= (4L * 0x40000000)){
+        if (dumpLenLong >= (4L * 0x40000000)) {
             throw new RuntimeException("Heap segment size overflow.");
         }
 
@@ -517,6 +513,71 @@
         fos.getChannel().position(currentPosition);
     }
 
+    // get the size in bytes for the requested type
+    private long getSizeForType(int type) throws IOException {
+        switch (type) {
+            case TypeArrayKlass.T_BOOLEAN:
+                return BOOLEAN_SIZE;
+            case TypeArrayKlass.T_INT:
+                return INT_SIZE;
+            case TypeArrayKlass.T_CHAR:
+                return CHAR_SIZE;
+            case TypeArrayKlass.T_SHORT:
+                return SHORT_SIZE;
+            case TypeArrayKlass.T_BYTE:
+                return BYTE_SIZE;
+            case TypeArrayKlass.T_LONG:
+                return LONG_SIZE;
+            case TypeArrayKlass.T_FLOAT:
+                return FLOAT_SIZE;
+            case TypeArrayKlass.T_DOUBLE:
+                return DOUBLE_SIZE;
+            default:
+                throw new RuntimeException(
+                    "Should not reach here: Unknown type: " + type);
+         }
+    }
+
+    private int getArrayHeaderSize(boolean isObjectAarray) {
+        return isObjectAarray?
+            ((int) BYTE_SIZE + 2 * (int) INT_SIZE + 2 * (int) OBJ_ID_SIZE):
+            (2 * (int) BYTE_SIZE + 2 * (int) INT_SIZE + (int) OBJ_ID_SIZE);
+    }
+
+    // Check if we need to truncate an array
+    private int calculateArrayMaxLength(long originalArrayLength,
+                                        int headerSize,
+                                        long typeSize,
+                                        String typeName) throws IOException {
+
+        long length = originalArrayLength;
+
+        // now get the current position to calculate length
+        long dumpEnd = fos.getChannel().position();
+        long originalLengthInBytes = originalArrayLength * typeSize;
+
+        // calculate the length of heap data
+        long currentRecordLength = (dumpEnd - currentSegmentStart - 4L);
+        if (currentRecordLength > 0 &&
+            (currentRecordLength + headerSize + originalLengthInBytes) > MAX_U4_VALUE) {
+            fillInHeapRecordLength();
+            currentSegmentStart = 0;
+            writeHeapRecordPrologue();
+            currentRecordLength = 0;
+        }
+
+        // Calculate the max bytes we can use.
+        long maxBytes = (MAX_U4_VALUE - (headerSize + currentRecordLength));
+
+        if (originalLengthInBytes > maxBytes) {
+            length = maxBytes/typeSize;
+            System.err.println("WARNING: Cannot dump array of type " + typeName
+                               + " with length " + originalArrayLength
+                               + "; truncating to length " + length);
+        }
+        return (int) length;
+    }
+
     private void writeClassDumpRecords() throws IOException {
         SystemDictionary sysDict = VM.getVM().getSystemDictionary();
         ClassLoaderDataGraph cldGraph = VM.getVM().getClassLoaderDataGraph();
@@ -694,12 +755,16 @@
     }
 
     protected void writeObjectArray(ObjArray array) throws IOException {
+        int headerSize = getArrayHeaderSize(true);
+        final int length = calculateArrayMaxLength(array.getLength(),
+                                                   headerSize,
+                                                   OBJ_ID_SIZE,
+                                                   "Object");
         out.writeByte((byte) HPROF_GC_OBJ_ARRAY_DUMP);
         writeObjectID(array);
         out.writeInt(DUMMY_STACK_TRACE_ID);
-        out.writeInt((int) array.getLength());
+        out.writeInt(length);
         writeObjectID(array.getKlass().getJavaMirror());
-        final int length = (int) array.getLength();
         for (int index = 0; index < length; index++) {
             OopHandle handle = array.getOopHandleAt(index);
             writeObjectID(getAddressValue(handle));
@@ -707,101 +772,101 @@
     }
 
     protected void writePrimitiveArray(TypeArray array) throws IOException {
+        int headerSize = getArrayHeaderSize(false);
+        TypeArrayKlass tak = (TypeArrayKlass) array.getKlass();
+        final int type = (int) tak.getElementType();
+        final String typeName = tak.getElementTypeName();
+        final long typeSize = getSizeForType(type);
+        final int length = calculateArrayMaxLength(array.getLength(),
+                                                   headerSize,
+                                                   typeSize,
+                                                   typeName);
         out.writeByte((byte) HPROF_GC_PRIM_ARRAY_DUMP);
         writeObjectID(array);
         out.writeInt(DUMMY_STACK_TRACE_ID);
-        out.writeInt((int) array.getLength());
-        TypeArrayKlass tak = (TypeArrayKlass) array.getKlass();
-        final int type = (int) tak.getElementType();
+        out.writeInt(length);
         out.writeByte((byte) type);
         switch (type) {
             case TypeArrayKlass.T_BOOLEAN:
-                writeBooleanArray(array);
+                writeBooleanArray(array, length);
                 break;
             case TypeArrayKlass.T_CHAR:
-                writeCharArray(array);
+                writeCharArray(array, length);
                 break;
             case TypeArrayKlass.T_FLOAT:
-                writeFloatArray(array);
+                writeFloatArray(array, length);
                 break;
             case TypeArrayKlass.T_DOUBLE:
-                writeDoubleArray(array);
+                writeDoubleArray(array, length);
                 break;
             case TypeArrayKlass.T_BYTE:
-                writeByteArray(array);
+                writeByteArray(array, length);
                 break;
             case TypeArrayKlass.T_SHORT:
-                writeShortArray(array);
+                writeShortArray(array, length);
                 break;
             case TypeArrayKlass.T_INT:
-                writeIntArray(array);
+                writeIntArray(array, length);
                 break;
             case TypeArrayKlass.T_LONG:
-                writeLongArray(array);
+                writeLongArray(array, length);
                 break;
             default:
-                throw new RuntimeException("should not reach here");
+                throw new RuntimeException(
+                    "Should not reach here: Unknown type: " + type);
         }
     }
 
-    private void writeBooleanArray(TypeArray array) throws IOException {
-        final int length = (int) array.getLength();
+    private void writeBooleanArray(TypeArray array, int length) throws IOException {
         for (int index = 0; index < length; index++) {
              long offset = BOOLEAN_BASE_OFFSET + index * BOOLEAN_SIZE;
              out.writeBoolean(array.getHandle().getJBooleanAt(offset));
         }
     }
 
-    private void writeByteArray(TypeArray array) throws IOException {
-        final int length = (int) array.getLength();
+    private void writeByteArray(TypeArray array, int length) throws IOException {
         for (int index = 0; index < length; index++) {
              long offset = BYTE_BASE_OFFSET + index * BYTE_SIZE;
              out.writeByte(array.getHandle().getJByteAt(offset));
         }
     }
 
-    private void writeShortArray(TypeArray array) throws IOException {
-        final int length = (int) array.getLength();
+    private void writeShortArray(TypeArray array, int length) throws IOException {
         for (int index = 0; index < length; index++) {
              long offset = SHORT_BASE_OFFSET + index * SHORT_SIZE;
              out.writeShort(array.getHandle().getJShortAt(offset));
         }
     }
 
-    private void writeIntArray(TypeArray array) throws IOException {
-        final int length = (int) array.getLength();
+    private void writeIntArray(TypeArray array, int length) throws IOException {
         for (int index = 0; index < length; index++) {
              long offset = INT_BASE_OFFSET + index * INT_SIZE;
              out.writeInt(array.getHandle().getJIntAt(offset));
         }
     }
 
-    private void writeLongArray(TypeArray array) throws IOException {
-        final int length = (int) array.getLength();
+    private void writeLongArray(TypeArray array, int length) throws IOException {
         for (int index = 0; index < length; index++) {
              long offset = LONG_BASE_OFFSET + index * LONG_SIZE;
              out.writeLong(array.getHandle().getJLongAt(offset));
         }
     }
 
-    private void writeCharArray(TypeArray array) throws IOException {
-        final int length = (int) array.getLength();
+    private void writeCharArray(TypeArray array, int length) throws IOException {
         for (int index = 0; index < length; index++) {
              long offset = CHAR_BASE_OFFSET + index * CHAR_SIZE;
              out.writeChar(array.getHandle().getJCharAt(offset));
         }
     }
 
-    private void writeFloatArray(TypeArray array) throws IOException {
-        final int length = (int) array.getLength();
+    private void writeFloatArray(TypeArray array, int length) throws IOException {
         for (int index = 0; index < length; index++) {
              long offset = FLOAT_BASE_OFFSET + index * FLOAT_SIZE;
              out.writeFloat(array.getHandle().getJFloatAt(offset));
         }
     }
 
-    private void writeDoubleArray(TypeArray array) throws IOException {
-        final int length = (int) array.getLength();
+    private void writeDoubleArray(TypeArray array, int length) throws IOException {
         for (int index = 0; index < length; index++) {
              long offset = DOUBLE_BASE_OFFSET + index * DOUBLE_SIZE;
              out.writeDouble(array.getHandle().getJDoubleAt(offset));
@@ -996,12 +1061,7 @@
     // writes hprof binary file header
     private void writeFileHeader() throws IOException {
         // version string
-        if(useSegmentedHeapDump) {
-            out.writeBytes(HPROF_HEADER_1_0_2);
-        }
-        else {
-            out.writeBytes(HPROF_HEADER_1_0_1);
-        }
+        out.writeBytes(HPROF_HEADER_1_0_2);
         out.writeByte((byte)'\0');
 
         // write identifier size. we use pointers as identifiers.
--- a/hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.hotspot/src/jdk/vm/ci/hotspot/HotSpotJVMCIMetaAccessContext.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.hotspot/src/jdk/vm/ci/hotspot/HotSpotJVMCIMetaAccessContext.java	Wed Jul 05 22:52:01 2017 +0200
@@ -27,8 +27,6 @@
 import java.lang.ref.WeakReference;
 import java.util.Arrays;
 import java.util.Iterator;
-import java.util.Map;
-import java.util.WeakHashMap;
 
 import jdk.vm.ci.meta.JavaKind;
 import jdk.vm.ci.meta.ResolvedJavaType;
@@ -147,21 +145,34 @@
         }
     }
 
-    private final Map<Class<?>, WeakReference<ResolvedJavaType>> typeMap = new WeakHashMap<>();
+    private final ClassValue<WeakReference<ResolvedJavaType>> resolvedJavaType = new ClassValue<WeakReference<ResolvedJavaType>>() {
+        @Override
+        protected WeakReference<ResolvedJavaType> computeValue(Class<?> type) {
+            return new WeakReference<>(createClass(type));
+        }
+    };
 
     /**
      * Gets the JVMCI mirror for a {@link Class} object.
      *
      * @return the {@link ResolvedJavaType} corresponding to {@code javaClass}
      */
-    public synchronized ResolvedJavaType fromClass(Class<?> javaClass) {
-        WeakReference<ResolvedJavaType> typeRef = typeMap.get(javaClass);
-        ResolvedJavaType type = typeRef != null ? typeRef.get() : null;
-        if (type == null) {
-            type = createClass(javaClass);
-            typeMap.put(javaClass, new WeakReference<>(type));
+    public ResolvedJavaType fromClass(Class<?> javaClass) {
+        ResolvedJavaType javaType = null;
+        while (javaType == null) {
+            WeakReference<ResolvedJavaType> type = resolvedJavaType.get(javaClass);
+            javaType = type.get();
+            if (javaType == null) {
+                /*
+                 * If the referent has become null, clear out the current value
+                 * and let computeValue above create a new value.  Reload the
+                 * value in a loop because in theory the WeakReference referent
+                 * can be reclaimed at any point.
+                 */
+                resolvedJavaType.remove(javaClass);
+            }
         }
-        return type;
+        return javaType;
     }
 
     /**
--- a/hotspot/src/jdk.vm.compiler/share/classes/org.graalvm.compiler.hotspot/src/org/graalvm/compiler/hotspot/stubs/Stub.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/jdk.vm.compiler/share/classes/org.graalvm.compiler.hotspot/src/org/graalvm/compiler/hotspot/stubs/Stub.java	Wed Jul 05 22:52:01 2017 +0200
@@ -90,17 +90,10 @@
     protected InstalledCode code;
 
     /**
-     * Compilation result from which {@link #code} was created.
-     */
-    protected CompilationResult compResult;
-
-    /**
      * The registers destroyed by this stub (from the caller's perspective).
      */
     private Set<Register> destroyedCallerRegisters;
 
-    private HotSpotCompiledCode compiledCode;
-
     public void initDestroyedCallerRegisters(Set<Register> registers) {
         assert registers != null;
         assert destroyedCallerRegisters == null || registers.equals(destroyedCallerRegisters) : "cannot redefine";
@@ -184,35 +177,13 @@
     public synchronized InstalledCode getCode(final Backend backend) {
         if (code == null) {
             try (Scope d = Debug.sandbox("CompilingStub", DebugScope.getConfig(), providers.getCodeCache(), debugScopeContext())) {
-                final StructuredGraph graph = getGraph(getStubCompilationId());
-
-                // Stubs cannot be recompiled so they cannot be compiled with assumptions
-                assert graph.getAssumptions() == null;
-
-                if (!(graph.start() instanceof StubStartNode)) {
-                    StubStartNode newStart = graph.add(new StubStartNode(Stub.this));
-                    newStart.setStateAfter(graph.start().stateAfter());
-                    graph.replaceFixed(graph.start(), newStart);
-                }
-
                 CodeCacheProvider codeCache = providers.getCodeCache();
-
-                compResult = new CompilationResult(toString(), GeneratePIC.getValue());
-                try (Scope s0 = Debug.scope("StubCompilation", graph, providers.getCodeCache())) {
-                    Suites suites = createSuites();
-                    emitFrontEnd(providers, backend, graph, providers.getSuites().getDefaultGraphBuilderSuite(), OptimisticOptimizations.ALL, DefaultProfilingInfo.get(TriState.UNKNOWN), suites);
-                    LIRSuites lirSuites = createLIRSuites();
-                    emitBackEnd(graph, Stub.this, getInstalledCodeOwner(), backend, compResult, CompilationResultBuilderFactory.Default, getRegisterConfig(), lirSuites);
-                    assert checkStubInvariants();
-                } catch (Throwable e) {
-                    throw Debug.handle(e);
-                }
-
-                assert destroyedCallerRegisters != null;
+                CompilationResult compResult = buildCompilationResult(backend);
                 try (Scope s = Debug.scope("CodeInstall", compResult)) {
+                    assert destroyedCallerRegisters != null;
                     // Add a GeneratePIC check here later, we don't want to install
                     // code if we don't have a corresponding VM global symbol.
-                    compiledCode = HotSpotCompiledCodeBuilder.createCompiledCode(null, null, compResult);
+                    HotSpotCompiledCode compiledCode = HotSpotCompiledCodeBuilder.createCompiledCode(null, null, compResult);
                     code = codeCache.installCode(null, compiledCode, null, null, false);
                 } catch (Throwable e) {
                     throw Debug.handle(e);
@@ -226,6 +197,44 @@
         return code;
     }
 
+    @SuppressWarnings("try")
+    private CompilationResult buildCompilationResult(final Backend backend) {
+        CompilationResult compResult = new CompilationResult(toString(), GeneratePIC.getValue());
+        final StructuredGraph graph = getGraph(getStubCompilationId());
+
+        // Stubs cannot be recompiled so they cannot be compiled with assumptions
+        assert graph.getAssumptions() == null;
+
+        if (!(graph.start() instanceof StubStartNode)) {
+            StubStartNode newStart = graph.add(new StubStartNode(Stub.this));
+            newStart.setStateAfter(graph.start().stateAfter());
+            graph.replaceFixed(graph.start(), newStart);
+        }
+
+        try (Scope s0 = Debug.scope("StubCompilation", graph, providers.getCodeCache())) {
+            Suites suites = createSuites();
+            emitFrontEnd(providers, backend, graph, providers.getSuites().getDefaultGraphBuilderSuite(), OptimisticOptimizations.ALL, DefaultProfilingInfo.get(TriState.UNKNOWN), suites);
+            LIRSuites lirSuites = createLIRSuites();
+            emitBackEnd(graph, Stub.this, getInstalledCodeOwner(), backend, compResult, CompilationResultBuilderFactory.Default, getRegisterConfig(), lirSuites);
+            assert checkStubInvariants(compResult);
+        } catch (Throwable e) {
+            throw Debug.handle(e);
+        }
+        return compResult;
+    }
+
+    /**
+     * Gets a {@link CompilationResult} that can be used for code generation. Required for AOT.
+     */
+    @SuppressWarnings("try")
+    public CompilationResult getCompilationResult(final Backend backend) {
+        try (Scope d = Debug.sandbox("CompilingStub", DebugScope.getConfig(), providers.getCodeCache(), debugScopeContext())) {
+            return buildCompilationResult(backend);
+        } catch (Throwable e) {
+            throw Debug.handle(e);
+        }
+    }
+
     public CompilationIdentifier getStubCompilationId() {
         return new StubCompilationIdentifier(this);
     }
@@ -233,7 +242,7 @@
     /**
      * Checks the conditions a compilation must satisfy to be installed as a RuntimeStub.
      */
-    private boolean checkStubInvariants() {
+    private boolean checkStubInvariants(CompilationResult compResult) {
         assert compResult.getExceptionHandlers().isEmpty() : this;
 
         // Stubs cannot be recompiled so they cannot be compiled with
@@ -278,24 +287,4 @@
         }
         return lirSuites;
     }
-
-    /**
-     * Gets the HotSpotCompiledCode that was created during installation.
-     */
-    public synchronized HotSpotCompiledCode getCompiledCode(final Backend backend) {
-        getCompilationResult(backend);
-        assert compiledCode != null;
-        return compiledCode;
-    }
-
-    /**
-     * Gets the compilation result for this stub, compiling it first if necessary, and installing it
-     * in code.
-     */
-    public synchronized CompilationResult getCompilationResult(final Backend backend) {
-        if (code == null) {
-            getCode(backend);
-        }
-        return compResult;
-    }
 }
--- a/hotspot/src/share/vm/c1/c1_Canonicalizer.cpp	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/share/vm/c1/c1_Canonicalizer.cpp	Wed Jul 05 22:52:01 2017 +0200
@@ -248,7 +248,9 @@
   } else if ((lf = x->array()->as_LoadField()) != NULL) {
     ciField* field = lf->field();
     if (field->is_static_constant()) {
-      assert(PatchALot || ScavengeRootsInCode < 2, "Constant field loads are folded during parsing");
+      // Constant field loads are usually folded during parsing.
+      // But it doesn't happen with PatchALot, ScavengeRootsInCode < 2, or when
+      // holder class is being initialized during parsing (for static fields).
       ciObject* c = field->constant_value().as_object();
       if (!c->is_null_object()) {
         set_constant(c->as_array()->length());
--- a/hotspot/src/share/vm/c1/c1_LIR.cpp	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/share/vm/c1/c1_LIR.cpp	Wed Jul 05 22:52:01 2017 +0200
@@ -1413,6 +1413,17 @@
   append(c);
 }
 
+void LIR_List::null_check(LIR_Opr opr, CodeEmitInfo* info, bool deoptimize_on_null) {
+  if (deoptimize_on_null) {
+    // Emit an explicit null check and deoptimize if opr is null
+    CodeStub* deopt = new DeoptimizeStub(info, Deoptimization::Reason_null_check, Deoptimization::Action_none);
+    cmp(lir_cond_equal, opr, LIR_OprFact::oopConst(NULL));
+    branch(lir_cond_equal, T_OBJECT, deopt);
+  } else {
+    // Emit an implicit null check
+    append(new LIR_Op1(lir_null_check, opr, info));
+  }
+}
 
 void LIR_List::cas_long(LIR_Opr addr, LIR_Opr cmp_value, LIR_Opr new_value,
                         LIR_Opr t1, LIR_Opr t2, LIR_Opr result) {
--- a/hotspot/src/share/vm/c1/c1_LIR.hpp	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/share/vm/c1/c1_LIR.hpp	Wed Jul 05 22:52:01 2017 +0200
@@ -2113,7 +2113,7 @@
   void   pack64(LIR_Opr src, LIR_Opr dst) { append(new LIR_Op1(lir_pack64,   src, dst, T_LONG, lir_patch_none, NULL)); }
   void unpack64(LIR_Opr src, LIR_Opr dst) { append(new LIR_Op1(lir_unpack64, src, dst, T_LONG, lir_patch_none, NULL)); }
 
-  void null_check(LIR_Opr opr, CodeEmitInfo* info)         { append(new LIR_Op1(lir_null_check, opr, info)); }
+  void null_check(LIR_Opr opr, CodeEmitInfo* info, bool deoptimize_on_null = false);
   void throw_exception(LIR_Opr exceptionPC, LIR_Opr exceptionOop, CodeEmitInfo* info) {
     append(new LIR_Op2(lir_throw, exceptionPC, exceptionOop, LIR_OprFact::illegalOpr, info));
   }
--- a/hotspot/src/share/vm/c1/c1_LIRGenerator.cpp	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/share/vm/c1/c1_LIRGenerator.cpp	Wed Jul 05 22:52:01 2017 +0200
@@ -1752,8 +1752,10 @@
   if (x->needs_null_check() &&
       (needs_patching ||
        MacroAssembler::needs_explicit_null_check(x->offset()))) {
-    // emit an explicit null check because the offset is too large
-    __ null_check(object.result(), new CodeEmitInfo(info));
+    // Emit an explicit null check because the offset is too large.
+    // If the class is not loaded and the object is NULL, we need to deoptimize to throw a
+    // NoClassDefFoundError in the interpreter instead of an implicit NPE from compiled code.
+    __ null_check(object.result(), new CodeEmitInfo(info), /* deoptimize */ needs_patching);
   }
 
   LIR_Address* address;
@@ -1838,8 +1840,10 @@
       obj = new_register(T_OBJECT);
       __ move(LIR_OprFact::oopConst(NULL), obj);
     }
-    // emit an explicit null check because the offset is too large
-    __ null_check(obj, new CodeEmitInfo(info));
+    // Emit an explicit null check because the offset is too large.
+    // If the class is not loaded and the object is NULL, we need to deoptimize to throw a
+    // NoClassDefFoundError in the interpreter instead of an implicit NPE from compiled code.
+    __ null_check(obj, new CodeEmitInfo(info), /* deoptimize */ needs_patching);
   }
 
   LIR_Opr reg = rlock_result(x, field_type);
--- a/hotspot/src/share/vm/ci/ciEnv.cpp	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/share/vm/ci/ciEnv.cpp	Wed Jul 05 22:52:01 2017 +0200
@@ -101,6 +101,7 @@
   _debug_info = NULL;
   _dependencies = NULL;
   _failure_reason = NULL;
+  _inc_decompile_count_on_failure = true;
   _compilable = MethodCompilable;
   _break_at_compile = false;
   _compiler_data = NULL;
@@ -161,6 +162,7 @@
   _debug_info = NULL;
   _dependencies = NULL;
   _failure_reason = NULL;
+  _inc_decompile_count_on_failure = true;
   _compilable = MethodCompilable_never;
   _break_at_compile = false;
   _compiler_data = NULL;
@@ -902,7 +904,12 @@
     if (deps.is_klass_type())  continue;  // skip klass dependencies
     Klass* witness = deps.check_dependency();
     if (witness != NULL) {
-      record_failure("invalid non-klass dependency");
+      if (deps.type() == Dependencies::call_site_target_value) {
+        _inc_decompile_count_on_failure = false;
+        record_failure("call site target change");
+      } else {
+        record_failure("invalid non-klass dependency");
+      }
       return;
     }
   }
@@ -1017,7 +1024,7 @@
     if (failing()) {
       // While not a true deoptimization, it is a preemptive decompile.
       MethodData* mdo = method()->method_data();
-      if (mdo != NULL) {
+      if (mdo != NULL && _inc_decompile_count_on_failure) {
         mdo->inc_decompile_count();
       }
 
--- a/hotspot/src/share/vm/ci/ciEnv.hpp	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/share/vm/ci/ciEnv.hpp	Wed Jul 05 22:52:01 2017 +0200
@@ -55,6 +55,7 @@
   DebugInformationRecorder* _debug_info;
   Dependencies*    _dependencies;
   const char*      _failure_reason;
+  bool             _inc_decompile_count_on_failure;
   int              _compilable;
   bool             _break_at_compile;
   int              _num_inlined_bytecodes;
--- a/hotspot/src/share/vm/classfile/javaClasses.cpp	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/share/vm/classfile/javaClasses.cpp	Wed Jul 05 22:52:01 2017 +0200
@@ -2269,6 +2269,7 @@
   compute_offset(_monitors_offset,   k, vmSymbols::monitors_name(),    vmSymbols::object_array_signature());
   compute_offset(_locals_offset,     k, vmSymbols::locals_name(),      vmSymbols::object_array_signature());
   compute_offset(_operands_offset,   k, vmSymbols::operands_name(),    vmSymbols::object_array_signature());
+  compute_offset(_mode_offset,       k, vmSymbols::mode_name(),        vmSymbols::int_signature());
 }
 
 void java_lang_reflect_AccessibleObject::compute_offsets() {
@@ -3658,6 +3659,7 @@
 int java_lang_LiveStackFrameInfo::_monitors_offset;
 int java_lang_LiveStackFrameInfo::_locals_offset;
 int java_lang_LiveStackFrameInfo::_operands_offset;
+int java_lang_LiveStackFrameInfo::_mode_offset;
 int java_lang_AssertionStatusDirectives::classes_offset;
 int java_lang_AssertionStatusDirectives::classEnabled_offset;
 int java_lang_AssertionStatusDirectives::packages_offset;
@@ -3728,6 +3730,10 @@
   element->obj_field_put(_operands_offset, value);
 }
 
+void java_lang_LiveStackFrameInfo::set_mode(oop element, int value) {
+  element->int_field_put(_mode_offset, value);
+}
+
 // Support for java Assertions - java_lang_AssertionStatusDirectives.
 
 void java_lang_AssertionStatusDirectives::set_classes(oop o, oop val) {
--- a/hotspot/src/share/vm/classfile/javaClasses.hpp	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/share/vm/classfile/javaClasses.hpp	Wed Jul 05 22:52:01 2017 +0200
@@ -1380,11 +1380,13 @@
   static int _monitors_offset;
   static int _locals_offset;
   static int _operands_offset;
+  static int _mode_offset;
 
  public:
   static void set_monitors(oop info, oop value);
   static void set_locals(oop info, oop value);
   static void set_operands(oop info, oop value);
+  static void set_mode(oop info, int value);
 
   static void compute_offsets();
 
--- a/hotspot/src/share/vm/classfile/vmSymbols.hpp	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/share/vm/classfile/vmSymbols.hpp	Wed Jul 05 22:52:01 2017 +0200
@@ -325,14 +325,8 @@
   template(java_lang_StackStreamFactory_AbstractStackWalker, "java/lang/StackStreamFactory$AbstractStackWalker") \
   template(doStackWalk_signature,                     "(JIIII)Ljava/lang/Object;")                \
   template(asPrimitive_name,                          "asPrimitive")                              \
-  template(asPrimitive_int_signature,                 "(I)Ljava/lang/LiveStackFrame$PrimitiveValue;") \
-  template(asPrimitive_long_signature,                "(J)Ljava/lang/LiveStackFrame$PrimitiveValue;") \
-  template(asPrimitive_short_signature,               "(S)Ljava/lang/LiveStackFrame$PrimitiveValue;") \
-  template(asPrimitive_byte_signature,                "(B)Ljava/lang/LiveStackFrame$PrimitiveValue;") \
-  template(asPrimitive_char_signature,                "(C)Ljava/lang/LiveStackFrame$PrimitiveValue;") \
-  template(asPrimitive_float_signature,               "(F)Ljava/lang/LiveStackFrame$PrimitiveValue;") \
-  template(asPrimitive_double_signature,              "(D)Ljava/lang/LiveStackFrame$PrimitiveValue;") \
-  template(asPrimitive_boolean_signature,             "(Z)Ljava/lang/LiveStackFrame$PrimitiveValue;") \
+  template(asPrimitive_int_signature,                 "(I)Ljava/lang/LiveStackFrame$PrimitiveSlot;") \
+  template(asPrimitive_long_signature,                "(J)Ljava/lang/LiveStackFrame$PrimitiveSlot;") \
                                                                                                   \
   /* common method and field names */                                                             \
   template(object_initializer_name,                   "<init>")                                   \
@@ -444,6 +438,7 @@
   template(monitors_name,                             "monitors")                                 \
   template(locals_name,                               "locals")                                   \
   template(operands_name,                             "operands")                                 \
+  template(mode_name,                                 "mode")                                     \
   template(oop_size_name,                             "oop_size")                                 \
   template(static_oop_field_count_name,               "static_oop_field_count")                   \
   template(protection_domain_name,                    "protection_domain")                        \
--- a/hotspot/src/share/vm/code/codeCache.cpp	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/share/vm/code/codeCache.cpp	Wed Jul 05 22:52:01 2017 +0200
@@ -1211,7 +1211,7 @@
   CompiledMethodIterator iter;
   while(iter.next_alive()) {
     CompiledMethod* nm = iter.method();
-    if (nm->is_marked_for_deoptimization()) {
+    if (nm->is_marked_for_deoptimization() && !nm->is_not_entrant()) {
       nm->make_not_entrant();
     }
   }
--- a/hotspot/src/share/vm/code/nmethod.cpp	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/share/vm/code/nmethod.cpp	Wed Jul 05 22:52:01 2017 +0200
@@ -1146,6 +1146,14 @@
   assert(state == zombie || state == not_entrant, "must be zombie or not_entrant");
   assert(!is_zombie(), "should not already be a zombie");
 
+  if (_state == state) {
+    // Avoid taking the lock if already in required state.
+    // This is safe from races because the state is an end-state,
+    // which the nmethod cannot back out of once entered.
+    // No need for fencing either.
+    return false;
+  }
+
   // Make sure neither the nmethod nor the method is flushed in case of a safepoint in code below.
   nmethodLocker nml(this);
   methodHandle the_method(method());
--- a/hotspot/src/share/vm/gc/g1/heapRegionRemSet.cpp	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/share/vm/gc/g1/heapRegionRemSet.cpp	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2001, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2001, 2017, 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
@@ -711,29 +711,6 @@
   guarantee(G1RSetSparseRegionEntries > 0 && G1RSetRegionEntries > 0 , "Sanity");
 }
 
-#ifndef PRODUCT
-void HeapRegionRemSet::print() {
-  HeapRegionRemSetIterator iter(this);
-  size_t card_index;
-  while (iter.has_next(card_index)) {
-    HeapWord* card_start = _bot->address_for_index(card_index);
-    tty->print_cr("  Card " PTR_FORMAT, p2i(card_start));
-  }
-  if (iter.n_yielded() != occupied()) {
-    tty->print_cr("Yielded disagrees with occupied:");
-    tty->print_cr("  " SIZE_FORMAT_W(6) " yielded (" SIZE_FORMAT_W(6)
-                  " coarse, " SIZE_FORMAT_W(6) " fine).",
-                  iter.n_yielded(),
-                  iter.n_yielded_coarse(), iter.n_yielded_fine());
-    tty->print_cr("  " SIZE_FORMAT_W(6) " occ     (" SIZE_FORMAT_W(6)
-                           " coarse, " SIZE_FORMAT_W(6) " fine).",
-                  occupied(), occ_coarse(), occ_fine());
-  }
-  guarantee(iter.n_yielded() == occupied(),
-            "We should have yielded all the represented cards.");
-}
-#endif
-
 void HeapRegionRemSet::cleanup() {
   SparsePRT::cleanup_all();
 }
@@ -917,10 +894,6 @@
     // Otherwise...
     break;
   }
-  assert(ParallelGCThreads > 1 ||
-         n_yielded() == _hrrs->occupied(),
-         "Should have yielded all the cards in the rem set "
-         "(in the non-par case).");
   return false;
 }
 
--- a/hotspot/src/share/vm/gc/g1/heapRegionRemSet.hpp	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/share/vm/gc/g1/heapRegionRemSet.hpp	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2001, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2001, 2017, 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
@@ -290,8 +290,6 @@
   // consumed by the strong code roots.
   size_t strong_code_roots_mem_size();
 
-  void print() PRODUCT_RETURN;
-
   // Called during a stop-world phase to perform any deferred cleanups.
   static void cleanup();
 
--- a/hotspot/src/share/vm/opto/type.cpp	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/share/vm/opto/type.cpp	Wed Jul 05 22:52:01 2017 +0200
@@ -373,7 +373,7 @@
   if (con_type != NULL && field->is_call_site_target()) {
     ciCallSite* call_site = holder->as_call_site();
     if (!call_site->is_constant_call_site()) {
-      ciMethodHandle* target = call_site->get_target();
+      ciMethodHandle* target = con.as_object()->as_method_handle();
       Compile::current()->dependencies()->assert_call_site_target_value(call_site, target);
     }
   }
--- a/hotspot/src/share/vm/prims/jvmtiExport.cpp	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/share/vm/prims/jvmtiExport.cpp	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 2017, 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
@@ -1230,8 +1230,12 @@
     assert(thread->is_VM_thread(), "wrong thread");
 
     // get JavaThread for whom we are proxy
-    JavaThread *real_thread =
-        (JavaThread *)((VMThread *)thread)->vm_operation()->calling_thread();
+    Thread *calling_thread = ((VMThread *)thread)->vm_operation()->calling_thread();
+    if (!calling_thread->is_Java_thread()) {
+      // cannot post an event to a non-JavaThread
+      return;
+    }
+    JavaThread *real_thread = (JavaThread *)calling_thread;
 
     JvmtiEnvIterator it;
     for (JvmtiEnv* env = it.first(); env != NULL; env = it.next(env)) {
--- a/hotspot/src/share/vm/prims/methodHandles.cpp	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/share/vm/prims/methodHandles.cpp	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2008, 2017, 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
@@ -1208,9 +1208,10 @@
     if (reference_klass != NULL && reference_klass->is_instance_klass()) {
       // Emulate LinkResolver::check_klass_accessability.
       Klass* caller = java_lang_Class::as_Klass(JNIHandles::resolve_non_null(caller_jh));
-      if (Reflection::verify_class_access(caller,
-                                          reference_klass,
-                                          true) != Reflection::ACCESS_OK) {
+      if (caller != SystemDictionary::Object_klass()
+          && Reflection::verify_class_access(caller,
+                                             reference_klass,
+                                             true) != Reflection::ACCESS_OK) {
         THROW_MSG_NULL(vmSymbols::java_lang_InternalError(), reference_klass->external_name());
       }
     }
--- a/hotspot/src/share/vm/prims/stackwalk.cpp	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/share/vm/prims/stackwalk.cpp	Wed Jul 05 22:52:01 2017 +0200
@@ -173,7 +173,11 @@
   }
 }
 
-oop LiveFrameStream::create_primitive_value_instance(StackValueCollection* values, int i, TRAPS) {
+// Create and return a LiveStackFrame.PrimitiveSlot (if needed) for the
+// StackValue at the given index. 'type' is expected to be T_INT, T_LONG,
+// T_OBJECT, or T_CONFLICT.
+oop LiveFrameStream::create_primitive_slot_instance(StackValueCollection* values,
+                                                    int i, BasicType type, TRAPS) {
   Klass* k = SystemDictionary::resolve_or_null(vmSymbols::java_lang_LiveStackFrameInfo(), CHECK_NULL);
   instanceKlassHandle ik (THREAD, k);
 
@@ -182,8 +186,8 @@
   Symbol* signature = NULL;
 
   // ## TODO: type is only available in LocalVariable table, if present.
-  // ## StackValue type is T_INT or T_OBJECT.
-  switch (values->at(i)->type()) {
+  // ## StackValue type is T_INT or T_OBJECT (or converted to T_LONG on 64-bit)
+  switch (type) {
     case T_INT:
       args.push_int(values->int_at(i));
       signature = vmSymbols::asPrimitive_int_signature();
@@ -195,42 +199,26 @@
       break;
 
     case T_FLOAT:
-      args.push_float(values->float_at(i));
-      signature = vmSymbols::asPrimitive_float_signature();
-      break;
-
     case T_DOUBLE:
-      args.push_double(values->double_at(i));
-      signature = vmSymbols::asPrimitive_double_signature();
-      break;
-
     case T_BYTE:
-      args.push_int(values->int_at(i));
-      signature = vmSymbols::asPrimitive_byte_signature();
-      break;
-
     case T_SHORT:
-      args.push_int(values->int_at(i));
-      signature = vmSymbols::asPrimitive_short_signature();
-      break;
-
     case T_CHAR:
-      args.push_int(values->int_at(i));
-      signature = vmSymbols::asPrimitive_char_signature();
-      break;
-
     case T_BOOLEAN:
-      args.push_int(values->int_at(i));
-      signature = vmSymbols::asPrimitive_boolean_signature();
-      break;
+      THROW_MSG_(vmSymbols::java_lang_InternalError(), "Unexpected StackValue type", NULL);
 
     case T_OBJECT:
       return values->obj_at(i)();
 
     case T_CONFLICT:
       // put a non-null slot
-      args.push_int(0);
-      signature = vmSymbols::asPrimitive_int_signature();
+      #ifdef _LP64
+        args.push_long(0);
+        signature = vmSymbols::asPrimitive_long_signature();
+      #else
+        args.push_int(0);
+        signature = vmSymbols::asPrimitive_int_signature();
+      #endif
+
       break;
 
     default: ShouldNotReachHere();
@@ -252,9 +240,19 @@
   objArrayHandle array_h(THREAD, array_oop);
   for (int i = 0; i < values->size(); i++) {
     StackValue* st = values->at(i);
-    oop obj = create_primitive_value_instance(values, i, CHECK_(empty));
-    if (obj != NULL)
+    BasicType type = st->type();
+    int index = i;
+#ifdef _LP64
+    if (type != T_OBJECT && type != T_CONFLICT) {
+        intptr_t ret = st->get_int(); // read full 64-bit slot
+        type = T_LONG;                // treat as long
+        index--;                      // undo +1 in StackValueCollection::long_at
+    }
+#endif
+    oop obj = create_primitive_slot_instance(values, index, type, CHECK_(empty));
+    if (obj != NULL) {
       array_h->obj_at_put(i, obj);
+    }
   }
   return array_h;
 }
@@ -286,6 +284,13 @@
     StackValueCollection* expressions = _jvf->expressions();
     GrowableArray<MonitorInfo*>* monitors = _jvf->monitors();
 
+    int mode = 0;
+    if (_jvf->is_interpreted_frame()) {
+      mode = MODE_INTERPRETED;
+    } else if (_jvf->is_compiled_frame()) {
+      mode = MODE_COMPILED;
+    }
+
     if (!locals->is_empty()) {
       objArrayHandle locals_h = values_to_object_array(locals, CHECK);
       java_lang_LiveStackFrameInfo::set_locals(stackFrame(), locals_h());
@@ -298,6 +303,7 @@
       objArrayHandle monitors_h = monitors_to_object_array(monitors, CHECK);
       java_lang_LiveStackFrameInfo::set_monitors(stackFrame(), monitors_h());
     }
+    java_lang_LiveStackFrameInfo::set_mode(stackFrame(), mode);
   }
 }
 
--- a/hotspot/src/share/vm/prims/stackwalk.hpp	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/src/share/vm/prims/stackwalk.hpp	Wed Jul 05 22:52:01 2017 +0200
@@ -92,11 +92,16 @@
 
 class LiveFrameStream : public BaseFrameStream {
 private:
+  enum {
+    MODE_INTERPRETED = 0x01,
+    MODE_COMPILED    = 0x02
+  };
+
   javaVFrame*           _jvf;
 
   void fill_live_stackframe(Handle stackFrame, const methodHandle& method, TRAPS);
-  static oop create_primitive_value_instance(StackValueCollection* values,
-                                             int i, TRAPS);
+  static oop create_primitive_slot_instance(StackValueCollection* values,
+                                            int i, BasicType type, TRAPS);
   static objArrayHandle monitors_to_object_array(GrowableArray<MonitorInfo*>* monitors,
                                                  TRAPS);
   static objArrayHandle values_to_object_array(StackValueCollection* values, TRAPS);
--- a/hotspot/test/ProblemList.txt	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/ProblemList.txt	Wed Jul 05 22:52:01 2017 +0200
@@ -73,6 +73,7 @@
 
 serviceability/jdwp/AllModulesCommandTest.java 8168478 generic-all
 serviceability/sa/sadebugd/SADebugDTest.java 8163805 generic-all
+serviceability/jvmti/ModuleAwareAgents/ClassFileLoadHook/MAAClassFileLoadHook.java 8173936 generic-all
 
 #############################################################################
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/compiler/c1/TestUnresolvedField.jasm	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,38 @@
+/*
+ * Copyright (c) 2017, 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.
+ *
+ */
+
+public class compiler/c1/TestUnresolvedField version 52:0 {
+    public static Method testGetField:"()V" stack 1 locals 1 {
+        aconst_null;
+        getfield Field T.f:I; // T does not exist
+        return;
+    }
+
+    public static Method testPutField:"()V" stack 2 locals 1 {
+        aconst_null;
+        iconst_0;
+        putfield Field T.f:I; // T does not exist
+        return;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/compiler/c1/TestUnresolvedFieldMain.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,48 @@
+/*
+ * Copyright (c) 2017, 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
+ * @bug 8173373
+ * @compile TestUnresolvedField.jasm
+ * @run main/othervm -XX:TieredStopAtLevel=1 -Xcomp
+ *                   -XX:CompileCommand=compileonly,compiler.c1.TestUnresolvedField::test*
+ *                   compiler.c1.TestUnresolvedFieldMain
+ */
+
+package compiler.c1;
+
+public class TestUnresolvedFieldMain {
+    public static void main(String[] args) {
+        try {
+          TestUnresolvedField.testGetField();
+        } catch (java.lang.NoClassDefFoundError error) {
+          // Expected
+        }
+        try {
+          TestUnresolvedField.testPutField();
+        } catch (java.lang.NoClassDefFoundError error) {
+          // Expected
+        }
+    }
+}
--- a/hotspot/test/compiler/jsr292/ContinuousCallSiteTargetChange.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/compiler/jsr292/ContinuousCallSiteTargetChange.java	Wed Jul 05 22:52:01 2017 +0200
@@ -23,7 +23,6 @@
 
 /**
  * @test
- * @modules java.base/jdk.internal.misc
  * @library /test/lib /
  *
  * @run driver compiler.jsr292.ContinuousCallSiteTargetChange
@@ -31,6 +30,7 @@
 
 package compiler.jsr292;
 
+import jdk.test.lib.Asserts;
 import jdk.test.lib.process.OutputAnalyzer;
 import jdk.test.lib.process.ProcessTools;
 
@@ -39,15 +39,26 @@
 import java.lang.invoke.MethodHandles;
 import java.lang.invoke.MethodType;
 import java.lang.invoke.MutableCallSite;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
 
 public class ContinuousCallSiteTargetChange {
-    static void testServer() throws Exception {
+    static final int ITERATIONS = Integer.parseInt(System.getProperty("iterations", "50"));
+
+    static void runTest(Class<?> test, String... extraArgs) throws Exception {
+        List<String> argsList = new ArrayList<>(
+                List.of("-XX:+IgnoreUnrecognizedVMOptions",
+                    "-XX:PerBytecodeRecompilationCutoff=10", "-XX:PerMethodRecompilationCutoff=10",
+                    "-XX:+PrintCompilation", "-XX:+UnlockDiagnosticVMOptions", "-XX:+PrintInlining"));
+
+        argsList.addAll(Arrays.asList(extraArgs));
+
+        argsList.add(test.getName());
+        argsList.add(Integer.toString(ITERATIONS));
+
         ProcessBuilder pb = ProcessTools.createJavaProcessBuilder(
-                "-XX:+IgnoreUnrecognizedVMOptions",
-                "-server", "-XX:-TieredCompilation", "-Xbatch",
-                "-XX:PerBytecodeRecompilationCutoff=10", "-XX:PerMethodRecompilationCutoff=10",
-                "-XX:+PrintCompilation", "-XX:+UnlockDiagnosticVMOptions", "-XX:+PrintInlining",
-                Test.class.getName(), "100");
+                argsList.toArray(new String[argsList.size()]));
 
         OutputAnalyzer analyzer = new OutputAnalyzer(pb.start());
 
@@ -55,30 +66,42 @@
 
         analyzer.shouldNotContain("made not compilable");
         analyzer.shouldNotContain("decompile_count > PerMethodRecompilationCutoff");
+
     }
 
-    static void testClient() throws Exception {
-        ProcessBuilder pb = ProcessTools.createJavaProcessBuilder(
-                "-XX:+IgnoreUnrecognizedVMOptions",
-                "-client", "-XX:+TieredCompilation", "-XX:TieredStopAtLevel=1", "-Xbatch",
-                "-XX:PerBytecodeRecompilationCutoff=10", "-XX:PerMethodRecompilationCutoff=10",
-                "-XX:+PrintCompilation", "-XX:+UnlockDiagnosticVMOptions", "-XX:+PrintInlining",
-                Test.class.getName(), "100");
+    static void testServer(Class<?> test, String... args) throws Exception {
+        List<String> extraArgsList = new ArrayList<>(
+                List.of("-server", "-XX:-TieredCompilation"));
+        extraArgsList.addAll(Arrays.asList(args));
 
-        OutputAnalyzer analyzer = new OutputAnalyzer(pb.start());
+        runTest(test, extraArgsList.toArray(new String[extraArgsList.size()]));
+    }
 
-        analyzer.shouldHaveExitValue(0);
+    static void testClient(Class<?> test, String... args) throws Exception {
+        List<String> extraArgsList = new ArrayList<>(
+                List.of("-client", "-XX:+TieredCompilation", "-XX:TieredStopAtLevel=1"));
+        extraArgsList.addAll(Arrays.asList(args));
 
-        analyzer.shouldNotContain("made not compilable");
-        analyzer.shouldNotContain("decompile_count > PerMethodRecompilationCutoff");
+        runTest(test, extraArgsList.toArray(new String[extraArgsList.size()]));
     }
 
     public static void main(String[] args) throws Exception {
-        testServer();
-        testClient();
+        testServer(RecompilationTest.class, "-Xbatch");
+        testClient(RecompilationTest.class, "-Xbatch");
+
+        testServer(PingPongTest.class);
+        testClient(PingPongTest.class);
     }
 
-    static class Test {
+    static MethodHandle findStatic(Class<?> cls, String name, MethodType mt) {
+        try {
+            return MethodHandles.lookup().findStatic(cls, name, mt);
+        } catch (Exception e) {
+            throw new Error(e);
+        }
+    }
+
+    static class RecompilationTest {
         static final MethodType mt = MethodType.methodType(void.class);
         static final CallSite cs = new MutableCallSite(mt);
 
@@ -96,7 +119,7 @@
         }
 
         static void iteration() throws Throwable {
-            MethodHandle mh1 = MethodHandles.lookup().findStatic(ContinuousCallSiteTargetChange.Test.class, "f", mt);
+            MethodHandle mh1 = findStatic(RecompilationTest.class, "f", mt);
             cs.setTarget(mh1);
             for (int i = 0; i < 20_000; i++) {
                 test1();
@@ -111,4 +134,38 @@
             }
         }
     }
+
+    static class PingPongTest {
+        static final MethodType mt = MethodType.methodType(void.class);
+        static final CallSite cs = new MutableCallSite(mt);
+
+        static final MethodHandle mh = cs.dynamicInvoker();
+
+        static final MethodHandle ping = findStatic(PingPongTest.class, "ping", mt);
+        static final MethodHandle pong = findStatic(PingPongTest.class, "pong", mt);
+
+        static void ping() {
+            Asserts.assertEQ(cs.getTarget(), ping, "wrong call site target");
+            cs.setTarget(pong);
+        }
+
+        static void pong() {
+            Asserts.assertEQ(cs.getTarget(), pong, "wrong call site target");
+            cs.setTarget(ping);
+        }
+
+        static void iteration() throws Throwable {
+            cs.setTarget(ping);
+            for (int i = 0; i < 20_000; i++) {
+                mh.invokeExact();
+            }
+        }
+
+        public static void main(String[] args) throws Throwable {
+            int iterations = Integer.parseInt(args[0]);
+            for (int i = 0; i < iterations; i++) {
+                iteration();
+            }
+        }
+    }
 }
--- a/hotspot/test/compiler/jvmci/compilerToVM/MaterializeVirtualObjectTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/compiler/jvmci/compilerToVM/MaterializeVirtualObjectTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -44,6 +44,8 @@
  *                   -XX:+UnlockExperimentalVMOptions -XX:+EnableJVMCI
  *                   -XX:CompileCommand=exclude,*::check
  *                   -XX:+DoEscapeAnalysis -XX:-UseCounterDecay
+ *                   -XX:CompileCommand=dontinline,compiler/jvmci/compilerToVM/MaterializeVirtualObjectTest,testFrame
+ *                   -XX:CompileCommand=inline,compiler/jvmci/compilerToVM/MaterializeVirtualObjectTest,recurse
  *                   -Xbatch
  *                   -Dcompiler.jvmci.compilerToVM.MaterializeVirtualObjectTest.invalidate=false
  *                   compiler.jvmci.compilerToVM.MaterializeVirtualObjectTest
@@ -119,14 +121,25 @@
         }
         Asserts.assertTrue(WB.isMethodCompiled(METHOD), getName()
                 + "Method unexpectedly not compiled");
+        Asserts.assertTrue(WB.getMethodCompilationLevel(METHOD) == 4, getName()
+                + "Method not compiled at level 4");
         testFrame("someString", COMPILE_THRESHOLD);
     }
 
     private void testFrame(String str, int iteration) {
         Helper helper = new Helper(str);
-        check(iteration);
+        recurse(2, iteration);
         Asserts.assertTrue((helper.string != null) && (this != null)
-                && (helper != null), getName() + " : some locals are null");
+                           && (helper != null), String.format("%s : some locals are null", getName()));
+    }
+    private void recurse(int depth, int iteration) {
+        if (depth == 0) {
+            check(iteration);
+        } else {
+            Integer s = new Integer(depth);
+            recurse(depth - 1, iteration);
+            Asserts.assertEQ(s.intValue(), depth, String.format("different values: %s != %s", s.intValue(), depth));
+        }
     }
 
     private void check(int iteration) {
--- a/hotspot/test/runtime/LocalLong/LocalLongHelper.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/LocalLong/LocalLongHelper.java	Wed Jul 05 22:52:01 2017 +0200
@@ -30,10 +30,10 @@
 
 public class LocalLongHelper {
     static StackWalker sw;
-    static Method intValue;
+    static Method longValue;
     static Method getLocals;
     static Class<?> primitiveValueClass;
-    static Method primitiveType;
+    static Method primitiveSize;
     static Method getMethodType;
     static Field memberName;
     static Field offset;
@@ -43,27 +43,29 @@
         new LocalLongHelper().longArg(0xC0FFEE, 0x1234567890ABCDEFL);
     }
 
-    // locals[2] contains the high byte of the long argument.
+    // locals[2] contains the unused slot of the long argument.
     public long longArg(int i, long l) throws Throwable {
         List<StackFrame> frames = sw.walk(s -> s.collect(Collectors.toList()));
         Object[] locals = (Object[]) getLocals.invoke(frames.get(0));
 
-        int locals_2 = (int) intValue.invoke(locals[2]);
-        if (locals_2 != 0){
-            throw new RuntimeException("Expected locals_2 == 0");
+        if (8 == (int) primitiveSize.invoke(locals[2])) { // Only test 64-bit
+            long locals_2 = (long) longValue.invoke(locals[2]);
+            if (locals_2 != 0){
+                throw new RuntimeException("Expected locals_2 == 0");
+            }
         }
         return l; // Don't want l to become a dead var
     }
 
     private static void setupReflectionStatics() throws Throwable {
         Class<?> liveStackFrameClass = Class.forName("java.lang.LiveStackFrame");
-        primitiveValueClass = Class.forName("java.lang.LiveStackFrame$PrimitiveValue");
+        primitiveValueClass = Class.forName("java.lang.LiveStackFrame$PrimitiveSlot");
 
         getLocals = liveStackFrameClass.getDeclaredMethod("getLocals");
         getLocals.setAccessible(true);
 
-        intValue = primitiveValueClass.getDeclaredMethod("intValue");
-        intValue.setAccessible(true);
+        longValue = primitiveValueClass.getDeclaredMethod("longValue");
+        longValue.setAccessible(true);
 
         Class<?> stackFrameInfoClass = Class.forName("java.lang.StackFrameInfo");
         memberName = stackFrameInfoClass.getDeclaredField("memberName");
@@ -80,20 +82,8 @@
         f.setAccessible(true);
         Object localsAndOperandsOption = f.get(null);
 
-        primitiveType = primitiveValueClass.getDeclaredMethod("type");
-        primitiveType.setAccessible(true);
-
+        primitiveSize = primitiveValueClass.getDeclaredMethod("size");
+        primitiveSize.setAccessible(true);
         sw = (StackWalker) ewsNI.invoke(null, java.util.Collections.emptySet(), localsAndOperandsOption);
     }
-
-    private static String type(Object o) throws Throwable {
-        if (primitiveValueClass.isInstance(o)) {
-            final char c = (char) primitiveType.invoke(o);
-            return String.valueOf(c);
-        } else if (o != null) {
-            return o.getClass().getName();
-        } else {
-            return "null";
-        }
-    }
 }
--- a/hotspot/test/runtime/modules/AccessCheck/AccessExportTwice.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/AccessExportTwice.java	Wed Jul 05 22:52:01 2017 +0200
@@ -68,7 +68,7 @@
         // Packages:          none
         // Packages exported: none
         ModuleDescriptor descriptor_first_mod =
-                ModuleDescriptor.module("first_mod")
+                ModuleDescriptor.newModule("first_mod")
                         .requires("java.base")
                         .requires("second_mod")
                         .build();
@@ -78,7 +78,7 @@
         // Packages:          p2
         // Packages exported: p2 is exported to first_mod
         ModuleDescriptor descriptor_second_mod =
-                ModuleDescriptor.module("second_mod")
+                ModuleDescriptor.newModule("second_mod")
                         .requires("java.base")
                         .exports("p2", Set.of("first_mod"))
                         .build();
@@ -89,7 +89,7 @@
         // Resolves "first_mod"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("first_mod"));
+                .resolve(finder, ModuleFinder.of(), Set.of("first_mod"));
 
         // Map each module to the same class loader
         Map<String, ClassLoader> map = new HashMap<>();
--- a/hotspot/test/runtime/modules/AccessCheck/AccessReadTwice.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/AccessReadTwice.java	Wed Jul 05 22:52:01 2017 +0200
@@ -66,9 +66,9 @@
         // Packages:          p1, p4
         // Packages exported: none
         ModuleDescriptor descriptor_first_mod =
-                ModuleDescriptor.module("first_mod")
+                ModuleDescriptor.newModule("first_mod")
                         .requires("java.base")
-                        .contains(Set.of("p1", "p4"))
+                        .packages(Set.of("p1", "p4"))
                         .build();
 
         // Define module:     second_mod
@@ -76,7 +76,7 @@
         // Packages:          p2
         // Packages exported: p2 is exported to first_mod
         ModuleDescriptor descriptor_second_mod =
-                ModuleDescriptor.module("second_mod")
+                ModuleDescriptor.newModule("second_mod")
                         .requires("java.base")
                         .exports("p2", Set.of("first_mod"))
                         .build();
@@ -87,7 +87,7 @@
         // Resolves "first_mod" and "second_mod"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("first_mod", "second_mod"));
+                .resolve(finder, ModuleFinder.of(), Set.of("first_mod", "second_mod"));
 
         // Map each module to this class loader
         Map<String, ClassLoader> map = new HashMap<>();
--- a/hotspot/test/runtime/modules/AccessCheck/CheckRead.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/CheckRead.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,8 +25,8 @@
 
 /*
  * @test
- * @summary Test that if module m1 can not read module m2, then class p1.c1
- *          in module m1 can not access p2.c2 in module m2.
+ * @summary Test that if module m1x can not read module m2x, then class p1.c1
+ *          in module m1x can not access p2.c2 in module m2x.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
  * @compile myloaders/MySameClassLoader.java
@@ -47,15 +47,15 @@
 import myloaders.MySameClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> packages p1
-//                  defines m2 --> packages p2
-//                  defines m3 --> packages p3
+// ClassLoader1 --> defines m1x --> packages p1
+//                  defines m2x --> packages p2
+//                  defines m3x --> packages p3
 //
-// m1 can not read m2
-// package p2 in m2 is exported to m1
+// m1x can not read m2x
+// package p2 in m2x is exported to m1x
 //
-// class p1.c1 defined in m1 tries to access p2.c2 defined in m2.
-// Access denied since m1 can not read m2.
+// class p1.c1 defined in m1x tries to access p2.c2 defined in m2x.
+// Access denied since m1x can not read m2x.
 //
 public class CheckRead {
 
@@ -64,65 +64,65 @@
     // publicly defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
-        // Can read:          java.base, m3
+        // Define module:     m1x
+        // Can read:          java.base, m3x
         // Packages:          p1
         // Packages exported: p1 is exported unqualifiedly
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m3")
+                        .requires("m3x")
                         .exports("p1")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p2
-        // Packages exported: p2 is exported to m1
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        // Packages exported: p2 is exported to m1x
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
-                        .exports("p2", Set.of("m1"))
+                        .exports("p2", Set.of("m1x"))
                         .build();
 
-        // Define module:     m3
-        // Can read:          java.base, m2
+        // Define module:     m3x
+        // Can read:          java.base, m2x
         // Packages:          p3
         // Packages exported: none
-        ModuleDescriptor descriptor_m3 =
-                ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor_m3x =
+                ModuleDescriptor.newModule("m3x")
                         .requires("java.base")
-                        .requires("m2")
-                        .contains("p3")
+                        .requires("m2x")
+                        .packages(Set.of("p3"))
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2, descriptor_m3);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x, descriptor_m3x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to differing class loaders for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MySameClassLoader.loader1);
-        map.put("m2", MySameClassLoader.loader1);
-        map.put("m3", MySameClassLoader.loader1);
+        map.put("m1x", MySameClassLoader.loader1);
+        map.put("m2x", MySameClassLoader.loader1);
+        map.put("m3x", MySameClassLoader.loader1);
 
-        // Create Layer that contains m1, m2 and m3
+        // Create Layer that contains m1x, m2x and m3x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MySameClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MySameClassLoader.loader1);
-        assertTrue(layer.findLoader("m3") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m1x") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m3x") == MySameClassLoader.loader1);
         assertTrue(layer.findLoader("java.base") == null);
 
         // now use the same loader to load class p1.c1
         Class p1_c1_class = MySameClassLoader.loader1.loadClass("p1.c1");
         try {
             p1_c1_class.newInstance();
-            throw new RuntimeException("Failed to get IAE (p2 in m2 is exported to m1 but m2 is not readable from m1)");
+            throw new RuntimeException("Failed to get IAE (p2 in m2x is exported to m1x but m2x is not readable from m1x)");
         } catch (IllegalAccessError e) {
             System.out.println(e.getMessage());
             if (!e.getMessage().contains("cannot access")) {
--- a/hotspot/test/runtime/modules/AccessCheck/DiffCL_CheckRead.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/DiffCL_CheckRead.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,8 +25,8 @@
 
 /*
  * @test
- * @summary Test that if module m1 can not read module m2, then class p1.c1
- *          in module m1 can not access p2.c2 in module m2.
+ * @summary Test that if module m1x can not read module m2x, then class p1.c1
+ *          in module m1x can not access p2.c2 in module m2x.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
  * @compile myloaders/MyDiffClassLoader.java
@@ -47,15 +47,15 @@
 import myloaders.MyDiffClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> packages p1
-// ClassLoader2 --> defines m2 --> packages p2
-//                  defines m3 --> packages p3
+// ClassLoader1 --> defines m1x --> packages p1
+// ClassLoader2 --> defines m2x --> packages p2
+//                  defines m3x --> packages p3
 //
-// m1 can not read m2
-// package p2 in m2 is exported to m1
+// m1x can not read m2x
+// package p2 in m2x is exported to m1x
 //
-// class p1.c1 defined in m1 tries to access p2.c2 defined in m2.
-// Access denied since m1 can not read m2.
+// class p1.c1 defined in m1x tries to access p2.c2 defined in m2x.
+// Access denied since m1x can not read m2x.
 //
 public class DiffCL_CheckRead {
 
@@ -64,65 +64,65 @@
     // publicly defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
-        // Can read:          java.base, m3
+        // Define module:     m1x
+        // Can read:          java.base, m3x
         // Packages:          p1
         // Packages exported: p1 is exported unqualifiedly
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m3")
+                        .requires("m3x")
                         .exports("p1")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p2
-        // Packages exported: p2 is exported to m1
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        // Packages exported: p2 is exported to m1x
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
-                        .exports("p2", Set.of("m1"))
+                        .exports("p2", Set.of("m1x"))
                         .build();
 
-        // Define module:     m3
-        // Can read:          java.base, m2
+        // Define module:     m3x
+        // Can read:          java.base, m2x
         // Packages:          p3
         // Packages exported: none
-        ModuleDescriptor descriptor_m3 =
-                ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor_m3x =
+                ModuleDescriptor.newModule("m3x")
                         .requires("java.base")
-                        .requires("m2")
-                        .contains("p3")
+                        .requires("m2x")
+                        .packages(Set.of("p3"))
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2, descriptor_m3);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x, descriptor_m3x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to differing class loaders for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MyDiffClassLoader.loader1);
-        map.put("m2", MyDiffClassLoader.loader2);
-        map.put("m3", MyDiffClassLoader.loader2);
+        map.put("m1x", MyDiffClassLoader.loader1);
+        map.put("m2x", MyDiffClassLoader.loader2);
+        map.put("m3x", MyDiffClassLoader.loader2);
 
-        // Create Layer that contains m1, m2 and m3
+        // Create Layer that contains m1x, m2x and m3x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MyDiffClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MyDiffClassLoader.loader2);
-        assertTrue(layer.findLoader("m3") == MyDiffClassLoader.loader2);
+        assertTrue(layer.findLoader("m1x") == MyDiffClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MyDiffClassLoader.loader2);
+        assertTrue(layer.findLoader("m3x") == MyDiffClassLoader.loader2);
         assertTrue(layer.findLoader("java.base") == null);
 
         // now use the same loader to load class p1.c1
         Class p1_c1_class = MyDiffClassLoader.loader1.loadClass("p1.c1");
         try {
             p1_c1_class.newInstance();
-            throw new RuntimeException("Failed to get IAE (p2 in m2 is exported to m1 but m2 is not readable from m1)");
+            throw new RuntimeException("Failed to get IAE (p2 in m2x is exported to m1x but m2x is not readable from m1x)");
         } catch (IllegalAccessError e) {
             System.out.println(e.getMessage());
             if (!e.getMessage().contains("cannot access")) {
--- a/hotspot/test/runtime/modules/AccessCheck/DiffCL_ExpQualOther.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/DiffCL_ExpQualOther.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,9 +25,9 @@
 
 /*
  * @test
- * @summary Test that if module m1 can read module m2, but package p2 in m2
- *          is exported specifically to module m3, then class p1.c1 in m1 can not
- *          access p2.c2 in m2.
+ * @summary Test that if module m1x can read module m2x, but package p2 in m2x
+ *          is exported specifically to module m3x, then class p1.c1 in m1x can not
+ *          access p2.c2 in m2x.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
  * @compile myloaders/MyDiffClassLoader.java
@@ -48,15 +48,15 @@
 import myloaders.MyDiffClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> packages p1
-// ClassLoader2 --> defines m2 --> packages p2
-//                  defines m3 --> packages p3
+// ClassLoader1 --> defines m1x --> packages p1
+// ClassLoader2 --> defines m2x --> packages p2
+//                  defines m3x --> packages p3
 //
-// m1 can read m2
-// package p2 in m2 is exported to m3
+// m1x can read m2x
+// package p2 in m2x is exported to m3x
 //
-// class p1.c1 defined in m1 tries to access p2.c2 defined in m2
-// Access denied since although m1 can read m2, p2 is exported only to m3.
+// class p1.c1 defined in m1x tries to access p2.c2 defined in m2x
+// Access denied since although m1x can read m2x, p2 is exported only to m3x.
 //
 public class DiffCL_ExpQualOther {
 
@@ -65,66 +65,66 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
-        // Can read:          java.base, m2, m3
+        // Define module:     m1x
+        // Can read:          java.base, m2x, m3x
         // Packages:          p1
         // Packages exported: p1 is exported unqualifiedly
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
-                        .requires("m3")
+                        .requires("m2x")
+                        .requires("m3x")
                         .exports("p1")
                         .build();
 
-        // Define module:     m2
-        // Can read:          java.base, m3
+        // Define module:     m2x
+        // Can read:          java.base, m3x
         // Packages:          p2
-        // Packages exported: p2 is exported to m3
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        // Packages exported: p2 is exported to m3x
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
-                        .exports("p2", Set.of("m3"))
+                        .exports("p2", Set.of("m3x"))
                         .build();
 
-        // Define module:     m3
-        // Can read:          java.base, m2
+        // Define module:     m3x
+        // Can read:          java.base, m2x
         // Packages:          p3
         // Packages exported: none
-        ModuleDescriptor descriptor_m3 =
-                ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor_m3x =
+                ModuleDescriptor.newModule("m3x")
                         .requires("java.base")
-                        .requires("m2")
-                        .contains("p3")
+                        .requires("m2x")
+                        .packages(Set.of("p3"))
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2, descriptor_m3);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x, descriptor_m3x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to differing class loaders for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MyDiffClassLoader.loader1);
-        map.put("m2", MyDiffClassLoader.loader2);
-        map.put("m3", MyDiffClassLoader.loader2);
+        map.put("m1x", MyDiffClassLoader.loader1);
+        map.put("m2x", MyDiffClassLoader.loader2);
+        map.put("m3x", MyDiffClassLoader.loader2);
 
-        // Create Layer that contains m1 & m2
+        // Create Layer that contains m1x & m2x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MyDiffClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MyDiffClassLoader.loader2);
-        assertTrue(layer.findLoader("m3") == MyDiffClassLoader.loader2);
+        assertTrue(layer.findLoader("m1x") == MyDiffClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MyDiffClassLoader.loader2);
+        assertTrue(layer.findLoader("m3x") == MyDiffClassLoader.loader2);
         assertTrue(layer.findLoader("java.base") == null);
 
         // now use the same loader to load class p1.c1
         Class p1_c1_class = MyDiffClassLoader.loader1.loadClass("p1.c1");
         try {
             p1_c1_class.newInstance();
-            throw new RuntimeException("Failed to get IAE (p2 in m2 is exported to m3 not to m1)");
+            throw new RuntimeException("Failed to get IAE (p2 in m2x is exported to m3x not to m1x)");
         } catch (IllegalAccessError e) {
             System.out.println(e.getMessage());
             if (!e.getMessage().contains("does not export")) {
--- a/hotspot/test/runtime/modules/AccessCheck/DiffCL_ExpQualToM1.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/DiffCL_ExpQualToM1.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,8 +25,8 @@
 
 /*
  * @test
- * @summary class p1.c1 defined in m1 tries to access p2.c2 defined in m2.
- *          Access allowed since m1 can read m2 and package p2 is exported to m1.
+ * @summary class p1.c1 defined in m1x tries to access p2.c2 defined in m2x.
+ *          Access allowed since m1x can read m2x and package p2 is exported to m1x.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
  * @compile myloaders/MyDiffClassLoader.java
@@ -47,14 +47,14 @@
 import myloaders.MyDiffClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> packages p1
-// ClassLoader2 --> defines m2 --> packages p2
+// ClassLoader1 --> defines m1x --> packages p1
+// ClassLoader2 --> defines m2x --> packages p2
 //
-// m1 can read m2
-// package p2 in m2 is exported to m1
+// m1x can read m2x
+// package p2 in m2x is exported to m1x
 //
-// class p1.c1 defined in m1 tries to access p2.c2 defined in m2
-// Access allowed since m1 can read m2 and package p2 is exported to m1.
+// class p1.c1 defined in m1x tries to access p2.c2 defined in m2x
+// Access allowed since m1x can read m2x and package p2 is exported to m1x.
 //
 public class DiffCL_ExpQualToM1 {
 
@@ -63,45 +63,45 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
-        // Can read:          java.base, m2
+        // Define module:     m1x
+        // Can read:          java.base, m2x
         // Packages:          p1
         // Packages exported: p1 is exported to unqualifiedly
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
+                        .requires("m2x")
                         .exports("p1")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p2
-        // Packages exported: package p2 is exported to m1
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        // Packages exported: package p2 is exported to m1x
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
-                        .exports("p2", Set.of("m1"))
+                        .exports("p2", Set.of("m1x"))
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to differing class loaders for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MyDiffClassLoader.loader1);
-        map.put("m2", MyDiffClassLoader.loader2);
+        map.put("m1x", MyDiffClassLoader.loader1);
+        map.put("m2x", MyDiffClassLoader.loader2);
 
-        // Create Layer that contains m1 & m2
+        // Create Layer that contains m1x & m2x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MyDiffClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MyDiffClassLoader.loader2);
+        assertTrue(layer.findLoader("m1x") == MyDiffClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MyDiffClassLoader.loader2);
         assertTrue(layer.findLoader("java.base") == null);
 
         // now use the same loader to load class p1.c1
@@ -109,7 +109,7 @@
         try {
             p1_c1_class.newInstance();
         } catch (IllegalAccessError e) {
-            throw new RuntimeException("Test Failed, an IAE should not be thrown since p2 is exported qualifiedly to m1");
+            throw new RuntimeException("Test Failed, an IAE should not be thrown since p2 is exported qualifiedly to m1x");
         }
     }
 
--- a/hotspot/test/runtime/modules/AccessCheck/DiffCL_ExpUnqual.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/DiffCL_ExpUnqual.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,8 +25,8 @@
 
 /*
  * @test
- * @summary Test that if module m1 can read module m2, and package p2 in m2 is
- *          exported unqualifiedly, then class p1.c1 in m1 can read p2.c2 in m2.
+ * @summary Test that if module m1x can read module m2x, and package p2 in m2x is
+ *          exported unqualifiedly, then class p1.c1 in m1x can read p2.c2 in m2x.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
  * @compile myloaders/MyDiffClassLoader.java
@@ -47,14 +47,14 @@
 import myloaders.MyDiffClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> packages p1
-// ClassLoader2 --> defines m2 --> packages p2
+// ClassLoader1 --> defines m1x --> packages p1
+// ClassLoader2 --> defines m2x --> packages p2
 //
-// m1 can read m2
-// package p2 in m2 is exported to m1
+// m1x can read m2x
+// package p2 in m2x is exported to m1x
 //
-// class p1.c1 defined in m1 tries to access p2.c2 defined in m2
-// Access allowed since m1 can read m2 and package p2 is exported
+// class p1.c1 defined in m1x tries to access p2.c2 defined in m2x
+// Access allowed since m1x can read m2x and package p2 is exported
 // unqualifiedly.
 //
 public class DiffCL_ExpUnqual {
@@ -64,45 +64,45 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
-        // Can read:          java.base, m2
+        // Define module:     m1x
+        // Can read:          java.base, m2x
         // Packages:          p1
         // Packages exported: p1 is exported unqualifiedly
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
+                        .requires("m2x")
                         .exports("p1")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p2
-        // Packages exported: package p2 is exported to m1
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        // Packages exported: package p2 is exported to m1x
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
                         .exports("p2")
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to differing class loaders for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MyDiffClassLoader.loader1);
-        map.put("m2", MyDiffClassLoader.loader2);
+        map.put("m1x", MyDiffClassLoader.loader1);
+        map.put("m2x", MyDiffClassLoader.loader2);
 
-        // Create Layer that contains m1 & m2
+        // Create Layer that contains m1x & m2x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MyDiffClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MyDiffClassLoader.loader2);
+        assertTrue(layer.findLoader("m1x") == MyDiffClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MyDiffClassLoader.loader2);
         assertTrue(layer.findLoader("java.base") == null);
 
         // now use the same loader to load class p1.c1
@@ -110,7 +110,7 @@
         try {
             p1_c1_class.newInstance();
         } catch (IllegalAccessError e) {
-            throw new RuntimeException("Test Failed, an IAE should not be thrown since p2 is exported qualifiedly to m1");
+            throw new RuntimeException("Test Failed, an IAE should not be thrown since p2 is exported qualifiedly to m1x");
         }
     }
 
--- a/hotspot/test/runtime/modules/AccessCheck/DiffCL_PkgNotExp.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/DiffCL_PkgNotExp.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,8 +25,8 @@
 
 /*
  * @test
- * @summary Test that if module m1 can read module m2, but package p2 in m2 is not
- *          exported, then class p1.c1 in m1 can not read p2.c2 in m2.
+ * @summary Test that if module m1x can read module m2x, but package p2 in m2x is not
+ *          exported, then class p1.c1 in m1x can not read p2.c2 in m2x.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
  * @compile myloaders/MyDiffClassLoader.java
@@ -47,13 +47,13 @@
 import myloaders.MyDiffClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> packages p1
-// ClassLoader2 --> defines m2 --> packages p2
+// ClassLoader1 --> defines m1x --> packages p1
+// ClassLoader2 --> defines m2x --> packages p2
 //
-// m1 can read m2
-// package p2 in m2 is not exported
+// m1x can read m2x
+// package p2 in m2x is not exported
 //
-// class p1.c1 defined in m1 tries to access p2.c2 defined in m2
+// class p1.c1 defined in m1x tries to access p2.c2 defined in m2x
 // Access denied since p2 is not exported.
 //
 public class DiffCL_PkgNotExp {
@@ -63,52 +63,52 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
-        // Can read:          java.base, m2
+        // Define module:     m1x
+        // Can read:          java.base, m2x
         // Packages:          p1
         // Packages exported: p1 is exported unqualifiedly
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
+                        .requires("m2x")
                         .exports("p1")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p2
         // Packages exported: none
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
-                        .contains("p2")
+                        .packages(Set.of("p2"))
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to differing class loaders for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MyDiffClassLoader.loader1);
-        map.put("m2", MyDiffClassLoader.loader2);
+        map.put("m1x", MyDiffClassLoader.loader1);
+        map.put("m2x", MyDiffClassLoader.loader2);
 
-        // Create Layer that contains m1 & m2
+        // Create Layer that contains m1x & m2x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MyDiffClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MyDiffClassLoader.loader2);
+        assertTrue(layer.findLoader("m1x") == MyDiffClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MyDiffClassLoader.loader2);
         assertTrue(layer.findLoader("java.base") == null);
 
         // now use the same loader to load class p1.c1
         Class p1_c1_class = MyDiffClassLoader.loader1.loadClass("p1.c1");
         try {
             p1_c1_class.newInstance();
-            throw new RuntimeException("Failed to get IAE (p2 in m2 is not exported)");
+            throw new RuntimeException("Failed to get IAE (p2 in m2x is not exported)");
         } catch (IllegalAccessError e) {
           System.out.println(e.getMessage());
           if (!e.getMessage().contains("does not export")) {
--- a/hotspot/test/runtime/modules/AccessCheck/DiffCL_Umod.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/DiffCL_Umod.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,7 +25,7 @@
 
 /*
  * @test
- * @summary class p1.c1 defined in m1 tries to access p2.c2 defined in unnamed module.
+ * @summary class p1.c1 defined in m1x tries to access p2.c2 defined in unnamed module.
  * @library /test/lib
  * @modules java.base/jdk.internal.misc
  * @modules java.base/jdk.internal.module
@@ -50,10 +50,10 @@
 import myloaders.MyDiffClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> packages p1
-//                  package p1 in m1 is exported unqualifiedly
+// ClassLoader1 --> defines m1x --> packages p1
+//                  package p1 in m1x is exported unqualifiedly
 //
-// class p1.c1 defined in m1 tries to access p2.c2 defined in
+// class p1.c1 defined in m1x tries to access p2.c2 defined in
 // in unnamed module.
 //
 // Three access attempts occur in this test:
@@ -62,7 +62,7 @@
 //   2. In this scenario a strict module establishes readability
 //      to the particular unnamed module it is trying to access.
 //      Access is allowed.
-//   3. Module m1 in the test_looseModuleLayer() method
+//   3. Module m1x in the test_looseModuleLayer() method
 //      is transitioned to a loose module, access
 //      to all unnamed modules is allowed.
 //
@@ -71,41 +71,41 @@
  // Create Layers over the boot layer to test different
  // accessing scenarios of a named module to an unnamed module.
 
- // Module m1 is a strict module and has not established
+ // Module m1x is a strict module and has not established
  // readability to an unnamed module that p2.c2 is defined in.
  public void test_strictModuleLayer() throws Throwable {
 
-     // Define module:     m1
+     // Define module:     m1x
      // Can read:          java.base
      // Packages:          p1
      // Packages exported: p1 is exported unqualifiedly
-     ModuleDescriptor descriptor_m1 =
-             ModuleDescriptor.module("m1")
+     ModuleDescriptor descriptor_m1x =
+             ModuleDescriptor.newModule("m1x")
                      .requires("java.base")
                      .exports("p1")
                      .build();
 
      // Set up a ModuleFinder containing all modules for this layer.
-     ModuleFinder finder = ModuleLibrary.of(descriptor_m1);
+     ModuleFinder finder = ModuleLibrary.of(descriptor_m1x);
 
-     // Resolves "m1"
+     // Resolves "m1x"
      Configuration cf = Layer.boot()
              .configuration()
-             .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+             .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
      MyDiffClassLoader.loader1 = new MyDiffClassLoader();
      MyDiffClassLoader.loader2 = new MyDiffClassLoader();
 
-     // map module m1 to class loader.
+     // map module m1x to class loader.
      // class c2 will be loaded in an unnamed module/loader2
      // to achieve differing class loaders.
      Map<String, ClassLoader> map = new HashMap<>();
-     map.put("m1", MyDiffClassLoader.loader1);
+     map.put("m1x", MyDiffClassLoader.loader1);
 
-     // Create Layer that contains m1
+     // Create Layer that contains m1x
      Layer layer = Layer.boot().defineModules(cf, map::get);
 
-     assertTrue(layer.findLoader("m1") == MyDiffClassLoader.loader1);
+     assertTrue(layer.findLoader("m1x") == MyDiffClassLoader.loader1);
      assertTrue(layer.findLoader("java.base") == null);
 
      // now use the same loader to load class p1.c1
@@ -114,109 +114,109 @@
      // Attempt access
      try {
          p1_c1_class.newInstance();
-         throw new RuntimeException("Test Failed, strict module m1 should not be able " +
+         throw new RuntimeException("Test Failed, strict module m1x should not be able " +
                                     "to access public type p2.c2 defined in unnamed module");
      } catch (IllegalAccessError e) {
      }
 }
 
- // Module m1 is a strict module and has established
+ // Module m1x is a strict module and has established
  // readability to an unnamed module that p2.c2 is defined in.
  public void test_strictModuleUnnamedReadableLayer() throws Throwable {
 
-     // Define module:     m1
+     // Define module:     m1x
      // Can read:          java.base
      // Packages:          p1
      // Packages exported: p1 is exported unqualifiedly
-     ModuleDescriptor descriptor_m1 =
-             ModuleDescriptor.module("m1")
+     ModuleDescriptor descriptor_m1x =
+             ModuleDescriptor.newModule("m1x")
                      .requires("java.base")
                      .exports("p1")
                      .build();
 
      // Set up a ModuleFinder containing all modules for this layer.
-     ModuleFinder finder = ModuleLibrary.of(descriptor_m1);
+     ModuleFinder finder = ModuleLibrary.of(descriptor_m1x);
 
-     // Resolves "m1"
+     // Resolves "m1x"
      Configuration cf = Layer.boot()
              .configuration()
-             .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+             .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
      MyDiffClassLoader.loader1 = new MyDiffClassLoader();
      MyDiffClassLoader.loader2 = new MyDiffClassLoader();
 
-     // map module m1 to class loader.
+     // map module m1x to class loader.
      // class c2 will be loaded in an unnamed module/loader2
      // to achieve differing class loaders.
      Map<String, ClassLoader> map = new HashMap<>();
-     map.put("m1", MyDiffClassLoader.loader1);
+     map.put("m1x", MyDiffClassLoader.loader1);
 
-     // Create Layer that contains m1
+     // Create Layer that contains m1x
      Layer layer = Layer.boot().defineModules(cf, map::get);
 
-     assertTrue(layer.findLoader("m1") == MyDiffClassLoader.loader1);
+     assertTrue(layer.findLoader("m1x") == MyDiffClassLoader.loader1);
      assertTrue(layer.findLoader("java.base") == null);
 
      // now use the same loader to load class p1.c1ReadEdgeDiffLoader
      Class p1_c1_class = MyDiffClassLoader.loader1.loadClass("p1.c1ReadEdgeDiffLoader");
 
      try {
-        // Read edge between m1 and the unnamed module that loads p2.c2 is established in
+        // Read edge between m1x and the unnamed module that loads p2.c2 is established in
         // c1ReadEdgeDiffLoader's ctor before attempting access.
         p1_c1_class.newInstance();
      } catch (IllegalAccessError e) {
-         throw new RuntimeException("Test Failed, module m1 has established readability to p2/c2 loader's " +
+         throw new RuntimeException("Test Failed, module m1x has established readability to p2/c2 loader's " +
                                     "unnamed module, access should be allowed: " + e.getMessage());
      }
  }
 
- // Module m1 is a loose module and thus can read all unnamed modules.
+ // Module m1x is a loose module and thus can read all unnamed modules.
  public void test_looseModuleLayer() throws Throwable {
 
-     // Define module:     m1
+     // Define module:     m1x
      // Can read:          java.base
      // Packages:          p1
      // Packages exported: p1 is exported unqualifiedly
-     ModuleDescriptor descriptor_m1 =
-             ModuleDescriptor.module("m1")
+     ModuleDescriptor descriptor_m1x =
+             ModuleDescriptor.newModule("m1x")
                      .requires("java.base")
                      .exports("p1")
                      .build();
 
      // Set up a ModuleFinder containing all modules for this layer.
-     ModuleFinder finder = ModuleLibrary.of(descriptor_m1);
+     ModuleFinder finder = ModuleLibrary.of(descriptor_m1x);
 
-     // Resolves "m1"
+     // Resolves "m1x"
      Configuration cf = Layer.boot()
              .configuration()
-             .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+             .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
      MyDiffClassLoader.loader1 = new MyDiffClassLoader();
      MyDiffClassLoader.loader2 = new MyDiffClassLoader();
 
-     // map module m1 to class loader.
+     // map module m1x to class loader.
      // class c2 will be loaded in an unnamed module/loader2
      // to achieve differing class loaders.
      Map<String, ClassLoader> map = new HashMap<>();
-     map.put("m1", MyDiffClassLoader.loader1);
+     map.put("m1x", MyDiffClassLoader.loader1);
 
-     // Create Layer that contains m1
+     // Create Layer that contains m1x
      Layer layer = Layer.boot().defineModules(cf, map::get);
 
-     assertTrue(layer.findLoader("m1") == MyDiffClassLoader.loader1);
+     assertTrue(layer.findLoader("m1x") == MyDiffClassLoader.loader1);
      assertTrue(layer.findLoader("java.base") == null);
 
      // now use the same loader to load class p1.c1Loose
      Class p1_c1_class = MyDiffClassLoader.loader1.loadClass("p1.c1Loose");
 
-     // change m1 to read all unnamed modules
-     Module m1 = layer.findModule("m1").get();
-     jdk.internal.module.Modules.addReadsAllUnnamed(m1);
+     // change m1x to read all unnamed modules
+     Module m1x = layer.findModule("m1x").get();
+     jdk.internal.module.Modules.addReadsAllUnnamed(m1x);
 
      try {
          p1_c1_class.newInstance();
      } catch (IllegalAccessError e) {
-         throw new RuntimeException("Test Failed, loose module m1 should be able to access " +
+         throw new RuntimeException("Test Failed, loose module m1x should be able to access " +
                                     "public type p2.c2 defined in unnamed module: " + e.getMessage());
      }
  }
--- a/hotspot/test/runtime/modules/AccessCheck/DiffCL_UmodUpkg.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/DiffCL_UmodUpkg.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,7 +25,7 @@
 
 /*
  * @test
- * @summary class p3.c3 defined in module m1 tries to access c4 defined in an unnamed package
+ * @summary class p3.c3 defined in module m1x tries to access c4 defined in an unnamed package
  *          and an unnamed module.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
@@ -48,10 +48,10 @@
 import myloaders.MyDiffClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> packages p3
-//                  package p3 in m1 is exported unqualifiedly
+// ClassLoader1 --> defines m1x --> packages p3
+//                  package p3 in m1x is exported unqualifiedly
 //
-// class p3.c3 defined in m1 tries to access c4 defined in
+// class p3.c3 defined in m1x tries to access c4 defined in
 // in unnamed module.
 //
 // Two access attempts occur in this test:
@@ -66,41 +66,41 @@
  // Create Layers over the boot layer to test different
  // accessing scenarios of a named module to an unnamed module.
 
- // Module m1 is a strict module and has not established
+ // Module m1x is a strict module and has not established
  // readability to an unnamed module that c4 is defined in.
  public void test_strictModuleLayer() throws Throwable {
 
-     // Define module:     m1
+     // Define module:     m1x
      // Can read:          java.base
      // Packages:          p3
      // Packages exported: p3 is exported unqualifiedly
-     ModuleDescriptor descriptor_m1 =
-             ModuleDescriptor.module("m1")
+     ModuleDescriptor descriptor_m1x =
+             ModuleDescriptor.newModule("m1x")
                      .requires("java.base")
                      .exports("p3")
                      .build();
 
      // Set up a ModuleFinder containing all modules for this layer.
-     ModuleFinder finder = ModuleLibrary.of(descriptor_m1);
+     ModuleFinder finder = ModuleLibrary.of(descriptor_m1x);
 
-     // Resolves "m1"
+     // Resolves "m1x"
      Configuration cf = Layer.boot()
              .configuration()
-             .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+             .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
      MyDiffClassLoader.loader1 = new MyDiffClassLoader();
      MyDiffClassLoader.loader2 = new MyDiffClassLoader();
 
-     // map module m1 to class loader.
+     // map module m1x to class loader.
      // class c2 will be loaded in an unnamed module/loader2
      // to achieve differing class loaders.
      Map<String, ClassLoader> map = new HashMap<>();
-     map.put("m1", MyDiffClassLoader.loader1);
+     map.put("m1x", MyDiffClassLoader.loader1);
 
-     // Create Layer that contains m1
+     // Create Layer that contains m1x
      Layer layer = Layer.boot().defineModules(cf, map::get);
 
-     assertTrue(layer.findLoader("m1") == MyDiffClassLoader.loader1);
+     assertTrue(layer.findLoader("m1x") == MyDiffClassLoader.loader1);
      assertTrue(layer.findLoader("java.base") == null);
 
      // now use the same loader to load class p3.c3
@@ -109,58 +109,58 @@
      // Attempt access
      try {
          p3_c3_class.newInstance();
-         throw new RuntimeException("Test Failed, strict module m1 should not be able to access " +
+         throw new RuntimeException("Test Failed, strict module m1x should not be able to access " +
                                     "public type c4 defined in unnamed module");
      } catch (IllegalAccessError e) {
      }
 }
 
- // Module m1 is a strict module and has established
+ // Module m1x is a strict module and has established
  // readability to an unnamed module that c4 is defined in.
  public void test_strictModuleUnnamedReadableLayer() throws Throwable {
 
-     // Define module:     m1
+     // Define module:     m1x
      // Can read:          java.base
      // Packages:          p3
      // Packages exported: p3 is exported unqualifiedly
-     ModuleDescriptor descriptor_m1 =
-             ModuleDescriptor.module("m1")
+     ModuleDescriptor descriptor_m1x =
+             ModuleDescriptor.newModule("m1x")
                      .requires("java.base")
                      .exports("p3")
                      .build();
 
      // Set up a ModuleFinder containing all modules for this layer.
-     ModuleFinder finder = ModuleLibrary.of(descriptor_m1);
+     ModuleFinder finder = ModuleLibrary.of(descriptor_m1x);
 
-     // Resolves "m1"
+     // Resolves "m1x"
      Configuration cf = Layer.boot()
              .configuration()
-             .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+             .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
      MyDiffClassLoader.loader1 = new MyDiffClassLoader();
      MyDiffClassLoader.loader2 = new MyDiffClassLoader();
 
-     // map module m1 to class loader.
+     // map module m1x to class loader.
      // class c2 will be loaded in an unnamed module/loader2
      // to achieve differing class loaders.
      Map<String, ClassLoader> map = new HashMap<>();
-     map.put("m1", MyDiffClassLoader.loader1);
+     map.put("m1x", MyDiffClassLoader.loader1);
 
-     // Create Layer that contains m1
+     // Create Layer that contains m1x
      Layer layer = Layer.boot().defineModules(cf, map::get);
 
-     assertTrue(layer.findLoader("m1") == MyDiffClassLoader.loader1);
+     assertTrue(layer.findLoader("m1x") == MyDiffClassLoader.loader1);
      assertTrue(layer.findLoader("java.base") == null);
 
      // now use the same loader to load class p3.c3ReadEdgeDiffLoader
      Class p3_c3_class = MyDiffClassLoader.loader1.loadClass("p3.c3ReadEdgeDiffLoader");
 
      try {
-        // Read edge between m1 and the unnamed module that loads c4 is established in
+        // Read edge between m1x and the unnamed module that loads c4 is established in
         // C3ReadEdgeDiffLoader's ctor before attempting access.
         p3_c3_class.newInstance();
      } catch (IllegalAccessError e) {
-         throw new RuntimeException("Test Failed, module m1 has established readability to " +
+         throw new RuntimeException("Test Failed, module m1x has established readability to " +
                                     "c4 loader's unnamed module, access should be allowed: " + e.getMessage());
      }
  }
--- a/hotspot/test/runtime/modules/AccessCheck/ExpQualOther.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/ExpQualOther.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,9 +25,9 @@
 
 /*
  * @test
- * @summary Test that if module m1 can read module m2, but package p2 in m2
- *          is exported specifically to module m3, then class p1.c1 in m1 can not
- *          access p2.c2 in m2.
+ * @summary Test that if module m1x can read module m2x, but package p2 in m2x
+ *          is exported specifically to module m3x, then class p1.c1 in m1x can not
+ *          access p2.c2 in m2x.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
  * @compile myloaders/MySameClassLoader.java
@@ -48,15 +48,15 @@
 import myloaders.MySameClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> packages p1
-//                  defines m2 --> packages p2
-//                  defines m3 --> packages p3
+// ClassLoader1 --> defines m1x --> packages p1
+//                  defines m2x --> packages p2
+//                  defines m3x --> packages p3
 //
-// m1 can read m2
-// package p2 in m2 is exported to m3
+// m1x can read m2x
+// package p2 in m2x is exported to m3x
 //
-// class p1.c1 defined in m1 tries to access p2.c2 defined in m2
-// Access denied since although m1 can read m2, p2 is exported only to m3.
+// class p1.c1 defined in m1x tries to access p2.c2 defined in m2x
+// Access denied since although m1x can read m2x, p2 is exported only to m3x.
 //
 public class ExpQualOther {
 
@@ -65,66 +65,66 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
-        // Can read:          java.base, m2, m3
+        // Define module:     m1x
+        // Can read:          java.base, m2x, m3x
         // Packages:          p1
         // Packages exported: p1 is exported unqualifiedly
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
-                        .requires("m3")
+                        .requires("m2x")
+                        .requires("m3x")
                         .exports("p1")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p2
-        // Packages exported: p2 is exported to m3
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        // Packages exported: p2 is exported to m3x
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
-                        .exports("p2", Set.of("m3"))
+                        .exports("p2", Set.of("m3x"))
                         .build();
 
-        // Define module:     m3
-        // Can read:          java.base, m2
+        // Define module:     m3x
+        // Can read:          java.base, m2x
         // Packages:          p3
         // Packages exported: none
-        ModuleDescriptor descriptor_m3 =
-                ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor_m3x =
+                ModuleDescriptor.newModule("m3x")
                         .requires("java.base")
-                        .requires("m2")
-                        .contains("p3")
+                        .requires("m2x")
+                        .packages(Set.of("p3"))
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2, descriptor_m3);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x, descriptor_m3x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to differing class loaders for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MySameClassLoader.loader1);
-        map.put("m2", MySameClassLoader.loader1);
-        map.put("m3", MySameClassLoader.loader1);
+        map.put("m1x", MySameClassLoader.loader1);
+        map.put("m2x", MySameClassLoader.loader1);
+        map.put("m3x", MySameClassLoader.loader1);
 
-        // Create Layer that contains m1 & m2
+        // Create Layer that contains m1x & m2x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MySameClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MySameClassLoader.loader1);
-        assertTrue(layer.findLoader("m3") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m1x") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m3x") == MySameClassLoader.loader1);
         assertTrue(layer.findLoader("java.base") == null);
 
         // now use the same loader to load class p1.c1
         Class p1_c1_class = MySameClassLoader.loader1.loadClass("p1.c1");
         try {
             p1_c1_class.newInstance();
-            throw new RuntimeException("Failed to get IAE (p2 in m2 is exported to m3 not to m1)");
+            throw new RuntimeException("Failed to get IAE (p2 in m2x is exported to m3x not to m1x)");
         } catch (IllegalAccessError e) {
             System.out.println(e.getMessage());
             if (!e.getMessage().contains("does not export")) {
--- a/hotspot/test/runtime/modules/AccessCheck/ExpQualToM1.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/ExpQualToM1.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,8 +25,8 @@
 
 /*
  * @test
- * @summary Test that if module m1 can read module m2, AND package p2 in m2 is
- *          exported qualifiedly to m1, then class p1.c1 in m1 can read p2.c2 in m2.
+ * @summary Test that if module m1x can read module m2x, AND package p2 in m2x is
+ *          exported qualifiedly to m1x, then class p1.c1 in m1x can read p2.c2 in m2x.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
  * @compile myloaders/MySameClassLoader.java
@@ -53,52 +53,52 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
-        // Can read:          java.base, m2
+        // Define module:     m1x
+        // Can read:          java.base, m2x
         // Packages:          p1
         // Packages exported: p1 is exported unqualifiedly
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
+                        .requires("m2x")
                         .exports("p1")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p2
-        // Packages exported: p2 is exported qualifiedly to m1
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        // Packages exported: p2 is exported qualifiedly to m1x
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
-                        .exports("p2", Set.of("m1"))
+                        .exports("p2", Set.of("m1x"))
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to the same class loader for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MySameClassLoader.loader1);
-        map.put("m2", MySameClassLoader.loader1);
+        map.put("m1x", MySameClassLoader.loader1);
+        map.put("m2x", MySameClassLoader.loader1);
 
-        // Create Layer that contains m1 & m2
+        // Create Layer that contains m1x & m2x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MySameClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m1x") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MySameClassLoader.loader1);
 
         // now use the same loader to load class p1.c1
         Class p1_c1_class = MySameClassLoader.loader1.loadClass("p1.c1");
         try {
             p1_c1_class.newInstance();
         } catch (IllegalAccessError e) {
-            throw new RuntimeException("Test Failed, an IAE should not be thrown since p2 is exported qualifiedly to m1");
+            throw new RuntimeException("Test Failed, an IAE should not be thrown since p2 is exported qualifiedly to m1x");
         }
     }
 
--- a/hotspot/test/runtime/modules/AccessCheck/ExpUnqual.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/ExpUnqual.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,8 +25,8 @@
 
 /*
  * @test
- * @summary Test that if module m1 can read module m2, AND package p2 in module2 is
- *          exported unqualifiedly, then class p1.c1 in m1 can read p2.c2 in m2.
+ * @summary Test that if module m1x can read module m2x, AND package p2 in module_two is
+ *          exported unqualifiedly, then class p1.c1 in m1x can read p2.c2 in m2x.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
  * @compile myloaders/MySameClassLoader.java
@@ -53,45 +53,45 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
-        // Can read:          java.base, m2
+        // Define module:     m1x
+        // Can read:          java.base, m2x
         // Packages:          p1
         // Packages exported: p1 is exported unqualifiedly
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
+                        .requires("m2x")
                         .exports("p1")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p2
         // Packages exported: p2 is exported unqualifiedly
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
                         .exports("p2")
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to the same class loader for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MySameClassLoader.loader1);
-        map.put("m2", MySameClassLoader.loader1);
+        map.put("m1x", MySameClassLoader.loader1);
+        map.put("m2x", MySameClassLoader.loader1);
 
-        // Create Layer that contains m1 & m2
+        // Create Layer that contains m1x & m2x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MySameClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m1x") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MySameClassLoader.loader1);
 
         // now use the same loader to load class p1.c1
         Class p1_c1_class = MySameClassLoader.loader1.loadClass("p1.c1");
--- a/hotspot/test/runtime/modules/AccessCheck/ExportAllUnnamed.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/ExportAllUnnamed.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,8 +25,8 @@
 
 /*
  * @test
- * @summary Test if package p2 in module m2 is exported to all unnamed,
- *          then class p1.c1 in an unnamed module can read p2.c2 in module m2.
+ * @summary Test if package p2 in module m2x is exported to all unnamed,
+ *          then class p1.c1 in an unnamed module can read p2.c2 in module m2x.
  * @library /test/lib
  * @modules java.base/jdk.internal.misc
  * @modules java.base/jdk.internal.module
@@ -49,15 +49,15 @@
 import myloaders.MySameClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> no packages
-//                  defines m2 --> packages p2
+// ClassLoader1 --> defines m1x --> no packages
+//                  defines m2x --> packages p2
 //
-// m1 can read m2
-// package p2 in m2 is exported unqualifiedly
+// m1x can read m2x
+// package p2 in m2x is exported unqualifiedly
 //
-// class p1.c1 defined in an unnamed module tries to access p2.c2 defined in m2
+// class p1.c1 defined in an unnamed module tries to access p2.c2 defined in m2x
 // Access allowed, an unnamed module can read all modules and p2 in module
-//           m2 is exported to all unnamed modules.
+//           m2x is exported to all unnamed modules.
 
 public class ExportAllUnnamed {
 
@@ -66,51 +66,51 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
-        // Can read:          java.base, m2
+        // Define module:     m1x
+        // Can read:          java.base, m2x
         // Packages:          none
         // Packages exported: none
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
+                        .requires("m2x")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p2
         // Packages exported: p2 is exported unqualifiedly
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
-                        .exports("p2", Set.of("m1"))
+                        .exports("p2", Set.of("m1x"))
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to differing class loaders for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MySameClassLoader.loader1);
-        map.put("m2", MySameClassLoader.loader1);
+        map.put("m1x", MySameClassLoader.loader1);
+        map.put("m2x", MySameClassLoader.loader1);
 
-        // Create Layer that contains m1 & m2
+        // Create Layer that contains m1x & m2x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MySameClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m1x") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MySameClassLoader.loader1);
         assertTrue(layer.findLoader("java.base") == null);
 
         Class p2_c2_class = MySameClassLoader.loader1.loadClass("p2.c2");
-        Module m2 = p2_c2_class.getModule();
+        Module m2x = p2_c2_class.getModule();
 
-        // Export m2/p2 to all unnamed modules.
-        jdk.internal.module.Modules.addExportsToAllUnnamed(m2, "p2");
+        // Export m2x/p2 to all unnamed modules.
+        jdk.internal.module.Modules.addExportsToAllUnnamed(m2x, "p2");
 
         // now use the same loader to load class p1.c1
         Class p1_c1_class = MySameClassLoader.loader1.loadClass("p1.c1");
--- a/hotspot/test/runtime/modules/AccessCheck/PkgNotExp.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/PkgNotExp.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,8 +25,8 @@
 
 /*
  * @test
- * @summary Test that if module m1 can read module m2, but package p2 in m2 is not
- *          exported, then class p1.c1 in m1 can not read p2.c2 in m2.
+ * @summary Test that if module m1x can read module m2x, but package p2 in m2x is not
+ *          exported, then class p1.c1 in m1x can not read p2.c2 in m2x.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
  * @compile myloaders/MySameClassLoader.java
@@ -47,13 +47,13 @@
 import myloaders.MySameClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> packages p1
-//                  defines m2 --> packages p2
+// ClassLoader1 --> defines m1x --> packages p1
+//                  defines m2x --> packages p2
 //
-// m1 can read m2
-// package p2 in m2 is not exported
+// m1x can read m2x
+// package p2 in m2x is not exported
 //
-// class p1.c1 defined in m1 tries to access p2.c2 defined in m2
+// class p1.c1 defined in m1x tries to access p2.c2 defined in m2x
 // Access denied since p2 is not exported.
 //
 public class PkgNotExp {
@@ -63,51 +63,51 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
-        // Can read:          java.base, m2
+        // Define module:     m1x
+        // Can read:          java.base, m2x
         // Packages:          p1
         // Packages exported: p1 is exported unqualifiedly
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
+                        .requires("m2x")
                         .exports("p1")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p2
         // Packages exported: none
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
-                        .contains("p2")
+                        .packages(Set.of("p2"))
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to the same class loader for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MySameClassLoader.loader1);
-        map.put("m2", MySameClassLoader.loader1);
+        map.put("m1x", MySameClassLoader.loader1);
+        map.put("m2x", MySameClassLoader.loader1);
 
-        // Create Layer that contains m1 and m2
+        // Create Layer that contains m1x and m2x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MySameClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m1x") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MySameClassLoader.loader1);
 
         // now use the same loader to load class p1.c1
         Class p1_c1_class = MySameClassLoader.loader1.loadClass("p1.c1");
         try {
             p1_c1_class.newInstance();
-            throw new RuntimeException("Failed to get IAE (p2 in m2 is not exported)");
+            throw new RuntimeException("Failed to get IAE (p2 in m2x is not exported)");
         } catch (IllegalAccessError e) {
           System.out.println(e.getMessage());
           if (!e.getMessage().contains("does not export")) {
--- a/hotspot/test/runtime/modules/AccessCheck/Umod.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/Umod.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,7 +25,7 @@
 
 /*
  * @test
- * @summary class p1.c1 defined in m1 tries to access p2.c2 defined in unnamed module.
+ * @summary class p1.c1 defined in m1x tries to access p2.c2 defined in unnamed module.
  * @library /test/lib
  * @modules java.base/jdk.internal.misc
  * @modules java.base/jdk.internal.module
@@ -50,10 +50,10 @@
 import myloaders.MySameClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> packages p1
-//                  package p1 in m1 is exported unqualifiedly
+// ClassLoader1 --> defines m1x --> packages p1
+//                  package p1 in m1x is exported unqualifiedly
 //
-// class p1.c1 defined in m1 tries to access p2.c2 defined in
+// class p1.c1 defined in m1x tries to access p2.c2 defined in
 // in unnamed module.
 //
 // Three access attempts occur in this test:
@@ -62,7 +62,7 @@
 //   2. In this scenario a strict module establishes readability
 //      to the particular unnamed module it is trying to access.
 //      Access is allowed.
-//   3. Module m1 in the test_looseModuleLayer() method
+//   3. Module m1x in the test_looseModuleLayer() method
 //      is transitioned to a loose module, access
 //      to all unnamed modules is allowed.
 //
@@ -71,38 +71,38 @@
  // Create Layers over the boot layer to test different
  // accessing scenarios of a named module to an unnamed module.
 
- // Module m1 is a strict module and has not established
+ // Module m1x is a strict module and has not established
  // readability to an unnamed module that p2.c2 is defined in.
  public void test_strictModuleLayer() throws Throwable {
 
-     // Define module:     m1
+     // Define module:     m1x
      // Can read:          java.base
      // Packages:          p1
      // Packages exported: p1 is exported unqualifiedly
-     ModuleDescriptor descriptor_m1 =
-             ModuleDescriptor.module("m1")
+     ModuleDescriptor descriptor_m1x =
+             ModuleDescriptor.newModule("m1x")
                      .requires("java.base")
                      .exports("p1")
                      .build();
 
      // Set up a ModuleFinder containing all modules for this layer.
-     ModuleFinder finder = ModuleLibrary.of(descriptor_m1);
+     ModuleFinder finder = ModuleLibrary.of(descriptor_m1x);
 
-     // Resolves "m1"
+     // Resolves "m1x"
      Configuration cf = Layer.boot()
              .configuration()
-             .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+             .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
-     // map module m1 to class loader.
+     // map module m1x to class loader.
      // class c2 will be loaded in an unnamed module/loader.
      MySameClassLoader loader = new MySameClassLoader();
      Map<String, ClassLoader> map = new HashMap<>();
-     map.put("m1", loader);
+     map.put("m1x", loader);
 
-     // Create Layer that contains m1
+     // Create Layer that contains m1x
      Layer layer = Layer.boot().defineModules(cf, map::get);
 
-     assertTrue(layer.findLoader("m1") == loader);
+     assertTrue(layer.findLoader("m1x") == loader);
      assertTrue(layer.findLoader("java.base") == null);
 
      // now use the same loader to load class p1.c1
@@ -111,103 +111,103 @@
      // Attempt access
      try {
          p1_c1_class.newInstance();
-         throw new RuntimeException("Test Failed, strict module m1, type p1.c1, should not be able " +
+         throw new RuntimeException("Test Failed, strict module m1x, type p1.c1, should not be able " +
                                     "to access public type p2.c2 defined in unnamed module");
      } catch (IllegalAccessError e) {
      }
  }
 
- // Module m1 is a strict module and has established
+ // Module m1x is a strict module and has established
  // readability to an unnamed module that p2.c2 is defined in.
  public void test_strictModuleUnnamedReadableLayer() throws Throwable {
 
-     // Define module:     m1
+     // Define module:     m1x
      // Can read:          java.base
      // Packages:          p1
      // Packages exported: p1 is exported unqualifiedly
-     ModuleDescriptor descriptor_m1 =
-             ModuleDescriptor.module("m1")
+     ModuleDescriptor descriptor_m1x =
+             ModuleDescriptor.newModule("m1x")
                      .requires("java.base")
                      .exports("p1")
                      .build();
 
      // Set up a ModuleFinder containing all modules for this layer.
-     ModuleFinder finder = ModuleLibrary.of(descriptor_m1);
+     ModuleFinder finder = ModuleLibrary.of(descriptor_m1x);
 
-     // Resolves "m1"
+     // Resolves "m1x"
      Configuration cf = Layer.boot()
              .configuration()
-             .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+             .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
      MySameClassLoader loader = new MySameClassLoader();
-     // map module m1 to class loader.
+     // map module m1x to class loader.
      // class c2 will be loaded in an unnamed module/loader.
      Map<String, ClassLoader> map = new HashMap<>();
-     map.put("m1", loader);
+     map.put("m1x", loader);
 
-     // Create Layer that contains m1
+     // Create Layer that contains m1x
      Layer layer = Layer.boot().defineModules(cf, map::get);
 
-     assertTrue(layer.findLoader("m1") == loader);
+     assertTrue(layer.findLoader("m1x") == loader);
      assertTrue(layer.findLoader("java.base") == null);
 
      // now use the same loader to load class p1.c1ReadEdge
      Class p1_c1_class = loader.loadClass("p1.c1ReadEdge");
 
      try {
-       // Read edge between m1 and the unnamed module that loads p2.c2 is established in
+       // Read edge between m1x and the unnamed module that loads p2.c2 is established in
        // c1ReadEdge's ctor before attempting access.
        p1_c1_class.newInstance();
      } catch (IllegalAccessError e) {
-         throw new RuntimeException("Test Failed, strict module m1, type p1.c1ReadEdge, should be able to acccess public type " +
+         throw new RuntimeException("Test Failed, strict module m1x, type p1.c1ReadEdge, should be able to acccess public type " +
                                     "p2.c2 defined in unnamed module: " + e.getMessage());
      }
 }
 
- // Module m1 is a loose module and thus can read all unnamed modules.
+ // Module m1x is a loose module and thus can read all unnamed modules.
  public void test_looseModuleLayer() throws Throwable {
 
-     // Define module:     m1
+     // Define module:     m1x
      // Can read:          java.base
      // Packages:          p1
      // Packages exported: p1 is exported unqualifiedly
-     ModuleDescriptor descriptor_m1 =
-             ModuleDescriptor.module("m1")
+     ModuleDescriptor descriptor_m1x =
+             ModuleDescriptor.newModule("m1x")
                      .requires("java.base")
                      .exports("p1")
                      .build();
 
      // Set up a ModuleFinder containing all modules for this layer.
-     ModuleFinder finder = ModuleLibrary.of(descriptor_m1);
+     ModuleFinder finder = ModuleLibrary.of(descriptor_m1x);
 
-     // Resolves "m1"
+     // Resolves "m1x"
      Configuration cf = Layer.boot()
              .configuration()
-             .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+             .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
      MySameClassLoader loader = new MySameClassLoader();
-     // map module m1 to class loader.
+     // map module m1x to class loader.
      // class c2 will be loaded in an unnamed module/loader.
      Map<String, ClassLoader> map = new HashMap<>();
-     map.put("m1", loader);
+     map.put("m1x", loader);
 
-     // Create Layer that contains m1
+     // Create Layer that contains m1x
      Layer layer = Layer.boot().defineModules(cf, map::get);
 
-     assertTrue(layer.findLoader("m1") == loader);
+     assertTrue(layer.findLoader("m1x") == loader);
      assertTrue(layer.findLoader("java.base") == null);
 
      // now use the same loader to load class p1.c1Loose
      Class p1_c1_class = loader.loadClass("p1.c1Loose");
 
-     // change m1 to read all unnamed modules
-     Module m1 = layer.findModule("m1").get();
-     jdk.internal.module.Modules.addReadsAllUnnamed(m1);
+     // change m1x to read all unnamed modules
+     Module m1x = layer.findModule("m1x").get();
+     jdk.internal.module.Modules.addReadsAllUnnamed(m1x);
 
      try {
          p1_c1_class.newInstance();
      } catch (IllegalAccessError e) {
-         throw new RuntimeException("Test Failed, strict module m1, type p1.c1Loose, should be able to acccess public type " +
+         throw new RuntimeException("Test Failed, strict module m1x, type p1.c1Loose, should be able to acccess public type " +
                                     "p2.c2 defined in unnamed module: " + e.getMessage());
      }
  }
--- a/hotspot/test/runtime/modules/AccessCheck/UmodDiffCL_ExpQualOther.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/UmodDiffCL_ExpQualOther.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,9 +25,9 @@
 
 /*
  * @test
- * @summary class p1.c1 defined in an unnamed module tries to access p2.c2 defined in m2.
+ * @summary class p1.c1 defined in an unnamed module tries to access p2.c2 defined in m2x.
  *          Access is denied, since an unnamed module can read all modules but p2 in module
- *          m2 is exported specifically to module m1, not to all modules.
+ *          m2x is exported specifically to module m1x, not to all modules.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
  * @compile myloaders/MyDiffClassLoader.java
@@ -48,15 +48,15 @@
 import myloaders.MyDiffClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> no packages
-// ClassLoader2 --> defines m2 --> packages p2
+// ClassLoader1 --> defines m1x --> no packages
+// ClassLoader2 --> defines m2x --> packages p2
 //
-// m1 can read m2
-// package p2 in m2 is not exported
+// m1x can read m2x
+// package p2 in m2x is not exported
 //
-// class p1.c1 defined in an unnamed module tries to access p2.c2 defined in m2
+// class p1.c1 defined in an unnamed module tries to access p2.c2 defined in m2x
 // Access denied, an unnamed module can read all modules but p2 in module
-//             m2 is exported specifically to module m1 not to all modules.
+//             m2x is exported specifically to module m1x not to all modules.
 //
 public class UmodDiffCL_ExpQualOther {
 
@@ -65,53 +65,53 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
+        // Define module:     m1x
         // Can read:          java.base
         // Packages:          none
         // Packages exported: none
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
+                        .requires("m2x")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p2
         // Packages exported: none
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
-                        .exports("p2", Set.of("m1"))
+                        .exports("p2", Set.of("m1x"))
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to differing class loaders for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MyDiffClassLoader.loader1);
-        map.put("m2", MyDiffClassLoader.loader2);
+        map.put("m1x", MyDiffClassLoader.loader1);
+        map.put("m2x", MyDiffClassLoader.loader2);
 
-        // Create Layer that contains m1 & m2
+        // Create Layer that contains m1x & m2x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MyDiffClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MyDiffClassLoader.loader2);
+        assertTrue(layer.findLoader("m1x") == MyDiffClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MyDiffClassLoader.loader2);
         assertTrue(layer.findLoader("java.base") == null);
 
         // now use the same loader to load class p1.c1
-        // NOTE: module m1 does not define a package named p1.
+        // NOTE: module m1x does not define a package named p1.
         //       p1 will be loaded in an unnamed module.
         Class p1_c1_class = MyDiffClassLoader.loader1.loadClass("p1.c1");
         try {
             p1_c1_class.newInstance();
-            throw new RuntimeException("Failed to get IAE (p2 in m2 is exported to m1, not unqualifiedly");
+            throw new RuntimeException("Failed to get IAE (p2 in m2x is exported to m1x, not unqualifiedly");
         } catch (IllegalAccessError e) {
             System.out.println(e.getMessage());
             if (!e.getMessage().contains("does not export")) {
--- a/hotspot/test/runtime/modules/AccessCheck/UmodDiffCL_ExpUnqual.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/UmodDiffCL_ExpUnqual.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,8 +25,8 @@
 
 /*
  * @test
- * @summary class p1.c1 defined in an unnamed module tries to access p2.c2 defined in m2.
- *          Access allowed, an unnamed module can read all modules and p2 in module m2
+ * @summary class p1.c1 defined in an unnamed module tries to access p2.c2 defined in m2x.
+ *          Access allowed, an unnamed module can read all modules and p2 in module m2x
  *          which is exported unqualifiedly.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
@@ -48,15 +48,15 @@
 import myloaders.MyDiffClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> no packages
-// ClassLoader2 --> defines m2 --> packages p2
+// ClassLoader1 --> defines m1x --> no packages
+// ClassLoader2 --> defines m2x --> packages p2
 //
-// m1 can read m2
-// package p2 in m2 is exported unqualifiedly.
+// m1x can read m2x
+// package p2 in m2x is exported unqualifiedly.
 //
-// class p1.c1 defined in an unnamed module tries to access p2.c2 defined in m2
+// class p1.c1 defined in an unnamed module tries to access p2.c2 defined in m2x
 // Access allowed, an unnamed module can read all modules and p2 in module
-//              m2 which is exported unqualifiedly.
+//              m2x which is exported unqualifiedly.
 //
 public class UmodDiffCL_ExpUnqual {
 
@@ -65,53 +65,53 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
-        // Can read:          java.base, m2
+        // Define module:     m1x
+        // Can read:          java.base, m2x
         // Packages:          none
         // Packages exported: none
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
+                        .requires("m2x")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p2
         // Packages exported: none
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
                         .exports("p2")
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to differing class loaders for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MyDiffClassLoader.loader1);
-        map.put("m2", MyDiffClassLoader.loader2);
+        map.put("m1x", MyDiffClassLoader.loader1);
+        map.put("m2x", MyDiffClassLoader.loader2);
 
-        // Create Layer that contains m1 & m2
+        // Create Layer that contains m1x & m2x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MyDiffClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MyDiffClassLoader.loader2);
+        assertTrue(layer.findLoader("m1x") == MyDiffClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MyDiffClassLoader.loader2);
         assertTrue(layer.findLoader("java.base") == null);
 
-        // NOTE: module m1 does not define a package named p1.
+        // NOTE: module m1x does not define a package named p1.
         //       p1 will be loaded in an unnamed module.
         Class p1_c1_class = MyDiffClassLoader.loader1.loadClass("p1.c1");
         try {
             p1_c1_class.newInstance();
         } catch (IllegalAccessError e) {
-            throw new RuntimeException("Test Failed, p1.c1 defined in unnamed module can access p2.c2 in module m2");
+            throw new RuntimeException("Test Failed, p1.c1 defined in unnamed module can access p2.c2 in module m2x");
         }
     }
 
--- a/hotspot/test/runtime/modules/AccessCheck/UmodDiffCL_PkgNotExp.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/UmodDiffCL_PkgNotExp.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,9 +25,9 @@
 
 /*
  * @test
- * @summary class p1.c1 defined in unnamed module tries to access p2.c2 defined in m2.
+ * @summary class p1.c1 defined in unnamed module tries to access p2.c2 defined in m2x.
  *          Access is denied since even though unnamed module can read all modules, p2
- *          in module m2 is not exported at all.
+ *          in module m2x is not exported at all.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
  * @compile myloaders/MyDiffClassLoader.java
@@ -47,15 +47,15 @@
 import myloaders.MyDiffClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> no packages
-// ClassLoader2 --> defines m2 --> packages p2
+// ClassLoader1 --> defines m1x --> no packages
+// ClassLoader2 --> defines m2x --> packages p2
 //
-// m1 can read m2
-// package p2 in m2 is not exported
+// m1x can read m2x
+// package p2 in m2x is not exported
 //
-// class p1.c1 defined in unnamed module tries to access p2.c2 defined in m2
+// class p1.c1 defined in unnamed module tries to access p2.c2 defined in m2x
 // Access denied since even though unnamed module can read all modules, p2
-// in module m2 is not exported at all.
+// in module m2x is not exported at all.
 //
 public class UmodDiffCL_PkgNotExp {
 
@@ -64,53 +64,53 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
-        // Can read:          java.base, m2
+        // Define module:     m1x
+        // Can read:          java.base, m2x
         // Packages:          none
         // Packages exported: none
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
+                        .requires("m2x")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p2
         // Packages exported: none
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
-                        .contains("p2")
+                        .packages(Set.of("p2"))
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to differing class loaders for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MyDiffClassLoader.loader1);
-        map.put("m2", MyDiffClassLoader.loader2);
+        map.put("m1x", MyDiffClassLoader.loader1);
+        map.put("m2x", MyDiffClassLoader.loader2);
 
-        // Create Layer that contains m1 & m2
+        // Create Layer that contains m1x & m2x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MyDiffClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MyDiffClassLoader.loader2);
+        assertTrue(layer.findLoader("m1x") == MyDiffClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MyDiffClassLoader.loader2);
         assertTrue(layer.findLoader("java.base") == null);
 
         // now use the same loader to load class p1.c1
-        // NOTE: module m1 does not define a package named p1.
+        // NOTE: module m1x does not define a package named p1.
         //       p1 will be loaded in an unnamed module.
         Class p1_c1_class = MyDiffClassLoader.loader1.loadClass("p1.c1");
         try {
             p1_c1_class.newInstance();
-            throw new RuntimeException("Failed to get IAE (p2 in m2 is not exported to an unnamed module)");
+            throw new RuntimeException("Failed to get IAE (p2 in m2x is not exported to an unnamed module)");
         } catch (IllegalAccessError e) {
           System.out.println(e.getMessage());
           if (!e.getMessage().contains("does not export")) {
--- a/hotspot/test/runtime/modules/AccessCheck/UmodUPkg.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/UmodUPkg.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,7 +25,7 @@
 
 /*
  * @test
- * @summary class p3.c3 defined in module m1 tries to access c4 defined in unnamed module.
+ * @summary class p3.c3 defined in module m1x tries to access c4 defined in unnamed module.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
  * @compile myloaders/MySameClassLoader.java
@@ -48,10 +48,10 @@
 import myloaders.MySameClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> packages p3
-//                  package p3 in m1 is exported unqualifiedly
+// ClassLoader1 --> defines m1x --> packages p3
+//                  package p3 in m1x is exported unqualifiedly
 //
-// class p3.c3 defined in m1 tries to access c4 defined in
+// class p3.c3 defined in m1x tries to access c4 defined in
 // in unnamed module.
 //
 // Two access attempts occur in this test:
@@ -66,38 +66,38 @@
  // Create Layers over the boot layer to test different
  // accessing scenarios of a named module to an unnamed module.
 
- // Module m1 is a strict module and has not established
+ // Module m1x is a strict module and has not established
  // readability to an unnamed module that c4 is defined in.
  public void test_strictModuleLayer() throws Throwable {
 
-     // Define module:     m1
+     // Define module:     m1x
      // Can read:          java.base
      // Packages:          p3
      // Packages exported: p3 is exported unqualifiedly
-     ModuleDescriptor descriptor_m1 =
-             ModuleDescriptor.module("m1")
+     ModuleDescriptor descriptor_m1x =
+             ModuleDescriptor.newModule("m1x")
                      .requires("java.base")
                      .exports("p3")
                      .build();
 
      // Set up a ModuleFinder containing all modules for this layer.
-     ModuleFinder finder = ModuleLibrary.of(descriptor_m1);
+     ModuleFinder finder = ModuleLibrary.of(descriptor_m1x);
 
-     // Resolves "m1"
+     // Resolves "m1x"
      Configuration cf = Layer.boot()
              .configuration()
-             .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+             .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
-     // map module m1 to class loader.
+     // map module m1x to class loader.
      // class c4 will be loaded in an unnamed module/loader.
      MySameClassLoader loader = new MySameClassLoader();
      Map<String, ClassLoader> map = new HashMap<>();
-     map.put("m1", loader);
+     map.put("m1x", loader);
 
-     // Create Layer that contains m1
+     // Create Layer that contains m1x
      Layer layer = Layer.boot().defineModules(cf, map::get);
 
-     assertTrue(layer.findLoader("m1") == loader);
+     assertTrue(layer.findLoader("m1x") == loader);
      assertTrue(layer.findLoader("java.base") == null);
 
      // now use the same loader to load class p3.c3
@@ -106,55 +106,55 @@
      // Attempt access
      try {
          p3_c3_class.newInstance();
-         throw new RuntimeException("Test Failed, strict module m1, type p3.c3, should not be able to access " +
+         throw new RuntimeException("Test Failed, strict module m1x, type p3.c3, should not be able to access " +
                                     "public type c4 defined in unnamed module");
      } catch (IllegalAccessError e) {
      }
  }
 
- // Module m1 is a strict module and has established
+ // Module m1x is a strict module and has established
  // readability to an unnamed module that c4 is defined in.
  public void test_strictModuleUnnamedReadableLayer() throws Throwable {
 
-     // Define module:     m1
+     // Define module:     m1x
      // Can read:          java.base
      // Packages:          p3
      // Packages exported: p3 is exported unqualifiedly
-     ModuleDescriptor descriptor_m1 =
-             ModuleDescriptor.module("m1")
+     ModuleDescriptor descriptor_m1x =
+             ModuleDescriptor.newModule("m1x")
                      .requires("java.base")
                      .exports("p3")
                      .build();
 
      // Set up a ModuleFinder containing all modules for this layer.
-     ModuleFinder finder = ModuleLibrary.of(descriptor_m1);
+     ModuleFinder finder = ModuleLibrary.of(descriptor_m1x);
 
-     // Resolves "m1"
+     // Resolves "m1x"
      Configuration cf = Layer.boot()
              .configuration()
-             .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+             .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
      MySameClassLoader loader = new MySameClassLoader();
-     // map module m1 to class loader.
+     // map module m1x to class loader.
      // class c4 will be loaded in an unnamed module/loader.
      Map<String, ClassLoader> map = new HashMap<>();
-     map.put("m1", loader);
+     map.put("m1x", loader);
 
-     // Create Layer that contains m1
+     // Create Layer that contains m1x
      Layer layer = Layer.boot().defineModules(cf, map::get);
 
-     assertTrue(layer.findLoader("m1") == loader);
+     assertTrue(layer.findLoader("m1x") == loader);
      assertTrue(layer.findLoader("java.base") == null);
 
      // now use the same loader to load class p3.c3ReadEdge
      Class p3_c3_class = loader.loadClass("p3.c3ReadEdge");
 
      try {
-        // Read edge between m1 and the unnamed module that loads c4 is established in
+        // Read edge between m1x and the unnamed module that loads c4 is established in
         // c3ReadEdge's ctor before attempting access.
         p3_c3_class.newInstance();
      } catch (IllegalAccessError e) {
-         throw new RuntimeException("Test Failed, module m1, type p3.c3ReadEdge, has established readability to " +
+         throw new RuntimeException("Test Failed, module m1x, type p3.c3ReadEdge, has established readability to " +
                                     "c4 loader's unnamed module, access should be allowed: " + e.getMessage());
      }
  }
--- a/hotspot/test/runtime/modules/AccessCheck/UmodUpkgDiffCL_ExpQualOther.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/UmodUpkgDiffCL_ExpQualOther.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,9 +25,9 @@
 
 /*
  * @test
- * @summary class c5 defined in an unnamed module tries to access p6.c6 defined in m2.
+ * @summary class c5 defined in an unnamed module tries to access p6.c6 defined in m2x.
  *          Access is denied, since an unnamed module can read all modules but p6 in module
- *          m2 is exported specifically to module m1, not to all modules.
+ *          m2x is exported specifically to module m1x, not to all modules.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
  * @compile myloaders/MyDiffClassLoader.java
@@ -48,15 +48,15 @@
 import myloaders.MyDiffClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> no packages
-// ClassLoader2 --> defines m2 --> packages p6
+// ClassLoader1 --> defines m1x --> no packages
+// ClassLoader2 --> defines m2x --> packages p6
 //
-// m1 can read m2
-// package p6 in m2 is not exported
+// m1x can read m2x
+// package p6 in m2x is not exported
 //
-// class c5 defined in an unnamed module tries to access p6.c6 defined in m2
+// class c5 defined in an unnamed module tries to access p6.c6 defined in m2x
 // Access denied, an unnamed module can read all modules but p6 in module
-//             m2 is exported specifically to module m1 not to all modules.
+//             m2x is exported specifically to module m1x not to all modules.
 //
 public class UmodUpkgDiffCL_ExpQualOther {
 
@@ -65,51 +65,51 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
-        // Can read:          java.base, m2
+        // Define module:     m1x
+        // Can read:          java.base, m2x
         // Packages:          none
         // Packages exported: none
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
+                        .requires("m2x")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p6
-        // Packages exported: p6 exported to m1
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        // Packages exported: p6 exported to m1x
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
-                        .exports("p6", Set.of("m1"))
+                        .exports("p6", Set.of("m1x"))
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to differing class loaders for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MyDiffClassLoader.loader1);
-        map.put("m2", MyDiffClassLoader.loader2);
+        map.put("m1x", MyDiffClassLoader.loader1);
+        map.put("m2x", MyDiffClassLoader.loader2);
 
-        // Create Layer that contains m1 & m2
+        // Create Layer that contains m1x & m2x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MyDiffClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MyDiffClassLoader.loader2);
+        assertTrue(layer.findLoader("m1x") == MyDiffClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MyDiffClassLoader.loader2);
         assertTrue(layer.findLoader("java.base") == null);
 
         // now use the same loader to load class c5
         Class c5_class = MyDiffClassLoader.loader1.loadClass("c5");
         try {
             c5_class.newInstance();
-            throw new RuntimeException("Failed to get IAE (p6 in m2 is exported to m1, not unqualifiedly");
+            throw new RuntimeException("Failed to get IAE (p6 in m2x is exported to m1x, not unqualifiedly");
         } catch (IllegalAccessError e) {
             System.out.println(e.getMessage());
             if (!e.getMessage().contains("does not export")) {
--- a/hotspot/test/runtime/modules/AccessCheck/UmodUpkgDiffCL_NotExp.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/UmodUpkgDiffCL_NotExp.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,8 +25,8 @@
 
 /*
  * @test
- * @summary class c5 in an unnamed module can read module m2, but package p6 in module m2 is not exported.
- *          Access denied since even though unnamed module can read all modules, p6 in module m2 is not exported at all.
+ * @summary class c5 in an unnamed module can read module m2x, but package p6 in module m2x is not exported.
+ *          Access denied since even though unnamed module can read all modules, p6 in module m2x is not exported at all.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
  * @compile myloaders/MyDiffClassLoader.java
@@ -47,15 +47,15 @@
 import myloaders.MyDiffClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> no packages
-// ClassLoader2 --> defines m2 --> packages p6
+// ClassLoader1 --> defines m1x --> no packages
+// ClassLoader2 --> defines m2x --> packages p6
 //
-// m1 can read m2
-// package p6 in m2 is not exported
+// m1x can read m2x
+// package p6 in m2x is not exported
 //
-// class c5 defined in unnamed module tries to access p6.c6 defined in m2
+// class c5 defined in unnamed module tries to access p6.c6 defined in m2x
 // Access denied since even though unnamed module can read all modules, p6
-// in module m2 is not exported at all.
+// in module m2x is not exported at all.
 //
 public class UmodUpkgDiffCL_NotExp {
 
@@ -64,53 +64,53 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
-        // Can read:          java.base, m2
+        // Define module:     m1x
+        // Can read:          java.base, m2x
         // Packages:          none
         // Packages exported: none
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
+                        .requires("m2x")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p6
         // Packages exported: none
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
-                        .contains("p6")
+                        .packages(Set.of("p6"))
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to differing class loaders for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MyDiffClassLoader.loader1);
-        map.put("m2", MyDiffClassLoader.loader2);
+        map.put("m1x", MyDiffClassLoader.loader1);
+        map.put("m2x", MyDiffClassLoader.loader2);
 
-        // Create Layer that contains m1 & m2
+        // Create Layer that contains m1x & m2x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MyDiffClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MyDiffClassLoader.loader2);
+        assertTrue(layer.findLoader("m1x") == MyDiffClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MyDiffClassLoader.loader2);
         assertTrue(layer.findLoader("java.base") == null);
 
         // now use the same loader to load class c5
-        // NOTE: module m1 does not define any packages.
+        // NOTE: module m1x does not define any packages.
         //       c5 will be loaded in an unnamed module.
         Class c5_class = MyDiffClassLoader.loader1.loadClass("c5");
         try {
             c5_class.newInstance();
-            throw new RuntimeException("Failed to get IAE (p6 in m2 is not exported to " +
+            throw new RuntimeException("Failed to get IAE (p6 in m2x is not exported to " +
                                        "an unnamed module that c5 is defined within)");
         } catch (IllegalAccessError e) {
           System.out.println(e.getMessage());
--- a/hotspot/test/runtime/modules/AccessCheck/UmodUpkg_ExpQualOther.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/UmodUpkg_ExpQualOther.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,8 +25,8 @@
 
 /*
  * @test
- * @summary Test that if class c5 in an unnamed module can read package p6 in module m2, but package p6 in module m2 is
- *          exported qualifiedly to module m3, then class c5 in an unnamed module can not read p6.c6 in module m2.
+ * @summary Test that if class c5 in an unnamed module can read package p6 in module m2x, but package p6 in module m2x is
+ *          exported qualifiedly to module m3x, then class c5 in an unnamed module can not read p6.c6 in module m2x.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
  * @compile myloaders/MySameClassLoader.java
@@ -47,15 +47,15 @@
 import myloaders.MySameClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> no packages
-//                  defines m2 --> packages p6
-//                  defines m3 --> packages p3
+// ClassLoader1 --> defines m1x --> no packages
+//                  defines m2x --> packages p6
+//                  defines m3x --> packages p3
 //
-// m1 can read m2
-// package p6 in m2 is exported to m3
+// m1x can read m2x
+// package p6 in m2x is exported to m3x
 //
-// class c5 defined in m1 tries to access p6.c6 defined in m2
-// Access denied since although m1 can read m2, p6 is exported only to m3.
+// class c5 defined in m1x tries to access p6.c6 defined in m2x
+// Access denied since although m1x can read m2x, p6 is exported only to m3x.
 //
 public class UmodUpkg_ExpQualOther {
 
@@ -64,63 +64,63 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1 (need to define m1 to establish the Layer successfully)
-        // Can read:          java.base, m2, m3
+        // Define module:     m1x (need to define m1x to establish the Layer successfully)
+        // Can read:          java.base, m2x, m3x
         // Packages:          none
         // Packages exported: none
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
-                        .requires("m3")
+                        .requires("m2x")
+                        .requires("m3x")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p6
-        // Packages exported: p6 is exported to m3
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        // Packages exported: p6 is exported to m3x
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
-                        .exports("p6", Set.of("m3"))
+                        .exports("p6", Set.of("m3x"))
                         .build();
 
-        // Define module:     m3
+        // Define module:     m3x
         // Can read:          java.base
         // Packages:          p3
         // Packages exported: none
-        ModuleDescriptor descriptor_m3 =
-                ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor_m3x =
+                ModuleDescriptor.newModule("m3x")
                         .requires("java.base")
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2, descriptor_m3);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x, descriptor_m3x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to differing class loaders for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MySameClassLoader.loader1);
-        map.put("m2", MySameClassLoader.loader1);
-        map.put("m3", MySameClassLoader.loader1);
+        map.put("m1x", MySameClassLoader.loader1);
+        map.put("m2x", MySameClassLoader.loader1);
+        map.put("m3x", MySameClassLoader.loader1);
 
-        // Create Layer that contains m1, m2 and m3
+        // Create Layer that contains m1x, m2x and m3x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MySameClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MySameClassLoader.loader1);
-        assertTrue(layer.findLoader("m3") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m1x") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m3x") == MySameClassLoader.loader1);
         assertTrue(layer.findLoader("java.base") == null);
 
         // now use the same loader to load class c5
         Class c5_class = MySameClassLoader.loader1.loadClass("c5");
         try {
             c5_class.newInstance();
-            throw new RuntimeException("Failed to get IAE (p6 in m2 is exported to m3, not unqualifiedly to everyone)");
+            throw new RuntimeException("Failed to get IAE (p6 in m2x is exported to m3x, not unqualifiedly to everyone)");
         } catch (IllegalAccessError e) {
             System.out.println(e.getMessage());
             if (!e.getMessage().contains("does not export")) {
--- a/hotspot/test/runtime/modules/AccessCheck/UmodUpkg_NotExp.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/UmodUpkg_NotExp.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,8 +25,8 @@
 
 /*
  * @test
- * @summary Test if package p6 in module m2 is not exported, then class c5
- *          in an unnamed module can not access p6.c2 in module m2.
+ * @summary Test if package p6 in module m2x is not exported, then class c5
+ *          in an unnamed module can not access p6.c2 in module m2x.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
  * @compile myloaders/MySameClassLoader.java
@@ -46,13 +46,13 @@
 import java.util.Set;
 import myloaders.MySameClassLoader;
 
-// ClassLoader1 --> defines m1 --> no packages
-//                  defines m2 --> packages p6
+// ClassLoader1 --> defines m1x --> no packages
+//                  defines m2x --> packages p6
 //
-// m1 can read m2
-// package p6 in m2 is not exported
+// m1x can read m2x
+// package p6 in m2x is not exported
 //
-// class c5 defined in an unnamed module tries to access p6.c2 defined in m2
+// class c5 defined in an unnamed module tries to access p6.c2 defined in m2x
 // Access denied since p6 is not exported.
 //
 public class UmodUpkg_NotExp {
@@ -62,51 +62,51 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
-        // Can read:          java.base, m2
+        // Define module:     m1x
+        // Can read:          java.base, m2x
         // Packages:          none
         // Packages exported: none
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
+                        .requires("m2x")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p6
         // Packages exported: none
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
-                        .contains("p6")
+                        .packages(Set.of("p6"))
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to the same class loader for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MySameClassLoader.loader1);
-        map.put("m2", MySameClassLoader.loader1);
+        map.put("m1x", MySameClassLoader.loader1);
+        map.put("m2x", MySameClassLoader.loader1);
 
-        // Create Layer that contains m1 and m2
+        // Create Layer that contains m1x and m2x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MySameClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m1x") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MySameClassLoader.loader1);
         assertTrue(layer.findLoader("java.base") == null);
 
         // now use the same loader to load class c5
         Class c5_class = MySameClassLoader.loader1.loadClass("c5");
         try {
             c5_class.newInstance();
-            throw new RuntimeException("Failed to get IAE (p6 in m2 is not exported)");
+            throw new RuntimeException("Failed to get IAE (p6 in m2x is not exported)");
         } catch (IllegalAccessError e) {
           System.out.println(e.getMessage());
           if (!e.getMessage().contains("does not export")) {
--- a/hotspot/test/runtime/modules/AccessCheck/Umod_ExpQualOther.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/Umod_ExpQualOther.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,8 +25,8 @@
 
 /*
  * @test
- * @summary Test that if package p2 in module m2 is exported to module m3,
- *          then class p1.c1 in an unnamed module can not read p2.c2 in module m2.
+ * @summary Test that if package p2 in module m2x is exported to module m3x,
+ *          then class p1.c1 in an unnamed module can not read p2.c2 in module m2x.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
  * @compile myloaders/MySameClassLoader.java
@@ -47,15 +47,15 @@
 import myloaders.MySameClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> no packages
-//                  defines m2 --> packages p2
-//                  defines m3 --> packages p3
+// ClassLoader1 --> defines m1x --> no packages
+//                  defines m2x --> packages p2
+//                  defines m3x --> packages p3
 //
-// m1 can read m2
-// package p2 in m2 is exported to m3
+// m1x can read m2x
+// package p2 in m2x is exported to m3x
 //
-// class p1.c1 defined in m1 tries to access p2.c2 defined in m2
-// Access denied since although m1 can read m2, p2 is exported only to m3.
+// class p1.c1 defined in m1x tries to access p2.c2 defined in m2x
+// Access denied since although m1x can read m2x, p2 is exported only to m3x.
 //
 public class Umod_ExpQualOther {
 
@@ -64,63 +64,63 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1 (need to define m1 to establish the Layer successfully)
-        // Can read:          java.base, m2, m3
+        // Define module:     m1x (need to define m1x to establish the Layer successfully)
+        // Can read:          java.base, m2x, m3x
         // Packages:          none
         // Packages exported: none
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
-                        .requires("m3")
+                        .requires("m2x")
+                        .requires("m3x")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p2
-        // Packages exported: p2 is exported to m3
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        // Packages exported: p2 is exported to m3x
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
-                        .exports("p2", Set.of("m3"))
+                        .exports("p2", Set.of("m3x"))
                         .build();
 
-        // Define module:     m3
+        // Define module:     m3x
         // Can read:          java.base
         // Packages:          p3
         // Packages exported: none
-        ModuleDescriptor descriptor_m3 =
-                ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor_m3x =
+                ModuleDescriptor.newModule("m3x")
                         .requires("java.base")
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2, descriptor_m3);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x, descriptor_m3x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to differing class loaders for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MySameClassLoader.loader1);
-        map.put("m2", MySameClassLoader.loader1);
-        map.put("m3", MySameClassLoader.loader1);
+        map.put("m1x", MySameClassLoader.loader1);
+        map.put("m2x", MySameClassLoader.loader1);
+        map.put("m3x", MySameClassLoader.loader1);
 
-        // Create Layer that contains m1, m2 and m3
+        // Create Layer that contains m1x, m2x and m3x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MySameClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MySameClassLoader.loader1);
-        assertTrue(layer.findLoader("m3") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m1x") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m3x") == MySameClassLoader.loader1);
         assertTrue(layer.findLoader("java.base") == null);
 
         // now use the same loader to load class p1.c1
         Class p1_c1_class = MySameClassLoader.loader1.loadClass("p1.c1");
         try {
             p1_c1_class.newInstance();
-            throw new RuntimeException("Failed to get IAE (p2 in m2 is exported to m3, not unqualifiedly to everyone)");
+            throw new RuntimeException("Failed to get IAE (p2 in m2x is exported to m3x, not unqualifiedly to everyone)");
         } catch (IllegalAccessError e) {
             System.out.println(e.getMessage());
             if (!e.getMessage().contains("does not export")) {
--- a/hotspot/test/runtime/modules/AccessCheck/Umod_ExpUnqual.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/Umod_ExpUnqual.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,8 +25,8 @@
 
 /*
  * @test
- * @summary Test if package p2 in module m2 is exported unqualifiedly,
- *          then class p1.c1 in an unnamed module can read p2.c2 in module m2.
+ * @summary Test if package p2 in module m2x is exported unqualifiedly,
+ *          then class p1.c1 in an unnamed module can read p2.c2 in module m2x.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
  * @compile myloaders/MySameClassLoader.java
@@ -47,15 +47,15 @@
 import myloaders.MySameClassLoader;
 
 //
-// ClassLoader1 --> defines m1 --> no packages
-//                  defines m2 --> packages p2
+// ClassLoader1 --> defines m1x --> no packages
+//                  defines m2x --> packages p2
 //
-// m1 can read m2
-// package p2 in m2 is exported unqualifiedly
+// m1x can read m2x
+// package p2 in m2x is exported unqualifiedly
 //
-// class p1.c1 defined in an unnamed module tries to access p2.c2 defined in m2
+// class p1.c1 defined in an unnamed module tries to access p2.c2 defined in m2x
 // Access allowed, an unnamed module can read all modules and p2 in module
-//           m2 which is exported unqualifiedly.
+//           m2x which is exported unqualifiedly.
 
 public class Umod_ExpUnqual {
 
@@ -64,44 +64,44 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
-        // Can read:          java.base, m2
+        // Define module:     m1x
+        // Can read:          java.base, m2x
         // Packages:          none
         // Packages exported: none
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
+                        .requires("m2x")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p2
         // Packages exported: p2 is exported unqualifiedly
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
                         .exports("p2")
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to differing class loaders for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MySameClassLoader.loader1);
-        map.put("m2", MySameClassLoader.loader1);
+        map.put("m1x", MySameClassLoader.loader1);
+        map.put("m2x", MySameClassLoader.loader1);
 
-        // Create Layer that contains m1 & m2
+        // Create Layer that contains m1x & m2x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MySameClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m1x") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MySameClassLoader.loader1);
         assertTrue(layer.findLoader("java.base") == null);
 
         // now use the same loader to load class p1.c1
--- a/hotspot/test/runtime/modules/AccessCheck/Umod_PkgNotExp.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/Umod_PkgNotExp.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -25,8 +25,8 @@
 
 /*
  * @test
- * @summary Test if package p2 in module m2 is not exported, then class p1.c1
- *          in an unnamed module can not access p2.c2 in module m2.
+ * @summary Test if package p2 in module m2x is not exported, then class p1.c1
+ *          in an unnamed module can not access p2.c2 in module m2x.
  * @modules java.base/jdk.internal.misc
  * @library /test/lib
  * @compile myloaders/MySameClassLoader.java
@@ -46,13 +46,13 @@
 import java.util.Set;
 import myloaders.MySameClassLoader;
 
-// ClassLoader1 --> defines m1 --> no packages
-//                  defines m2 --> packages p2
+// ClassLoader1 --> defines m1x --> no packages
+//                  defines m2x --> packages p2
 //
-// m1 can read m2
-// package p2 in m2 is not exported
+// m1x can read m2x
+// package p2 in m2x is not exported
 //
-// class p1.c1 defined in an unnamed module tries to access p2.c2 defined in m2
+// class p1.c1 defined in an unnamed module tries to access p2.c2 defined in m2x
 // Access denied since p2 is not exported.
 //
 public class Umod_PkgNotExp {
@@ -62,51 +62,51 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
-        // Can read:          java.base, m2
+        // Define module:     m1x
+        // Can read:          java.base, m2x
         // Packages:          none
         // Packages exported: none
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
+                        .requires("m2x")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p2
         // Packages exported: none
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
-                        .contains("p2")
+                        .packages(Set.of("p2"))
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to the same class loader for this test
         Map<String, ClassLoader> map = new HashMap<>();
-        map.put("m1", MySameClassLoader.loader1);
-        map.put("m2", MySameClassLoader.loader1);
+        map.put("m1x", MySameClassLoader.loader1);
+        map.put("m2x", MySameClassLoader.loader1);
 
-        // Create Layer that contains m1 and m2
+        // Create Layer that contains m1x and m2x
         Layer layer = Layer.boot().defineModules(cf, map::get);
 
-        assertTrue(layer.findLoader("m1") == MySameClassLoader.loader1);
-        assertTrue(layer.findLoader("m2") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m1x") == MySameClassLoader.loader1);
+        assertTrue(layer.findLoader("m2x") == MySameClassLoader.loader1);
         assertTrue(layer.findLoader("java.base") == null);
 
         // now use the same loader to load class p1.c1
         Class p1_c1_class = MySameClassLoader.loader1.loadClass("p1.c1");
         try {
             p1_c1_class.newInstance();
-            throw new RuntimeException("Failed to get IAE (p2 in m2 is not exported)");
+            throw new RuntimeException("Failed to get IAE (p2 in m2x is not exported)");
         } catch (IllegalAccessError e) {
           System.out.println(e.getMessage());
           if (!e.getMessage().contains("does not export")) {
--- a/hotspot/test/runtime/modules/AccessCheck/p1/c1Loose.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/p1/c1Loose.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2017, 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
@@ -26,7 +26,7 @@
 
 public class c1Loose {
     public c1Loose() {
-        // Attempt access - access should succeed since m1 is a loose module
+        // Attempt access - access should succeed since m1x is a loose module
         p2.c2 c2_obj = new p2.c2();
         c2_obj.method2();
     }
--- a/hotspot/test/runtime/modules/AccessCheck/p1/c1ReadEdge.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/p1/c1ReadEdge.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2017, 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
@@ -27,12 +27,12 @@
 
 public class c1ReadEdge {
     public c1ReadEdge() {
-        // Establish read edge from module m1, where c1ReadEdge is defined,
+        // Establish read edge from module m1x, where c1ReadEdge is defined,
         // to the unnamed module, where p2.c2 will be defined.
-        Module m1 = c1ReadEdge.class.getModule();
+        Module m1x = c1ReadEdge.class.getModule();
         ClassLoader loader = c1ReadEdge.class.getClassLoader();
         Module unnamed_module = loader.getUnnamedModule();
-        m1.addReads(unnamed_module);
+        m1x.addReads(unnamed_module);
 
         // Attempt access - access should succeed
         p2.c2 c2_obj = new p2.c2();
--- a/hotspot/test/runtime/modules/AccessCheck/p1/c1ReadEdgeDiffLoader.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/p1/c1ReadEdgeDiffLoader.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2017, 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
@@ -28,32 +28,32 @@
 
 public class c1ReadEdgeDiffLoader {
     public c1ReadEdgeDiffLoader() {
-        // The goal is to establish a read edge between module m1
+        // The goal is to establish a read edge between module m1x
         // which is the module where p1.c1ReadEdgeDiffLoader is defined,
         // and the unnamed module that defines p2.c2.  This must be
         // done in 2 steps:
         //
-        // Step #1: Establish a read edge between m1, where c1ReadEdgeDiffLoader
+        // Step #1: Establish a read edge between m1x, where c1ReadEdgeDiffLoader
         //          is defined, and the System ClassLoader's unnamed module,
         //          where MyDiffClassLoader is defined. This read edge
         //          is needed before we can obtain MyDiffClassLoader.loader2's unnamed module.
         //
-        // Step #2: Establish a read edge between m1, where c1ReadEdgeDiffLoader
+        // Step #2: Establish a read edge between m1x, where c1ReadEdgeDiffLoader
         //          is defined, and the MyDiffClassLoader.loader2's unnamed module,
         //          where p2.c2 will be defined.
 
-        // Step #1: read edge m1 -> System ClassLoader's unnamed module
-        Module m1 = c1ReadEdgeDiffLoader.class.getModule();
+        // Step #1: read edge m1x -> System ClassLoader's unnamed module
+        Module m1x = c1ReadEdgeDiffLoader.class.getModule();
         ClassLoader system_loader = ClassLoader.getSystemClassLoader();
-        Module unnamed_module1 = system_loader.getUnnamedModule();
-        m1.addReads(unnamed_module1);
+        Module unnamed_module_one = system_loader.getUnnamedModule();
+        m1x.addReads(unnamed_module_one);
 
-        // Step #2: read edge m1 -> MyDiffClassLoader.loader2's unnamed module
+        // Step #2: read edge m1x -> MyDiffClassLoader.loader2's unnamed module
         ClassLoader loader2 = MyDiffClassLoader.loader2;
-        Module unnamed_module2 = loader2.getUnnamedModule();
-        m1.addReads(unnamed_module2);
+        Module unnamed_module_two = loader2.getUnnamedModule();
+        m1x.addReads(unnamed_module_two);
 
-        // Attempt access - access should succeed since m1 can read
+        // Attempt access - access should succeed since m1x can read
         //                  MyDiffClassLoader.loader2's unnamed module
         p2.c2 c2_obj = new p2.c2();
         c2_obj.method2();
--- a/hotspot/test/runtime/modules/AccessCheck/p3/c3ReadEdge.jcod	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/p3/c3ReadEdge.jcod	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2017, 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
@@ -26,12 +26,12 @@
  * import java.lang.reflect.*;
  * public class c3ReadEdge {
  *    public c3ReadEdge() {
- *       // Establish read edge from module m1, where c3ReadEdge is defined,
+ *       // Establish read edge from module m1x, where c3ReadEdge is defined,
  *       // to the unnamed module, where c4 will be defined.
- *       Module m1 = c3ReadEdge.class.getModule();
+ *       Module m1x = c3ReadEdge.class.getModule();
  *       ClassLoader loader = c3ReadEdge.class.getClassLoader();
  *       Module unnamed_module = loader.getUnnamedModule();
- *       m1.addReads(unnamed_module);
+ *       m1x.addReads(unnamed_module);
  *       // Attempt access - access should succeed
  *       c4 c4_obj = new c4();
  *       c4_obj.method4();
--- a/hotspot/test/runtime/modules/AccessCheck/p3/c3ReadEdgeDiffLoader.jcod	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheck/p3/c3ReadEdgeDiffLoader.jcod	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2017, 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
@@ -28,32 +28,32 @@
  *
  * public class c3ReadEdgeDiffLoader {
  *    public c3ReadEdgeDiffLoader() {
- *       // The goal is to establish a read edge between module m1
+ *       // The goal is to establish a read edge between module m1x
  *       // which is the module where p3.c3ReadEdgeDiffLoader is defined,
  *       // and the unnamed module that defines c4.  This must be
  *       // done in 2 steps:
  *       //
- *       // Step #1: Establish a read edge between m1, where c3ReadEdgeDiffLoader
+ *       // Step #1: Establish a read edge between m1x, where c3ReadEdgeDiffLoader
  *       //          is defined, and the System ClassLoader's unnamed module,
  *       //          where MyDiffClassLoader is defined. This read edge
  *       //          is needed before we can obtain MyDiffClassLoader.loader2's unnamed module.
  *       //
- *       // Step #2: Establish a read edge between m1, where c3ReadEdgeDiffLoader
+ *       // Step #2: Establish a read edge between m1x, where c3ReadEdgeDiffLoader
  *       //          is defined, and the MyDiffClassLoader.loader2's unnamed module,
  *       //          where c4 will be defined.
  *
- *       // Step #1: read edge m1 -> System ClassLoader's unnamed module
- *       Module m1 = c3ReadEdgeDiffLoader.class.getModule();
+ *       // Step #1: read edge m1x -> System ClassLoader's unnamed module
+ *       Module m1x = c3ReadEdgeDiffLoader.class.getModule();
  *       ClassLoader system_loader = ClassLoader.getSystemClassLoader();
- *       Module unnamed_module1 = system_loader.getUnnamedModule();
- *       m1.addReads(unnamed_module1);
+ *       Module unnamed_module_one = system_loader.getUnnamedModule();
+ *       m1x.addReads(unnamed_module_one);
  *
- *       // Step #2: read edge m1 -> MyDiffClassLoader.loader2's unnamed module
+ *       // Step #2: read edge m1x -> MyDiffClassLoader.loader2's unnamed module
  *       ClassLoader loader2 = MyDiffClassLoader.loader2;
- *       Module unnamed_module2 = loader2.getUnnamedModule();
- *       m1.addReads(unnamed_module2);
+ *       Module unnamed_module_two = loader2.getUnnamedModule();
+ *       m1x.addReads(unnamed_module_two);
  *
- *       // Attempt access - should succeed since m1 can read
+ *       // Attempt access - should succeed since m1x can read
  *       //                  MyDiffClassLoader.loader2's unnamed module
  *       c4 c4_obj = new c4();
  *       c4_obj.method4();
--- a/hotspot/test/runtime/modules/AccessCheckAllUnnamed.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheckAllUnnamed.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -43,7 +43,7 @@
     // and then test that a class in the unnamed module can access a package in a
     // named module that has been exported to all unnamed modules.
     public static void main(String args[]) throws Throwable {
-        Object m1, m2;
+        Object m1x, m2x;
 
         // Get the java.lang.reflect.Module object for module java.base.
         Class jlObject = Class.forName("java.lang.Object");
@@ -55,16 +55,16 @@
         ClassLoader this_cldr = AccessCheckAllUnnamed.class.getClassLoader();
 
         // Define a module for p3.
-        m1 = ModuleHelper.ModuleObject("module1", this_cldr, new String[] { "p3" });
-        assertNotNull(m1, "Module should not be null");
-        ModuleHelper.DefineModule(m1, "9.0", "m1/there", new String[] { "p3" });
-        ModuleHelper.AddReadsModule(m1, jlObject_jlrM);
+        m1x = ModuleHelper.ModuleObject("module_one", this_cldr, new String[] { "p3" });
+        assertNotNull(m1x, "Module should not be null");
+        ModuleHelper.DefineModule(m1x, "9.0", "m1x/there", new String[] { "p3" });
+        ModuleHelper.AddReadsModule(m1x, jlObject_jlrM);
 
         // Define a module for p2.
-        m2 = ModuleHelper.ModuleObject("module2", this_cldr, new String[] { "p2" });
-        assertNotNull(m2, "Module should not be null");
-        ModuleHelper.DefineModule(m2, "9.0", "m2/there", new String[] { "p2" });
-        ModuleHelper.AddReadsModule(m2, jlObject_jlrM);
+        m2x = ModuleHelper.ModuleObject("module_two", this_cldr, new String[] { "p2" });
+        assertNotNull(m2x, "Module should not be null");
+        ModuleHelper.DefineModule(m2x, "9.0", "m2x/there", new String[] { "p2" });
+        ModuleHelper.AddReadsModule(m2x, jlObject_jlrM);
 
         try {
             ModuleHelper.AddModuleExportsToAllUnnamed((Module)null, "p2");
@@ -74,7 +74,7 @@
         }
 
         try {
-            ModuleHelper.AddModuleExportsToAllUnnamed(m2, null);
+            ModuleHelper.AddModuleExportsToAllUnnamed(m2x, null);
             throw new RuntimeException("Failed to get the expected NPE for null package");
         } catch(NullPointerException e) {
             // Expected
@@ -88,21 +88,21 @@
         }
 
         try {
-            ModuleHelper.AddModuleExportsToAllUnnamed(m2, "p3");
+            ModuleHelper.AddModuleExportsToAllUnnamed(m2x, "p3");
             throw new RuntimeException("Failed to get the expected IAE for package in other module");
         } catch(IllegalArgumentException e) {
             // Expected
         }
 
         try {
-            ModuleHelper.AddModuleExportsToAllUnnamed(m2, "p4");
+            ModuleHelper.AddModuleExportsToAllUnnamed(m2x, "p4");
             throw new RuntimeException("Failed to get the expected IAE for package not in module");
         } catch(IllegalArgumentException e) {
             // Expected
         }
 
-        // Export package p2 in m2 to allUnnamed.
-        ModuleHelper.AddModuleExportsToAllUnnamed(m2, "p2");
+        // Export package p2 in m2x to allUnnamed.
+        ModuleHelper.AddModuleExportsToAllUnnamed(m2x, "p2");
 
         // p1.c1's ctor tries to call a method in p2.c2.  This should succeed because
         // p1 is in an unnamed module and p2.c2 is exported to all unnamed modules.
--- a/hotspot/test/runtime/modules/AccessCheckExp.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheckExp.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -39,10 +39,10 @@
 
 public class AccessCheckExp {
 
-    // Test that if module1 can read module2, but package p2 in module2 is not
-    // exported then class p1.c1 in module1 can not read p2.c2 in module2.
+    // Test that if module_one can read module_two, but package p2 in module_two is not
+    // exported then class p1.c1 in module_one can not read p2.c2 in module_two.
     public static void main(String args[]) throws Throwable {
-        Object m1, m2;
+        Object m1x, m2x;
 
         // Get the java.lang.reflect.Module object for module java.base.
         Class jlObject = Class.forName("java.lang.Object");
@@ -54,28 +54,28 @@
         ClassLoader this_cldr = AccessCheckExp.class.getClassLoader();
 
         // Define a module for p1.
-        m1 = ModuleHelper.ModuleObject("module1", this_cldr, new String[] { "p1" });
-        assertNotNull(m1, "Module should not be null");
-        ModuleHelper.DefineModule(m1, "9.0", "m1/here", new String[] { "p1" });
-        ModuleHelper.AddReadsModule(m1, jlObject_jlrM);
+        m1x = ModuleHelper.ModuleObject("module_one", this_cldr, new String[] { "p1" });
+        assertNotNull(m1x, "Module should not be null");
+        ModuleHelper.DefineModule(m1x, "9.0", "m1x/here", new String[] { "p1" });
+        ModuleHelper.AddReadsModule(m1x, jlObject_jlrM);
 
         // Define a module for p2.
-        m2 = ModuleHelper.ModuleObject("module2", this_cldr, new String[] { "p2" });
-        assertNotNull(m2, "Module should not be null");
-        ModuleHelper.DefineModule(m2, "9.0", "m2/there", new String[] { "p2" });
-        ModuleHelper.AddReadsModule(m2, jlObject_jlrM);
+        m2x = ModuleHelper.ModuleObject("module_two", this_cldr, new String[] { "p2" });
+        assertNotNull(m2x, "Module should not be null");
+        ModuleHelper.DefineModule(m2x, "9.0", "m2x/there", new String[] { "p2" });
+        ModuleHelper.AddReadsModule(m2x, jlObject_jlrM);
 
-        // Make package p1 in m1 visible to everyone.
-        ModuleHelper.AddModuleExportsToAll(m1, "p1");
+        // Make package p1 in m1x visible to everyone.
+        ModuleHelper.AddModuleExportsToAll(m1x, "p1");
 
         // p1.c1's ctor tries to call a method in p2.c2, but p2.c2 is not
         // exported.  So should get IllegalAccessError.
-        ModuleHelper.AddReadsModule(m1, m2);
+        ModuleHelper.AddReadsModule(m1x, m2x);
 
         Class p1_c1_class = Class.forName("p1.c1");
         try {
             p1_c1_class.newInstance();
-            throw new RuntimeException("Failed to get IAE (p2 in m2 is not exported");
+            throw new RuntimeException("Failed to get IAE (p2 in m2x is not exported");
         } catch (IllegalAccessError f) {
             System.out.println(f.getMessage());
             if (!f.getMessage().contains("does not export")) {
--- a/hotspot/test/runtime/modules/AccessCheckJavaBase.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheckJavaBase.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -38,16 +38,16 @@
 
 public class AccessCheckJavaBase {
 
-    // Test that a class defined to module2 always can read java.base.
+    // Test that a class defined to module_two always can read java.base.
     public static void main(String args[]) throws Throwable {
         // Get the class loader for AccessCheckJavaBase and assume it's also used to
         // load class p2.c2.
         ClassLoader this_cldr = AccessCheckJavaBase.class.getClassLoader();
 
         // Define a module for p2.
-        Object m2 = ModuleHelper.ModuleObject("module2", this_cldr, new String[] { "p2" });
-        assertNotNull(m2, "Module should not be null");
-        ModuleHelper.DefineModule(m2, "9.0", "m2/there", new String[] { "p2" });
+        Object m2x = ModuleHelper.ModuleObject("module_two", this_cldr, new String[] { "p2" });
+        assertNotNull(m2x, "Module should not be null");
+        ModuleHelper.DefineModule(m2x, "9.0", "m2x/there", new String[] { "p2" });
 
         // p2.c2 can read its superclass java.lang.Object defined within java.base
         try {
--- a/hotspot/test/runtime/modules/AccessCheckRead.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheckRead.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -39,10 +39,10 @@
 
 public class AccessCheckRead {
 
-    // Test that a class in a package in module1 cannot access a class in
-    // a package n module2 if module1 cannot read module2.
+    // Test that a class in a package in module_one cannot access a class in
+    // a package in module_two if module_one cannot read module_two.
     public static void main(String args[]) throws Throwable {
-        Object m1, m2;
+        Object m1x, m2x;
 
         // Get the java.lang.reflect.Module object for module java.base.
         Class jlObject = Class.forName("java.lang.Object");
@@ -54,19 +54,19 @@
         ClassLoader this_cldr = AccessCheckRead.class.getClassLoader();
 
         // Define a module for p1.
-        m1 = ModuleHelper.ModuleObject("module1", this_cldr, new String[] { "p1" });
-        assertNotNull(m1, "Module should not be null");
-        ModuleHelper.DefineModule(m1, "9.0", "m1/here", new String[] { "p1" });
-        ModuleHelper.AddReadsModule(m1, jlObject_jlrM);
+        m1x = ModuleHelper.ModuleObject("module_one", this_cldr, new String[] { "p1" });
+        assertNotNull(m1x, "Module should not be null");
+        ModuleHelper.DefineModule(m1x, "9.0", "m1x/here", new String[] { "p1" });
+        ModuleHelper.AddReadsModule(m1x, jlObject_jlrM);
 
         // Define a module for p2.
-        m2 = ModuleHelper.ModuleObject("module2", this_cldr, new String[] { "p2" });
-        assertNotNull(m2, "Module should not be null");
-        ModuleHelper.DefineModule(m2, "9.0", "m2/there", new String[] { "p2" });
-        ModuleHelper.AddReadsModule(m2, jlObject_jlrM);
+        m2x = ModuleHelper.ModuleObject("module_two", this_cldr, new String[] { "p2" });
+        assertNotNull(m2x, "Module should not be null");
+        ModuleHelper.DefineModule(m2x, "9.0", "m2x/there", new String[] { "p2" });
+        ModuleHelper.AddReadsModule(m2x, jlObject_jlrM);
 
-        // Make package p1 in m1 visible to everyone.
-        ModuleHelper.AddModuleExportsToAll(m1, "p1");
+        // Make package p1 in m1x visible to everyone.
+        ModuleHelper.AddModuleExportsToAll(m1x, "p1");
 
         Class p1_c1_class = Class.forName("p1.c1");
 
@@ -74,7 +74,7 @@
         // cannot read p2's module.  So should get IllegalAccessError.
         try {
             p1_c1_class.newInstance();
-            throw new RuntimeException("Failed to get IAE (m1 can't read m2)");
+            throw new RuntimeException("Failed to get IAE (m1x can't read m2x)");
         } catch (IllegalAccessError e) {
             System.out.println(e.getMessage());
             if (!e.getMessage().contains("does not read") ||
--- a/hotspot/test/runtime/modules/AccessCheckSuper.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheckSuper.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -48,17 +48,17 @@
         ClassLoader this_cldr = AccessCheckSuper.class.getClassLoader();
 
         // Define a module for p2.
-        Object m2 = ModuleHelper.ModuleObject("module2", this_cldr, new String[] { "p2" });
-        assertNotNull(m2, "Module should not be null");
-        ModuleHelper.DefineModule(m2, "9.0", "m2/there", new String[] { "p2" });
+        Object m2x = ModuleHelper.ModuleObject("module_two", this_cldr, new String[] { "p2" });
+        assertNotNull(m2x, "Module should not be null");
+        ModuleHelper.DefineModule(m2x, "9.0", "m2x/there", new String[] { "p2" });
 
         // Define a module for p3.
-        Object m3 = ModuleHelper.ModuleObject("module3", this_cldr, new String[] { "p3" });
-        assertNotNull(m3, "Module should not be null");
-        ModuleHelper.DefineModule(m3, "9.0", "m3/there", new String[] { "p3" });
+        Object m3x = ModuleHelper.ModuleObject("module_three", this_cldr, new String[] { "p3" });
+        assertNotNull(m3x, "Module should not be null");
+        ModuleHelper.DefineModule(m3x, "9.0", "m3x/there", new String[] { "p3" });
 
-        // Since a readability edge has not been established between module2
-        // and module3, p3.c3 cannot read its superclass p2.c2.
+        // Since a readability edge has not been established between module_two
+        // and module_three, p3.c3 cannot read its superclass p2.c2.
         try {
             Class p3_c3_class = Class.forName("p3.c3");
             throw new RuntimeException("Failed to get IAE (can't read superclass)");
--- a/hotspot/test/runtime/modules/AccessCheckUnnamed.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheckUnnamed.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -42,7 +42,7 @@
     // Test that a class in the unnamed module can not access a package in a
     // named module that has not been unqualifiedly exported.
     public static void main(String args[]) throws Throwable {
-        Object m1, m2;
+        Object m1x, m2x;
 
         // Get the java.lang.reflect.Module object for module java.base.
         Class jlObject = Class.forName("java.lang.Object");
@@ -54,17 +54,17 @@
         ClassLoader this_cldr = AccessCheckUnnamed.class.getClassLoader();
 
         // Define a module for p2.
-        m2 = ModuleHelper.ModuleObject("module2", this_cldr, new String[] { "p2" });
-        assertNotNull(m2, "Module should not be null");
-        ModuleHelper.DefineModule(m2, "9.0", "m2/there", new String[] { "p2" });
-        ModuleHelper.AddReadsModule(m2, jlObject_jlrM);
+        m2x = ModuleHelper.ModuleObject("module_two", this_cldr, new String[] { "p2" });
+        assertNotNull(m2x, "Module should not be null");
+        ModuleHelper.DefineModule(m2x, "9.0", "m2x/there", new String[] { "p2" });
+        ModuleHelper.AddReadsModule(m2x, jlObject_jlrM);
 
         // p1.c1's ctor tries to call a method in p2.c2.  This should fail because
         // p1 is in the unnamed module and p2.c2 is not unqualifiedly exported.
         Class p1_c1_class = Class.forName("p1.c1");
         try {
             Object c1_obj = p1_c1_class.newInstance();
-            throw new RuntimeException("Failed to get IAE (p2 in m2 is not exported to unnamed module)");
+            throw new RuntimeException("Failed to get IAE (p2 in m2x is not exported to unnamed module)");
         } catch (IllegalAccessError f) {
             System.out.println(f.getMessage());
             if (!f.getMessage().contains("does not export p2 to unnamed module")) {
--- a/hotspot/test/runtime/modules/AccessCheckWorks.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/AccessCheckWorks.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -39,11 +39,11 @@
 
 public class AccessCheckWorks {
 
-    // Check that a class in a package in module1 can successfully access a
-    // class in module2 when module1 can read module2 and the class's package
+    // Check that a class in a package in module_one can successfully access a
+    // class in module_two when module_one can read module_two and the class's package
     // has been exported.
     public static void main(String args[]) throws Throwable {
-        Object m1, m2;
+        Object m1x, m2x;
 
         // Get the java.lang.reflect.Module object for module java.base.
         Class jlObject = Class.forName("java.lang.Object");
@@ -55,24 +55,24 @@
         ClassLoader this_cldr = AccessCheckWorks.class.getClassLoader();
 
         // Define a module for p1.
-        m1 = ModuleHelper.ModuleObject("module1", this_cldr, new String[] { "p1" });
-        assertNotNull(m1, "Module should not be null");
-        ModuleHelper.DefineModule(m1, "9.0", "m1/here", new String[] { "p1" });
-        ModuleHelper.AddReadsModule(m1, jlObject_jlrM);
+        m1x = ModuleHelper.ModuleObject("module_one", this_cldr, new String[] { "p1" });
+        assertNotNull(m1x, "Module should not be null");
+        ModuleHelper.DefineModule(m1x, "9.0", "m1x/here", new String[] { "p1" });
+        ModuleHelper.AddReadsModule(m1x, jlObject_jlrM);
 
         // Define a module for p2.
-        m2 = ModuleHelper.ModuleObject("module2", this_cldr, new String[] { "p2" });
-        assertNotNull(m2, "Module should not be null");
-        ModuleHelper.DefineModule(m2, "9.0", "m2/there", new String[] { "p2" });
-        ModuleHelper.AddReadsModule(m2, jlObject_jlrM);
+        m2x = ModuleHelper.ModuleObject("module_two", this_cldr, new String[] { "p2" });
+        assertNotNull(m2x, "Module should not be null");
+        ModuleHelper.DefineModule(m2x, "9.0", "m2x/there", new String[] { "p2" });
+        ModuleHelper.AddReadsModule(m2x, jlObject_jlrM);
 
-        // Make package p1 in m1 visible to everyone.
-        ModuleHelper.AddModuleExportsToAll(m1, "p1");
+        // Make package p1 in m1x visible to everyone.
+        ModuleHelper.AddModuleExportsToAll(m1x, "p1");
 
         // p1.c1's ctor tries to call a method in p2.c2.  This should work because
         // p1's module can read p2's module and p2 is exported to p1's module.
-        ModuleHelper.AddReadsModule(m1, m2);
-        ModuleHelper.AddModuleExports(m2, "p2", m1);
+        ModuleHelper.AddReadsModule(m1x, m2x);
+        ModuleHelper.AddModuleExports(m2x, "p2", m1x);
         Class p1_c1_class = Class.forName("p1.c1");
         p1_c1_class.newInstance();
     }
--- a/hotspot/test/runtime/modules/CCE_module_msg.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/CCE_module_msg.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -83,21 +83,21 @@
         ClassLoader this_cldr = CCE_module_msg.class.getClassLoader();
 
         // Define a module for p2.
-        Object m2 = ModuleHelper.ModuleObject("module2", this_cldr, new String[] { "p2" });
-        assertNotNull(m2, "Module should not be null");
-        ModuleHelper.DefineModule(m2, "9.0", "m2/there", new String[] { "p2" });
-        ModuleHelper.AddReadsModule(m2, jlObject_jlrM);
+        Object m2x = ModuleHelper.ModuleObject("module_two", this_cldr, new String[] { "p2" });
+        assertNotNull(m2x, "Module should not be null");
+        ModuleHelper.DefineModule(m2x, "9.0", "m2x/there", new String[] { "p2" });
+        ModuleHelper.AddReadsModule(m2x, jlObject_jlrM);
 
         try {
-            ModuleHelper.AddModuleExportsToAll(m2, "p2");
+            ModuleHelper.AddModuleExportsToAll(m2x, "p2");
             Object p2Obj = new p2.c2();
             System.out.println((String)p2Obj);
             throw new RuntimeException("ClassCastException wasn't thrown, test failed.");
         } catch (ClassCastException cce) {
             String exception = cce.getMessage();
             System.out.println(exception);
-            if (exception.contains("module2/p2.c2") ||
-                !(exception.contains("module2@") &&
+            if (exception.contains("module_two/p2.c2") ||
+                !(exception.contains("module_two@") &&
                   exception.contains("/p2.c2 cannot be cast to java.base/java.lang.String"))) {
                 throw new RuntimeException("Wrong message: " + exception);
             }
--- a/hotspot/test/runtime/modules/ExportTwice.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/ExportTwice.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -44,7 +44,7 @@
     // Also, check that a package can be exported to a specific package and then
     // exported unqualifiedly.
     public static void main(String args[]) throws Throwable {
-        Object m1, m2, m3;
+        Object m1x, m2x, m3x;
 
         // Get the java.lang.reflect.Module object for module java.base.
         Class jlObject = Class.forName("java.lang.Object");
@@ -56,37 +56,37 @@
         ClassLoader this_cldr = ExportTwice.class.getClassLoader();
 
         // Define a module for p1.
-        m1 = ModuleHelper.ModuleObject("module1", this_cldr, new String[] { "p1" });
-        assertNotNull(m1, "Module should not be null");
-        ModuleHelper.DefineModule(m1, "9.0", "m1/here", new String[] { "p1" });
-        ModuleHelper.AddReadsModule(m1, jlObject_jlrM);
+        m1x = ModuleHelper.ModuleObject("module_one", this_cldr, new String[] { "p1" });
+        assertNotNull(m1x, "Module should not be null");
+        ModuleHelper.DefineModule(m1x, "9.0", "m1x/here", new String[] { "p1" });
+        ModuleHelper.AddReadsModule(m1x, jlObject_jlrM);
 
         // Define a module for p2.
-        m2 = ModuleHelper.ModuleObject("module2", this_cldr, new String[] { "p2" });
-        assertNotNull(m2, "Module should not be null");
-        ModuleHelper.DefineModule(m2, "9.0", "m2/there", new String[] { "p2" });
-        ModuleHelper.AddReadsModule(m2, jlObject_jlrM);
+        m2x = ModuleHelper.ModuleObject("module_two", this_cldr, new String[] { "p2" });
+        assertNotNull(m2x, "Module should not be null");
+        ModuleHelper.DefineModule(m2x, "9.0", "m2x/there", new String[] { "p2" });
+        ModuleHelper.AddReadsModule(m2x, jlObject_jlrM);
 
         // Define a module for p3.
-        m3 = ModuleHelper.ModuleObject("module3", this_cldr, new String[] { "p3" });
-        assertNotNull(m3, "Module should not be null");
-        ModuleHelper.DefineModule(m3, "9.0", "m3/there", new String[] { "p3" });
-        ModuleHelper.AddReadsModule(m3, jlObject_jlrM);
+        m3x = ModuleHelper.ModuleObject("module_three", this_cldr, new String[] { "p3" });
+        assertNotNull(m3x, "Module should not be null");
+        ModuleHelper.DefineModule(m3x, "9.0", "m3x/there", new String[] { "p3" });
+        ModuleHelper.AddReadsModule(m3x, jlObject_jlrM);
 
-        // Make package p1 in m1 visible to everyone.
-        ModuleHelper.AddModuleExportsToAll(m1, "p1");
+        // Make package p1 in m1x visible to everyone.
+        ModuleHelper.AddModuleExportsToAll(m1x, "p1");
 
-        // Try to export p1 only to m2 after it was exported unqualifiedly.  It
+        // Try to export p1 only to m2x after it was exported unqualifiedly.  It
         // should silently succeed.
-        ModuleHelper.AddModuleExports(m1, "p1", m2);
+        ModuleHelper.AddModuleExports(m1x, "p1", m2x);
 
-        // Export p2 to m3 then export it again unqualifiedly.
-        ModuleHelper.AddModuleExports(m2, "p2", m3);
-        ModuleHelper.AddModuleExportsToAll(m2, "p2");
+        // Export p2 to m3x then export it again unqualifiedly.
+        ModuleHelper.AddModuleExports(m2x, "p2", m3x);
+        ModuleHelper.AddModuleExportsToAll(m2x, "p2");
 
         // p1.c1's ctor tries to call a method in p2.c2.  This should work because
         // p1's module can read p2's module and p2 is now exported unqualifiedly.
-        ModuleHelper.AddReadsModule(m1, m2);
+        ModuleHelper.AddReadsModule(m1x, m2x);
         Class p1_c1_class = Class.forName("p1.c1");
         p1_c1_class.newInstance();
     }
--- a/hotspot/test/runtime/modules/IgnoreModulePropertiesTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/IgnoreModulePropertiesTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -67,8 +67,8 @@
     }
 
     public static void main(String[] args) throws Exception {
-        testOption("--add-modules", "java.sqlx", "jdk.module.addmods.0", "java.lang.module.ResolutionException");
-        testOption("--limit-modules", "java.sqlx", "jdk.module.limitmods", "java.lang.module.ResolutionException");
+        testOption("--add-modules", "java.sqlx", "jdk.module.addmods.0", "java.lang.module.FindException");
+        testOption("--limit-modules", "java.sqlx", "jdk.module.limitmods", "java.lang.module.FindException");
         testOption("--add-reads", "xyzz=yyzd", "jdk.module.addreads.0", "WARNING: Unknown module: xyzz");
         testOption("--add-exports", "java.base/xyzz=yyzd", "jdk.module.addexports.0",
                    "WARNING: package xyzz not in java.base");
--- a/hotspot/test/runtime/modules/JVMAddModuleExportToAllUnnamed.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/JVMAddModuleExportToAllUnnamed.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -39,10 +39,10 @@
 
 public class JVMAddModuleExportToAllUnnamed {
 
-    // Check that a class in a package in module1 cannot access a class
+    // Check that a class in a package in module_one cannot access a class
     // that is in the unnamed module if the accessing package is strict.
     public static void main(String args[]) throws Throwable {
-        Object m1;
+        Object m1x;
 
         // Get the java.lang.reflect.Module object for module java.base.
         Class jlObject = Class.forName("java.lang.Object");
@@ -54,13 +54,13 @@
         ClassLoader this_cldr = JVMAddModuleExportToAllUnnamed.class.getClassLoader();
 
         // Define a module for p1.
-        m1 = ModuleHelper.ModuleObject("module1", this_cldr, new String[] { "p1" });
-        assertNotNull(m1, "Module should not be null");
-        ModuleHelper.DefineModule(m1, "9.0", "m1/here", new String[] { "p1" });
-        ModuleHelper.AddReadsModule(m1, jlObject_jlrM);
+        m1x = ModuleHelper.ModuleObject("module_one", this_cldr, new String[] { "p1" });
+        assertNotNull(m1x, "Module should not be null");
+        ModuleHelper.DefineModule(m1x, "9.0", "m1x/here", new String[] { "p1" });
+        ModuleHelper.AddReadsModule(m1x, jlObject_jlrM);
 
-        // Make package p1 in m1 visible to everyone.
-        ModuleHelper.AddModuleExportsToAll(m1, "p1");
+        // Make package p1 in m1x visible to everyone.
+        ModuleHelper.AddModuleExportsToAll(m1x, "p1");
 
         // p1.c1's ctor tries to call a method in p2.c2.  This should not work
         // because p2 is in the unnamed module and p1.c1 is strict.
--- a/hotspot/test/runtime/modules/JVMAddModuleExportsToAll.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/JVMAddModuleExportsToAll.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -43,7 +43,7 @@
     // and then test that a class in the unnamed module can access a package in
     // a named module that has been exported unqualifiedly.
     public static void main(String args[]) throws Throwable {
-        Object m1, m2, m3;
+        Object m1x, m2x, m3x;
 
         // Get the java.lang.reflect.Module object for module java.base.
         Class jlObject = Class.forName("java.lang.Object");
@@ -55,16 +55,16 @@
         ClassLoader this_cldr = JVMAddModuleExportsToAll.class.getClassLoader();
 
         // Define a module for p3.
-        m1 = ModuleHelper.ModuleObject("module1", this_cldr, new String[] { "p3" });
-        assertNotNull(m1, "Module should not be null");
-        ModuleHelper.DefineModule(m1, "9.0", "m1/there", new String[] { "p3" });
-        ModuleHelper.AddReadsModule(m1, jlObject_jlrM);
+        m1x = ModuleHelper.ModuleObject("module_one", this_cldr, new String[] { "p3" });
+        assertNotNull(m1x, "Module should not be null");
+        ModuleHelper.DefineModule(m1x, "9.0", "m1x/there", new String[] { "p3" });
+        ModuleHelper.AddReadsModule(m1x, jlObject_jlrM);
 
         // Define a module for p2.
-        m2 = ModuleHelper.ModuleObject("module2", this_cldr, new String[] { "p2" });
-        assertNotNull(m2, "Module should not be null");
-        ModuleHelper.DefineModule(m2, "9.0", "m2/there", new String[] { "p2" });
-        ModuleHelper.AddReadsModule(m2, jlObject_jlrM);
+        m2x = ModuleHelper.ModuleObject("module_two", this_cldr, new String[] { "p2" });
+        assertNotNull(m2x, "Module should not be null");
+        ModuleHelper.DefineModule(m2x, "9.0", "m2x/there", new String[] { "p2" });
+        ModuleHelper.AddReadsModule(m2x, jlObject_jlrM);
 
         try {
             ModuleHelper.AddModuleExportsToAll((Module)null, "p2");
@@ -74,7 +74,7 @@
         }
 
         try {
-            ModuleHelper.AddModuleExportsToAll(m2, null);
+            ModuleHelper.AddModuleExportsToAll(m2x, null);
             throw new RuntimeException("Failed to get the expected NPE for null package");
         } catch(NullPointerException e) {
             // Expected
@@ -88,26 +88,26 @@
         }
 
         try {
-            ModuleHelper.AddModuleExportsToAll(m2, "p3");
+            ModuleHelper.AddModuleExportsToAll(m2x, "p3");
             throw new RuntimeException("Failed to get the expected IAE for package that is in another module");
         } catch(IllegalArgumentException e) {
             // Expected
         }
 
         try {
-            ModuleHelper.AddModuleExportsToAll(m2, "p4");
+            ModuleHelper.AddModuleExportsToAll(m2x, "p4");
             throw new RuntimeException("Failed to get the expected IAE for package not in any module");
         } catch(IllegalArgumentException e) {
             // Expected
         }
 
-        // Export package p2 in m2 unqualifiedly. Then, do a qualified export
-        // of p2 in m2 to m3.  This should not affect the unqualified export.
-        m3 = ModuleHelper.ModuleObject("module3", this_cldr, new String[] { "p4" });
-        assertNotNull(m3, "Module m3 should not be null");
-        ModuleHelper.DefineModule(m3, "9.0", "m3/there", new String[] { "p4" });
-        ModuleHelper.AddModuleExportsToAll(m2, "p2");
-        ModuleHelper.AddModuleExports(m2, "p2", m3);
+        // Export package p2 in m2x unqualifiedly. Then, do a qualified export
+        // of p2 in m2x to m3x.  This should not affect the unqualified export.
+        m3x = ModuleHelper.ModuleObject("module_three", this_cldr, new String[] { "p4" });
+        assertNotNull(m3x, "Module m3x should not be null");
+        ModuleHelper.DefineModule(m3x, "9.0", "m3x/there", new String[] { "p4" });
+        ModuleHelper.AddModuleExportsToAll(m2x, "p2");
+        ModuleHelper.AddModuleExports(m2x, "p2", m3x);
 
         // p1.c1's ctor tries to call a method in p2.c2.  This should succeed because
         // p1 is in an unnamed module and p2.c2 is exported unqualifiedly.
--- a/hotspot/test/runtime/modules/JVMAddModulePackage.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/JVMAddModulePackage.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -40,25 +40,25 @@
     public static void main(String args[]) throws Throwable {
         MyClassLoader cl1 = new MyClassLoader();
         MyClassLoader cl3 = new MyClassLoader();
-        Object module1, module2, module3;
+        Object module_one, module_two, module_three;
         boolean result;
 
-        module1 = ModuleHelper.ModuleObject("module1", cl1, new String[] { "mypackage" });
-        assertNotNull(module1, "Module should not be null");
-        ModuleHelper.DefineModule(module1, "9.0", "module1/here", new String[] { "mypackage" });
-        module2 = ModuleHelper.ModuleObject("module2", cl1, new String[] { "yourpackage" });
-        assertNotNull(module2, "Module should not be null");
-        ModuleHelper.DefineModule(module2, "9.0", "module2/here", new String[] { "yourpackage" });
-        module3 = ModuleHelper.ModuleObject("module3", cl3, new String[] { "package/num3" });
-        assertNotNull(module3, "Module should not be null");
-        ModuleHelper.DefineModule(module3, "9.0", "module3/here", new String[] { "package/num3" });
+        module_one = ModuleHelper.ModuleObject("module_one", cl1, new String[] { "mypackage" });
+        assertNotNull(module_one, "Module should not be null");
+        ModuleHelper.DefineModule(module_one, "9.0", "module_one/here", new String[] { "mypackage" });
+        module_two = ModuleHelper.ModuleObject("module_two", cl1, new String[] { "yourpackage" });
+        assertNotNull(module_two, "Module should not be null");
+        ModuleHelper.DefineModule(module_two, "9.0", "module_two/here", new String[] { "yourpackage" });
+        module_three = ModuleHelper.ModuleObject("module_three", cl3, new String[] { "package/num3" });
+        assertNotNull(module_three, "Module should not be null");
+        ModuleHelper.DefineModule(module_three, "9.0", "module_three/here", new String[] { "package/num3" });
 
         // Simple call
-        ModuleHelper.AddModulePackage(module1, "new_package");
+        ModuleHelper.AddModulePackage(module_one, "new_package");
 
         // Add a package and export it
-        ModuleHelper.AddModulePackage(module1, "package/num3");
-        ModuleHelper.AddModuleExportsToAll(module1, "package/num3");
+        ModuleHelper.AddModulePackage(module_one, "package/num3");
+        ModuleHelper.AddModuleExportsToAll(module_one, "package/num3");
 
         // Null module argument, expect an NPE
         try {
@@ -78,7 +78,7 @@
 
         // Null package argument, expect an NPE
         try {
-            ModuleHelper.AddModulePackage(module1, null);
+            ModuleHelper.AddModulePackage(module_one, null);
             throw new RuntimeException("Failed to get the expected NPE");
         } catch(NullPointerException e) {
             // Expected
@@ -86,7 +86,7 @@
 
         // Existing package, expect an ISE
         try {
-            ModuleHelper.AddModulePackage(module1, "yourpackage");
+            ModuleHelper.AddModulePackage(module_one, "yourpackage");
             throw new RuntimeException("Failed to get the expected ISE");
         } catch(IllegalStateException e) {
             // Expected
@@ -94,7 +94,7 @@
 
         // Invalid package name, expect an IAE
         try {
-            ModuleHelper.AddModulePackage(module1, "your.package");
+            ModuleHelper.AddModulePackage(module_one, "your.package");
             throw new RuntimeException("Failed to get the expected IAE");
         } catch(IllegalArgumentException e) {
             // Expected
@@ -102,7 +102,7 @@
 
         // Invalid package name, expect an IAE
         try {
-            ModuleHelper.AddModulePackage(module1, ";your/package");
+            ModuleHelper.AddModulePackage(module_one, ";your/package");
             throw new RuntimeException("Failed to get the expected IAE");
         } catch(IllegalArgumentException e) {
             // Expected
@@ -110,7 +110,7 @@
 
         // Invalid package name, expect an IAE
         try {
-            ModuleHelper.AddModulePackage(module1, "7[743");
+            ModuleHelper.AddModulePackage(module_one, "7[743");
             throw new RuntimeException("Failed to get the expected IAE");
         } catch(IllegalArgumentException e) {
             // Expected
@@ -118,7 +118,7 @@
 
         // Empty package name, expect an IAE
         try {
-            ModuleHelper.AddModulePackage(module1, "");
+            ModuleHelper.AddModulePackage(module_one, "");
             throw new RuntimeException("Failed to get the expected IAE");
         } catch(IllegalArgumentException e) {
             // Expected
@@ -126,8 +126,8 @@
 
         // Add package named "java" to an module defined to a class loader other than the boot or platform loader.
         try {
-            // module1 is defined to a MyClassLoader class loader.
-            ModuleHelper.AddModulePackage(module1, "java/foo");
+            // module_one is defined to a MyClassLoader class loader.
+            ModuleHelper.AddModulePackage(module_one, "java/foo");
             throw new RuntimeException("Failed to get the expected IAE");
         } catch(IllegalArgumentException e) {
             if (!e.getMessage().contains("prohibited package name")) {
@@ -136,10 +136,10 @@
         }
 
         // Package "javabar" should be ok
-        ModuleHelper.AddModulePackage(module1, "javabar");
+        ModuleHelper.AddModulePackage(module_one, "javabar");
 
         // Package named "java" defined to the boot class loader, should be ok
-        Object module_javabase = module1.getClass().getModule();
+        Object module_javabase = module_one.getClass().getModule();
         ModuleHelper.AddModulePackage(module_javabase, "java/foo");
 
         // Package named "java" defined to the platform class loader, should be ok
--- a/hotspot/test/runtime/modules/JVMDefineModule.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/JVMDefineModule.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -49,7 +49,7 @@
 /* Invalid test, won't compile.
         // Invalid classloader argument, expect an IAE
         try {
-            m = ModuleHelper.ModuleObject("mymodule1", new Object(), new String[] { "mypackage1" });
+            m = ModuleHelper.ModuleObject("mymodule_one", new Object(), new String[] { "mypackage1" });
             ModuleHelper.DefineModule(m,  "9.0", "mymodule/here", new String[] { "mypackage1" });
             throw new RuntimeException("Failed to get expected IAE for bad loader");
         } catch(IllegalArgumentException e) {
--- a/hotspot/test/runtime/modules/JVMGetModuleByPkgName.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/JVMGetModuleByPkgName.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -79,10 +79,10 @@
         }
 
         MyClassLoader cl1 = new MyClassLoader();
-        Module module1 = (Module)ModuleHelper.ModuleObject("module1", cl1, new String[] { "mypackage" });
-        assertNotNull(module1, "Module should not be null");
-        ModuleHelper.DefineModule(module1, "9.0", "module1/here", new String[] { "mypackage" });
-        if (ModuleHelper.GetModuleByPackageName(cl1, "mypackage") != module1) {
+        Module module_one = (Module)ModuleHelper.ModuleObject("module_one", cl1, new String[] { "mypackage" });
+        assertNotNull(module_one, "Module should not be null");
+        ModuleHelper.DefineModule(module_one, "9.0", "module_one/here", new String[] { "mypackage" });
+        if (ModuleHelper.GetModuleByPackageName(cl1, "mypackage") != module_one) {
             throw new RuntimeException("Wrong module returned for cl1 mypackage");
         }
     }
--- a/hotspot/test/runtime/modules/ModuleHelper.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/ModuleHelper.java	Wed Jul 05 22:52:01 2017 +0200
@@ -84,7 +84,7 @@
         }
 
         ModuleDescriptor descriptor =
-            ModuleDescriptor.module(name).contains(pkg_set).build();
+            ModuleDescriptor.newModule(name).packages(pkg_set).build();
         URI uri = URI.create("module:/" + name);
 
         return java.lang.reflect.ModuleHelper.newModule(loader, descriptor);
--- a/hotspot/test/runtime/modules/ModuleOptionsTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/ModuleOptionsTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -43,7 +43,7 @@
         ProcessBuilder pb = ProcessTools.createJavaProcessBuilder(
             "--add-modules=i_dont_exist", "--add-modules=java.base", "-version");
         OutputAnalyzer output = new OutputAnalyzer(pb.start());
-        output.shouldContain("ResolutionException");
+        output.shouldContain("FindException");
         output.shouldContain("i_dont_exist");
         output.shouldHaveExitValue(1);
 
--- a/hotspot/test/runtime/modules/ModuleStress/CustomSystemClassLoader.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/ModuleStress/CustomSystemClassLoader.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -22,7 +22,7 @@
  */
 
 /**
- * A custom system ClassLoader to define the module "m2" to during iterations of
+ * A custom system ClassLoader to define the module "m2x" to during iterations of
  * differing test runs within the test ModuleStress.java
  */
 public class CustomSystemClassLoader extends ClassLoader {
--- a/hotspot/test/runtime/modules/ModuleStress/ModuleNonBuiltinCLMain.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/ModuleStress/ModuleNonBuiltinCLMain.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -35,15 +35,15 @@
 import java.util.Set;
 
 //
-// ClassLoader1 --> defines m1 --> packages p1
-// ClassLoader2 --> defines m2 --> packages p2
-// Java System Class Loader --> defines m3 --> packages p3
+// ClassLoader1 --> defines m1x --> packages p1
+// ClassLoader2 --> defines m2x --> packages p2
+// Java System Class Loader --> defines m3x --> packages p3
 //
-// m1 can read m2
-// package p2 in m2 is exported to m1 and m3
+// m1x can read m2x
+// package p2 in m2x is exported to m1x and m3x
 //
-// class p1.c1 defined in m1 tries to access p2.c2 defined in m2
-// Access allowed since m1 can read m2 and package p2 is exported to m1.
+// class p1.c1 defined in m1x tries to access p2.c2 defined in m2x
+// Access allowed since m1x can read m2x and package p2 is exported to m1x.
 //
 public class ModuleNonBuiltinCLMain {
 
@@ -52,62 +52,62 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
-        // Can read:          java.base, m2
+        // Define module:     m1x
+        // Can read:          java.base, m2x
         // Packages:          p1
         // Packages exported: p1 is exported to unqualifiedly
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
+                        .requires("m2x")
                         .exports("p1")
                         .build();
 
-        // Define module:     m2
-        // Can read:          java.base, m3
+        // Define module:     m2x
+        // Can read:          java.base, m3x
         // Packages:          p2
-        // Packages exported: package p2 is exported to m1 and m3
+        // Packages exported: package p2 is exported to m1x and m3x
         Set<String> targets = new HashSet<>();
-        targets.add("m1");
-        targets.add("m3");
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        targets.add("m1x");
+        targets.add("m3x");
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
-                        .requires("m3")
+                        .requires("m3x")
                         .exports("p2", targets)
                         .build();
 
-        // Define module:     m3
+        // Define module:     m3x
         // Can read:          java.base
         // Packages:          p3
         // Packages exported: none
-        ModuleDescriptor descriptor_m3 =
-                ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor_m3x =
+                ModuleDescriptor.newModule("m3x")
                         .requires("java.base")
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2, descriptor_m3);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x, descriptor_m3x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to differing user defined class loaders for this test
         Map<String, ClassLoader> map = new HashMap<>();
         Loader1 cl1 = new Loader1();
         Loader2 cl2 = new Loader2();
         ClassLoader cl3 = ClassLoader.getSystemClassLoader();
-        map.put("m1", cl1);
-        map.put("m2", cl2);
-        map.put("m3", cl3);
+        map.put("m1x", cl1);
+        map.put("m2x", cl2);
+        map.put("m3x", cl3);
 
-        // Create Layer that contains m1 & m2
+        // Create Layer that contains m1x & m2x
         Layer layer = Layer.boot().defineModules(cf, map::get);
-        assertTrue(layer.findLoader("m1") == cl1);
-        assertTrue(layer.findLoader("m2") == cl2);
-        assertTrue(layer.findLoader("m3") == cl3);
+        assertTrue(layer.findLoader("m1x") == cl1);
+        assertTrue(layer.findLoader("m2x") == cl2);
+        assertTrue(layer.findLoader("m3x") == cl3);
         assertTrue(layer.findLoader("java.base") == null);
 
         // now use the same loader to load class p1.c1
@@ -115,7 +115,7 @@
         try {
             p1_c1_class.newInstance();
         } catch (IllegalAccessError e) {
-            throw new RuntimeException("Test Failed, an IAE should not be thrown since p2 is exported qualifiedly to m1");
+            throw new RuntimeException("Test Failed, an IAE should not be thrown since p2 is exported qualifiedly to m1x");
         }
     }
 
--- a/hotspot/test/runtime/modules/ModuleStress/ModuleSameCLMain.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/ModuleStress/ModuleSameCLMain.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -34,14 +34,14 @@
 import java.util.Set;
 
 //
-// ClassLoader1 --> defines m1 --> packages p1
-// ClassLoader1 --> defines m2 --> packages p2
+// ClassLoader1 --> defines m1x --> packages p1
+// ClassLoader1 --> defines m2x --> packages p2
 //
-// m1 can read m2
-// package p2 in m2 is exported to m1
+// m1x can read m2x
+// package p2 in m2x is exported to m1x
 //
-// class p1.c1 defined in m1 tries to access p2.c2 defined in m2
-// Access allowed since m1 can read m2 and package p2 is exported to m1.
+// class p1.c1 defined in m1x tries to access p2.c2 defined in m2x
+// Access allowed since m1x can read m2x and package p2 is exported to m1x.
 //
 public class ModuleSameCLMain {
 
@@ -50,45 +50,45 @@
     // publically defined classes within packages of those modules.
     public void createLayerOnBoot() throws Throwable {
 
-        // Define module:     m1
-        // Can read:          java.base, m2
+        // Define module:     m1x
+        // Can read:          java.base, m2x
         // Packages:          p1
         // Packages exported: p1 is exported to unqualifiedly
-        ModuleDescriptor descriptor_m1 =
-                ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor_m1x =
+                ModuleDescriptor.newModule("m1x")
                         .requires("java.base")
-                        .requires("m2")
+                        .requires("m2x")
                         .exports("p1")
                         .build();
 
-        // Define module:     m2
+        // Define module:     m2x
         // Can read:          java.base
         // Packages:          p2
-        // Packages exported: package p2 is exported to m1
-        ModuleDescriptor descriptor_m2 =
-                ModuleDescriptor.module("m2")
+        // Packages exported: package p2 is exported to m1x
+        ModuleDescriptor descriptor_m2x =
+                ModuleDescriptor.newModule("m2x")
                         .requires("java.base")
-                        .exports("p2", Set.of("m1"))
+                        .exports("p2", Set.of("m1x"))
                         .build();
 
         // Set up a ModuleFinder containing all modules for this layer.
-        ModuleFinder finder = ModuleLibrary.of(descriptor_m1, descriptor_m2);
+        ModuleFinder finder = ModuleLibrary.of(descriptor_m1x, descriptor_m2x);
 
-        // Resolves "m1"
+        // Resolves "m1x"
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1x"));
 
         // map each module to the same class loader for this test
         Map<String, ClassLoader> map = new HashMap<>();
         Loader1 cl1 = new Loader1();
-        map.put("m1", cl1);
-        map.put("m2", cl1);
+        map.put("m1x", cl1);
+        map.put("m2x", cl1);
 
-        // Create Layer that contains m1 & m2
+        // Create Layer that contains m1x & m2x
         Layer layer = Layer.boot().defineModules(cf, map::get);
-        assertTrue(layer.findLoader("m1") == cl1);
-        assertTrue(layer.findLoader("m2") == cl1);
+        assertTrue(layer.findLoader("m1x") == cl1);
+        assertTrue(layer.findLoader("m2x") == cl1);
         assertTrue(layer.findLoader("java.base") == null);
 
         // now use the same loader to load class p1.c1
@@ -96,7 +96,7 @@
         try {
             p1_c1_class.newInstance();
         } catch (IllegalAccessError e) {
-            throw new RuntimeException("Test Failed, an IAE should not be thrown since p2 is exported qualifiedly to m1");
+            throw new RuntimeException("Test Failed, an IAE should not be thrown since p2 is exported qualifiedly to m1x");
         }
     }
 
--- a/hotspot/test/runtime/modules/ModuleStress/ModuleStress.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/ModuleStress/ModuleStress.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -83,7 +83,7 @@
              InMemoryJavaCompiler.compile("p1.c1", source1), System.getProperty("test.classes"));
 
         // Test #2: Load two modules defined to the same customer class loader.
-        //   m1's module readability list and package p2's exportability should
+        //   m1x's module readability list and package p2's exportability should
         //   not be walked at a GC safepoint since both modules are defined to
         //   the same loader and thus have the exact same life cycle.
         pb = ProcessTools.createJavaProcessBuilder(
@@ -97,7 +97,7 @@
           .shouldHaveExitValue(0);
 
         // Test #3: Load two modules in differing custom class loaders.
-        //   m1's module readability list and package p2's exportability list must
+        //   m1x's module readability list and package p2's exportability list must
         //   be walked at a GC safepoint since both modules are defined to non-builtin
         //   class loaders which could die and thus be unloaded.
         pb = ProcessTools.createJavaProcessBuilder(
@@ -106,15 +106,15 @@
              "ModuleNonBuiltinCLMain");
 
         oa = new OutputAnalyzer(pb.start());
-        oa.shouldContain("module m1 reads list must be walked")
-          .shouldContain("package p2 defined in module m2, exports list must be walked")
-          .shouldNotContain("module m2 reads list must be walked")
+        oa.shouldContain("module m1x reads list must be walked")
+          .shouldContain("package p2 defined in module m2x, exports list must be walked")
+          .shouldNotContain("module m2x reads list must be walked")
           .shouldHaveExitValue(0);
 
         // Test #4: Load two modules in differing custom class loaders,
         //   of which one has been designated as the custom system class loader
         //   via -Djava.system.class.loader=CustomSystemClassLoader. Since
-        //   m3 is defined to the system class loader, m2's module readability
+        //   m3x is defined to the system class loader, m2x's module readability
         //   list does not have to be walked at a GC safepoint, but package p2's
         //   exportability list does.
         pb = ProcessTools.createJavaProcessBuilder(
@@ -124,8 +124,8 @@
              "ModuleNonBuiltinCLMain");
 
         oa = new OutputAnalyzer(pb.start());
-        oa.shouldContain("package p2 defined in module m2, exports list must be walked")
-          .shouldNotContain("module m2 reads list must be walked")
+        oa.shouldContain("package p2 defined in module m2x, exports list must be walked")
+          .shouldNotContain("module m2x reads list must be walked")
           .shouldHaveExitValue(0);
 
     }
--- a/hotspot/test/runtime/modules/ModuleStress/src/jdk.test/test/Main.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/ModuleStress/src/jdk.test/test/Main.java	Wed Jul 05 22:52:01 2017 +0200
@@ -48,7 +48,7 @@
 
         Configuration cf = layerBoot
                 .configuration()
-                .resolveRequires(ModuleFinder.of(), finder, Set.of(MODULE_NAME));
+                .resolve(ModuleFinder.of(), finder, Set.of(MODULE_NAME));
 
         Module testModule = Main.class.getModule();
         ClassLoader scl = ClassLoader.getSystemClassLoader();
--- a/hotspot/test/runtime/modules/ModuleStress/src/jdk.test/test/MainGC.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/ModuleStress/src/jdk.test/test/MainGC.java	Wed Jul 05 22:52:01 2017 +0200
@@ -48,7 +48,7 @@
 
         Configuration cf = layerBoot
                 .configuration()
-                .resolveRequires(ModuleFinder.of(), finder, Set.of(MODULE_NAME));
+                .resolve(ModuleFinder.of(), finder, Set.of(MODULE_NAME));
 
         Module testModule = MainGC.class.getModule();
         ClassLoader scl = ClassLoader.getSystemClassLoader();
--- a/hotspot/test/runtime/modules/PatchModule/PatchModuleDupModule.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/runtime/modules/PatchModule/PatchModuleDupModule.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -38,8 +38,8 @@
 
   public static void main(String args[]) throws Exception {
     ProcessBuilder pb = ProcessTools.createJavaProcessBuilder(
-      "--patch-module=module1=module1_dir",
-      "--patch-module=module1=module1_dir",
+      "--patch-module=module_one=module_one_dir",
+      "--patch-module=module_one=module_one_dir",
       "-version");
     OutputAnalyzer output = new OutputAnalyzer(pb.start());
     output.shouldContain("java.lang.ExceptionInInitializerError");
--- a/hotspot/test/serviceability/jvmti/GetModulesInfo/JvmtiGetAllModulesTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/serviceability/jvmti/GetModulesInfo/JvmtiGetAllModulesTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -82,12 +82,11 @@
         Asserts.assertEquals(Layer.boot().modules(), getModulesJVMTI());
 
         // Load a new named module
-        ModuleDescriptor descriptor
-                = ModuleDescriptor.module(MY_MODULE_NAME).build();
+        ModuleDescriptor descriptor = ModuleDescriptor.newModule(MY_MODULE_NAME).build();
         ModuleFinder finder = finderOf(descriptor);
         ClassLoader loader = new ClassLoader() {};
         Configuration parent = Layer.boot().configuration();
-        Configuration cf = parent.resolveRequires(finder, ModuleFinder.of(), Set.of(MY_MODULE_NAME));
+        Configuration cf = parent.resolve(finder, ModuleFinder.of(), Set.of(MY_MODULE_NAME));
         Layer my = Layer.boot().defineModules(cf, m -> loader);
 
         // Verify that the loaded module is indeed reported by JVMTI
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/serviceability/sa/LingeredAppWithLargeArray.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,31 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+
+import jdk.test.lib.apps.LingeredApp;
+
+public class LingeredAppWithLargeArray extends LingeredApp {
+    public static void main(String args[]) {
+        int[] hugeArray = new int[Integer.MAX_VALUE/2];
+        LingeredApp.main(args);
+    }
+ }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/serviceability/sa/TestHeapDumpForLargeArray.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,117 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+
+import java.util.ArrayList;
+import java.util.List;
+import java.io.File;
+import java.nio.file.Files;
+import java.io.IOException;
+import java.io.BufferedInputStream;
+import java.util.stream.Collectors;
+import java.io.FileInputStream;
+
+import sun.jvm.hotspot.HotSpotAgent;
+import sun.jvm.hotspot.debugger.*;
+
+import jdk.test.lib.apps.LingeredApp;
+import jdk.test.lib.JDKToolLauncher;
+import jdk.test.lib.JDKToolFinder;
+import jdk.test.lib.Platform;
+import jdk.test.lib.process.ProcessTools;
+import jdk.test.lib.process.OutputAnalyzer;
+import jdk.test.lib.Utils;
+import jdk.test.lib.Asserts;
+
+/*
+ * @test
+ * @library /test/lib
+ * @bug 8171084
+ * @requires (vm.bits == "64" & os.maxMemory > 8g)
+ * @modules java.base/jdk.internal.misc
+ *          jdk.hotspot.agent/sun.jvm.hotspot
+ *          jdk.hotspot.agent/sun.jvm.hotspot.utilities
+ *          jdk.hotspot.agent/sun.jvm.hotspot.oops
+ *          jdk.hotspot.agent/sun.jvm.hotspot.debugger
+ * @run main/timeout=1800/othervm -Xmx8g TestHeapDumpForLargeArray
+ */
+
+public class TestHeapDumpForLargeArray {
+
+    private static LingeredAppWithLargeArray theApp = null;
+
+    private static void attachAndDump(String heapDumpFileName,
+                                      long lingeredAppPid) throws Exception {
+
+        JDKToolLauncher launcher = JDKToolLauncher.createUsingTestJDK("jhsdb");
+        launcher.addToolArg("jmap");
+        launcher.addToolArg("--binaryheap");
+        launcher.addToolArg("--dumpfile");
+        launcher.addToolArg(heapDumpFileName);
+        launcher.addToolArg("--pid");
+        launcher.addToolArg(Long.toString(lingeredAppPid));
+
+        ProcessBuilder processBuilder = new ProcessBuilder();
+        processBuilder.command(launcher.getCommand());
+        System.out.println(
+            processBuilder.command().stream().collect(Collectors.joining(" ")));
+
+        OutputAnalyzer SAOutput = ProcessTools.executeProcess(processBuilder);
+        SAOutput.shouldHaveExitValue(0);
+        SAOutput.shouldNotContain("Heap segment size overflow");
+        SAOutput.shouldContain("truncating to");
+        SAOutput.shouldContain("heap written to");
+        SAOutput.shouldContain(heapDumpFileName);
+        System.out.println(SAOutput.getOutput());
+
+    }
+
+    public static void main (String... args) throws Exception {
+
+        String heapDumpFileName = "LargeArrayHeapDump.bin";
+
+        if (!Platform.shouldSAAttach()) {
+            System.out.println(
+               "SA attach not expected to work - test skipped.");
+            return;
+        }
+
+        File heapDumpFile = new File(heapDumpFileName);
+        if (heapDumpFile.exists()) {
+            heapDumpFile.delete();
+        }
+
+        try {
+            List<String> vmArgs = new ArrayList<String>();
+            vmArgs.add("-XX:+UsePerfData");
+            vmArgs.add("-Xmx8g");
+            vmArgs.addAll(Utils.getVmOptions());
+
+            theApp = new LingeredAppWithLargeArray();
+            LingeredApp.startApp(vmArgs, theApp);
+            attachAndDump(heapDumpFileName, theApp.getPid());
+        } finally {
+            LingeredApp.stopApp(theApp);
+            heapDumpFile.delete();
+        }
+    }
+}
--- a/hotspot/test/serviceability/sa/jmap-hprof/JMapHProfLargeHeapTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/serviceability/sa/jmap-hprof/JMapHProfLargeHeapTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -53,7 +53,6 @@
 
 public class JMapHProfLargeHeapTest {
     private static final String HEAP_DUMP_FILE_NAME = "heap.bin";
-    private static final String HPROF_HEADER_1_0_1 = "JAVA PROFILE 1.0.1";
     private static final String HPROF_HEADER_1_0_2 = "JAVA PROFILE 1.0.2";
     private static final long M = 1024L;
     private static final long G = 1024L * M;
@@ -65,9 +64,7 @@
         }
 
         // All heap dumps should create 1.0.2 file format
-        // Hotspot internal heapdumper always use HPROF_HEADER_1_0_2 format,
-        // but SA heapdumper still use HPROF_HEADER_1_0_1 for small heaps
-        testHProfFileFormat("-Xmx1g", 22 * M, HPROF_HEADER_1_0_1);
+        testHProfFileFormat("-Xmx1g", 22 * M, HPROF_HEADER_1_0_2);
 
         /**
          * This test was deliberately commented out since the test system lacks
--- a/hotspot/test/testlibrary/jittester/Makefile	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/testlibrary/jittester/Makefile	Wed Jul 05 22:52:01 2017 +0200
@@ -108,7 +108,7 @@
 	$(shell if [ ! -d $(CLASSES_DIR) ]; then mkdir -p $(CLASSES_DIR); fi)
 
 install: clean_testbase testgroup testroot copytestlibrary copyaot JAR cleantmp
-	$(JAVA) --add-exports=java.base/jdk.internal.org.objectweb.asm=ALL-UNNAMED -ea -jar $(DIST_JAR) $(APPLICATION_ARGS)
+	$(JAVA) --add-exports=java.base/jdk.internal.org.objectweb.asm=ALL-UNNAMED --add-opens java.base/java.util=ALL-UNNAMED -ea -jar $(DIST_JAR) $(APPLICATION_ARGS)
 
 clean_testbase:
 	@rm -rf $(TESTBASE_DIR)
--- a/hotspot/test/testlibrary/jittester/src/jdk/test/lib/jittester/TestsGenerator.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/hotspot/test/testlibrary/jittester/src/jdk/test/lib/jittester/TestsGenerator.java	Wed Jul 05 22:52:01 2017 +0200
@@ -43,6 +43,7 @@
     protected final Path generatorDir;
     protected final Function<String, String[]> preRunActions;
     protected final String jtDriverOptions;
+    private static final String DISABLE_WARNINGS = "-XX:-PrintWarnings";
 
     protected TestsGenerator(String suffix) {
         this(suffix, s -> new String[0], "");
@@ -57,8 +58,8 @@
 
     protected void generateGoldenOut(String mainClassName) {
         String classPath = getRoot() + File.pathSeparator + generatorDir;
-        ProcessBuilder pb = new ProcessBuilder(JAVA, "-Xint", "-Xverify", "-cp", classPath,
-                mainClassName);
+        ProcessBuilder pb = new ProcessBuilder(JAVA, "-Xint", DISABLE_WARNINGS, "-Xverify",
+                "-cp", classPath, mainClassName);
         String goldFile = mainClassName + ".gold";
         try {
             runProcess(pb, generatorDir.resolve(goldFile).toString());
@@ -128,6 +129,8 @@
                   .append("\n");
         }
         header.append(" * @run driver jdk.test.lib.jittester.jtreg.JitTesterDriver ")
+              .append(DISABLE_WARNINGS)
+              .append(" ")
               .append(jtDriverOptions)
               .append(" ")
               .append(mainClassName)
--- a/jaxp/.hgtags	Mon Feb 13 11:57:56 2017 +0100
+++ b/jaxp/.hgtags	Wed Jul 05 22:52:01 2017 +0200
@@ -398,3 +398,4 @@
 1384504d2cd0e55c5e0becaeaf40ab05cae959d6 jdk-9+153
 7fa738305436d14c0926df0f04892890cacc766b jdk-9+154
 48fa77af153288b08ba794e1616a7b0685f3b67e jdk-9+155
+e930c373aaa4e0e712c9a25ba4b03d473b48c294 jdk-9+156
--- a/jaxp/src/java.xml/share/classes/com/sun/org/apache/xalan/internal/xsltc/trax/TemplatesImpl.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jaxp/src/java.xml/share/classes/com/sun/org/apache/xalan/internal/xsltc/trax/TemplatesImpl.java	Wed Jul 05 22:52:01 2017 +0200
@@ -438,7 +438,7 @@
         Layer bootLayer = Layer.boot();
 
         Configuration cf = bootLayer.configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of(mn));
+                .resolve(finder, ModuleFinder.of(), Set.of(mn));
 
         PrivilegedAction<Layer> pa = () -> bootLayer.defineModules(cf, name -> loader);
         Layer layer = AccessController.doPrivileged(pa);
@@ -483,10 +483,11 @@
             String pn = _tfactory.getPackageName();
             assert pn != null && pn.length() > 0;
 
-            ModuleDescriptor descriptor = ModuleDescriptor.module(mn)
-                    .requires("java.xml")
-                    .exports(pn)
-                    .build();
+            ModuleDescriptor descriptor =
+                ModuleDescriptor.newModule(mn, Set.of(ModuleDescriptor.Modifier.SYNTHETIC))
+                                .requires("java.xml")
+                                .exports(pn)
+                                .build();
 
             Module m = createModule(descriptor, loader);
 
--- a/jaxp/src/java.xml/share/classes/com/sun/org/apache/xml/internal/serializer/ToHTMLStream.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jaxp/src/java.xml/share/classes/com/sun/org/apache/xml/internal/serializer/ToHTMLStream.java	Wed Jul 05 22:52:01 2017 +0200
@@ -717,7 +717,9 @@
      */
     public final void endDocument() throws org.xml.sax.SAXException
     {
-        flushCharactersBuffer();
+        if (m_doIndent) {
+            flushCharactersBuffer();
+        }
         flushPending();
         if (m_doIndent && !m_isprevtext)
         {
@@ -776,9 +778,11 @@
         Attributes atts)
         throws SAXException
     {
-        // will add extra one if having namespace but no matter
-        m_childNodeNum++;
-        flushCharactersBuffer();
+        if (m_doIndent) {
+            // will add extra one if having namespace but no matter
+            m_childNodeNum++;
+            flushCharactersBuffer();
+        }
         ElemContext elemContext = m_elemContext;
 
         // clean up any pending things first
@@ -839,8 +843,10 @@
             writer.write('<');
             writer.write(name);
 
-            m_childNodeNumStack.push(m_childNodeNum);
-            m_childNodeNum = 0;
+            if (m_doIndent) {
+                m_childNodeNumStack.add(m_childNodeNum);
+                m_childNodeNum = 0;
+            }
 
             if (m_tracer != null)
                 firePseudoAttributes();
@@ -915,7 +921,9 @@
         final String name)
         throws org.xml.sax.SAXException
     {
-        flushCharactersBuffer();
+        if (m_doIndent) {
+            flushCharactersBuffer();
+        }
         // deal with any pending issues
         if (m_cdataTagOpen)
             closeCDATA();
@@ -997,12 +1005,11 @@
                 }
             }
 
-            m_childNodeNum = m_childNodeNumStack.pop();
-            // clean up because the element has ended
-            if ((elemFlags & ElemDesc.WHITESPACESENSITIVE) != 0)
-                m_ispreserve = true;
-            m_isprevtext = false;
-
+            if (m_doIndent) {
+                m_childNodeNum = m_childNodeNumStack.remove(m_childNodeNumStack.size() - 1);
+                // clean up because the element has ended
+                m_isprevtext = false;
+            }
             // fire off the end element event
             if (m_tracer != null)
                 super.fireEndElem(name);
@@ -1018,11 +1025,6 @@
             }
 
             // some more clean because the element has ended.
-            if (!elemContext.m_startTagOpen)
-            {
-                if (m_doIndent && !m_preserves.isEmpty())
-                    m_preserves.pop();
-            }
             m_elemContext = elemContext.m_prev;
 //            m_isRawStack.pop();
         }
@@ -1525,7 +1527,6 @@
                     closeStartTag();
                     m_elemContext.m_startTagOpen = false;
                 }
-                m_ispreserve = true;
 
 //              With m_ispreserve just set true it looks like shouldIndent()
 //              will always return false, so drop any possible indentation.
@@ -1602,8 +1603,6 @@
                     m_elemContext.m_startTagOpen = false;
                 }
 
-                m_ispreserve = true;
-
                 if (shouldIndent())
                     indent();
 
@@ -1640,8 +1639,10 @@
     public void processingInstruction(String target, String data)
         throws org.xml.sax.SAXException
     {
-        m_childNodeNum++;
-        flushCharactersBuffer();
+        if (m_doIndent) {
+            m_childNodeNum++;
+            flushCharactersBuffer();
+        }
         // Process any pending starDocument and startElement first.
         flushPending();
 
@@ -1790,11 +1791,6 @@
              */
             if (m_StringOfCDATASections != null)
                 m_elemContext.m_isCdataSection = isCdataSection();
-            if (m_doIndent)
-            {
-                m_isprevtext = false;
-                m_preserves.push(m_ispreserve);
-            }
 
             }
             catch(IOException e)
--- a/jaxp/src/java.xml/share/classes/com/sun/org/apache/xml/internal/serializer/ToStream.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jaxp/src/java.xml/share/classes/com/sun/org/apache/xml/internal/serializer/ToStream.java	Wed Jul 05 22:52:01 2017 +0200
@@ -20,34 +20,36 @@
 
 package com.sun.org.apache.xml.internal.serializer;
 
-import com.sun.org.apache.xalan.internal.utils.SecuritySupport;
-import com.sun.org.apache.xml.internal.serializer.utils.MsgKey;
-import com.sun.org.apache.xml.internal.serializer.utils.Utils;
-import com.sun.org.apache.xml.internal.serializer.utils.WrappedRuntimeException;
 import java.io.IOException;
 import java.io.OutputStream;
 import java.io.OutputStreamWriter;
 import java.io.UnsupportedEncodingException;
 import java.io.Writer;
-import java.util.ArrayDeque;
 import java.util.ArrayList;
 import java.util.Arrays;
-import java.util.Deque;
 import java.util.EmptyStackException;
 import java.util.Enumeration;
+import java.util.Iterator;
+import java.util.List;
 import java.util.Properties;
-import java.util.Queue;
 import java.util.Set;
 import java.util.StringTokenizer;
+
 import javax.xml.transform.ErrorListener;
 import javax.xml.transform.OutputKeys;
 import javax.xml.transform.Transformer;
 import javax.xml.transform.TransformerException;
+
 import org.w3c.dom.Node;
 import org.xml.sax.Attributes;
 import org.xml.sax.ContentHandler;
 import org.xml.sax.SAXException;
 
+import com.sun.org.apache.xalan.internal.utils.SecuritySupport;
+import com.sun.org.apache.xml.internal.serializer.utils.MsgKey;
+import com.sun.org.apache.xml.internal.serializer.utils.Utils;
+import com.sun.org.apache.xml.internal.serializer.utils.WrappedRuntimeException;
+
 /**
  * This abstract class is a base class for other stream
  * serializers (xml, html, text ...) that write output to a stream.
@@ -103,7 +105,7 @@
      * If m_childNodeNum > 1, the text node will be indented.
      *
      */
-    protected Deque<Integer> m_childNodeNumStack = new ArrayDeque<>();
+    protected List<Integer> m_childNodeNumStack = new ArrayList<>();
 
     protected int m_childNodeNum = 0;
 
@@ -115,26 +117,6 @@
 
     protected boolean m_ispreserveSpace = false;
 
-    /**
-     * Stack to keep track of whether or not we need to
-     * preserve whitespace.
-     *
-     * Used to push/pop values used for the field m_ispreserve, but
-     * m_ispreserve is only relevant if m_doIndent is true.
-     * If m_doIndent is false this field has no impact.
-     *
-     */
-    protected BoolStack m_preserves = new BoolStack();
-
-    /**
-     * State flag to tell if preservation of whitespace
-     * is important.
-     *
-     * Used only in shouldIndent() but only if m_doIndent is true.
-     * If m_doIndent is false this flag has no impact.
-     *
-     */
-    protected boolean m_ispreserve = false;
 
     /**
      * State flag that tells if the previous node processed
@@ -1267,7 +1249,6 @@
                 closeStartTag();
                 m_elemContext.m_startTagOpen = false;
             }
-            m_ispreserve = true;
 
             if (shouldIndent())
                 indent();
@@ -1357,8 +1338,6 @@
                 m_elemContext.m_startTagOpen = false;
             }
 
-            m_ispreserve = true;
-
             m_writer.write(ch, start, length);
         }
         catch (IOException e)
@@ -1405,8 +1384,8 @@
         if (length == 0 || (isInEntityRef()))
             return;
 
-        final boolean shouldFormat = shouldFormatOutput();
-        if (m_elemContext.m_startTagOpen && !shouldFormat)
+        final boolean shouldNotFormat = !shouldFormatOutput();
+        if (m_elemContext.m_startTagOpen && shouldNotFormat)
         {
             closeStartTag();
             m_elemContext.m_startTagOpen = false;
@@ -1441,16 +1420,16 @@
             return;
         }
 
-        if (m_elemContext.m_startTagOpen && !shouldFormat)
+        if (m_elemContext.m_startTagOpen && shouldNotFormat)
         {
             closeStartTag();
             m_elemContext.m_startTagOpen = false;
         }
 
-        if (shouldFormat) {
+        if (shouldNotFormat) {
+            outputCharacters(chars, start, length);
+        } else {
             m_charactersBuffer.addText(chars, start, length);
-        } else {
-            outputCharacters(chars, start, length);
         }
 
         // time to fire off characters generation event
@@ -1465,7 +1444,7 @@
      * @return True if the content should be formatted.
      */
     protected boolean shouldFormatOutput() {
-        return !m_ispreserveSpace && m_doIndent;
+        return m_doIndent && !m_ispreserveSpace;
     }
 
     /**
@@ -1506,12 +1485,6 @@
                     i = lastDirty;
                 }
             }
-            /* If there is some non-whitespace, mark that we may need
-             * to preserve this. This is only important if we have indentation on.
-             */
-            if (i < end)
-                m_ispreserve = true;
-
 
 //          int lengthClean;    // number of clean characters in a row
 //          final boolean[] isAsciiClean = m_charInfo.getASCIIClean();
@@ -1858,8 +1831,10 @@
         if (isInEntityRef())
             return;
 
-        m_childNodeNum++;
-        flushCharactersBuffer();
+        if (m_doIndent) {
+            m_childNodeNum++;
+            flushCharactersBuffer();
+        }
 
         if (m_needToCallStartDocument)
         {
@@ -1890,8 +1865,6 @@
             if (namespaceURI != null)
                 ensurePrefixIsDeclared(namespaceURI, name);
 
-            m_ispreserve = false;
-
             if (shouldIndent() && m_startNewLine)
             {
                 indent();
@@ -1912,11 +1885,13 @@
         if (atts != null)
             addAttributes(atts);
 
-        m_ispreserveSpace = m_preserveSpaces.peekOrFalse();
-        m_preserveSpaces.push(m_ispreserveSpace);
-
-        m_childNodeNumStack.push(m_childNodeNum);
-        m_childNodeNum = 0;
+        if (m_doIndent) {
+            m_ispreserveSpace = m_preserveSpaces.peekOrFalse();
+            m_preserveSpaces.push(m_ispreserveSpace);
+
+            m_childNodeNumStack.add(m_childNodeNum);
+            m_childNodeNum = 0;
+        }
 
         m_elemContext = m_elemContext.push(namespaceURI,localName,name);
         m_isprevtext = false;
@@ -2128,7 +2103,9 @@
         if (isInEntityRef())
             return;
 
-        flushCharactersBuffer();
+        if (m_doIndent) {
+            flushCharactersBuffer();
+        }
         // namespaces declared at the current depth are no longer valid
         // so get rid of them
         m_prefixMap.popNamespaces(m_elemContext.m_currentElemDepth, null);
@@ -2175,16 +2152,13 @@
             throw new SAXException(e);
         }
 
-        if (!m_elemContext.m_startTagOpen && m_doIndent)
-        {
-            m_ispreserve = m_preserves.isEmpty() ? false : m_preserves.pop();
+        if (m_doIndent) {
+            m_ispreserveSpace = m_preserveSpaces.popAndTop();
+            m_childNodeNum = m_childNodeNumStack.remove(m_childNodeNumStack.size() - 1);
+
+            m_isprevtext = false;
         }
 
-        m_ispreserveSpace = m_preserveSpaces.popAndTop();
-        m_childNodeNum = m_childNodeNumStack.pop();
-
-        m_isprevtext = false;
-
         // fire off the end element event
         if (m_tracer != null)
             super.fireEndElem(name);
@@ -2320,8 +2294,10 @@
         int start_old = start;
         if (isInEntityRef())
             return;
-        m_childNodeNum++;
-        flushCharactersBuffer();
+        if (m_doIndent) {
+            m_childNodeNum++;
+            flushCharactersBuffer();
+        }
         if (m_elemContext.m_startTagOpen)
         {
             closeStartTag();
@@ -2501,8 +2477,10 @@
      */
     public void startCDATA() throws org.xml.sax.SAXException
     {
-        m_childNodeNum++;
-        flushCharactersBuffer();
+        if (m_doIndent) {
+            m_childNodeNum++;
+            flushCharactersBuffer();
+        }
 
         m_cdataStartCalled = true;
     }
@@ -2588,12 +2566,6 @@
              */
             if (m_StringOfCDATASections != null)
                 m_elemContext.m_isCdataSection = isCdataSection();
-
-            if (m_doIndent)
-            {
-                m_isprevtext = false;
-                m_preserves.push(m_ispreserve);
-            }
         }
 
     }
@@ -2943,7 +2915,9 @@
         String value,
         boolean xslAttribute)
     {
-        if (m_charactersBuffer.isAnyCharactersBuffered()) {
+        if (m_charactersBuffer.isNoCharactersBuffered()) {
+            return doAddAttributeAlways(uri, localName, rawName, type, value, xslAttribute);
+        } else {
             /*
              * If stylesheet includes xsl:copy-of an attribute node, XSLTC will
              * fire an addAttribute event. When a text node is handling in
@@ -2954,8 +2928,6 @@
              *
              */
             return m_attributes.getIndex(rawName) < 0;
-        } else {
-            return doAddAttributeAlways(uri, localName, rawName, type, value, xslAttribute);
         }
     }
 
@@ -3086,7 +3058,7 @@
             }
         }
 
-        if (rawName.equals("xml:space")) {
+        if (m_doIndent && rawName.equals("xml:space")) {
             if (value.equals("preserve")) {
                 m_ispreserveSpace = true;
                 if (m_preserveSpaces.size() > 0)
@@ -3227,8 +3199,6 @@
          // Leave m_format alone for now - Brian M.
          // this.m_format = null;
          this.m_inDoctype = false;
-         this.m_ispreserve = false;
-         this.m_preserves.clear();
          this.m_ispreserveSpace = false;
          this.m_preserveSpaces.clear();
          this.m_childNodeNum = 0;
@@ -3411,6 +3381,7 @@
         }
     }
 
+
     /**
      * This inner class is used to buffer the text nodes and the entity
      * reference nodes if indentation is on. There is only one CharacterBuffer
@@ -3438,7 +3409,7 @@
             abstract char[] toChars();
         }
 
-        private Queue<GenericCharacters> bufferedCharacters = new ArrayDeque<>();
+        private List<GenericCharacters> bufferedCharacters = new ArrayList<>();
 
         /**
          * Append a text node to the buffer.
@@ -3495,35 +3466,44 @@
         }
 
         /**
-         * @return True if any GenericCharacters is already buffered.
+         * @return True if no GenericCharacters are buffered.
          */
-        public boolean isAnyCharactersBuffered() {
-            return !bufferedCharacters.isEmpty();
+        public boolean isNoCharactersBuffered() {
+            return bufferedCharacters.isEmpty();
         }
 
         /**
          * @return True if any buffered GenericCharacters has content.
          */
         public boolean hasContent() {
-            return bufferedCharacters.stream().anyMatch(GenericCharacters::hasContent);
+            for (GenericCharacters element : bufferedCharacters) {
+                if (element.hasContent())
+                    return true;
+            }
+            return false;
         }
 
         /**
          * Flush all buffered GenericCharacters.
          */
         public void flush() throws SAXException {
-            GenericCharacters element;
-            while ((element = bufferedCharacters.poll()) != null)
+            Iterator<GenericCharacters> itr = bufferedCharacters.iterator();
+            while (itr.hasNext()) {
+                GenericCharacters element = itr.next();
                 element.flush();
+                itr.remove();
+            }
         }
 
         /**
          * Converts all buffered GenericCharacters to a new character array.
          */
         public char[] toChars() {
-            return bufferedCharacters.stream().map(GenericCharacters::toChars)
-                    .collect(StringBuilder::new, StringBuilder::append, StringBuilder::append).toString()
-                    .toCharArray();
+            StringBuilder sb = new StringBuilder();
+            for (GenericCharacters element : bufferedCharacters) {
+                sb.append(element.toChars());
+            }
+            return sb.toString().toCharArray();
         }
 
         /**
@@ -3534,6 +3514,7 @@
         }
     }
 
+
     // Implement DTDHandler
     /**
      * If this method is called, the serializer is used as a
--- a/jaxp/src/java.xml/share/classes/com/sun/org/apache/xml/internal/serializer/ToXMLStream.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jaxp/src/java.xml/share/classes/com/sun/org/apache/xml/internal/serializer/ToXMLStream.java	Wed Jul 05 22:52:01 2017 +0200
@@ -88,8 +88,6 @@
 
         setOmitXMLDeclaration(xmlListener.getOmitXMLDeclaration());
 
-        m_ispreserve = xmlListener.m_ispreserve;
-        m_preserves = xmlListener.m_preserves;
         m_ispreserveSpace = xmlListener.m_ispreserveSpace;
         m_preserveSpaces = xmlListener.m_preserveSpaces;
         m_childNodeNum = xmlListener.m_childNodeNum;
@@ -201,7 +199,9 @@
      */
     public void endDocument() throws org.xml.sax.SAXException
     {
-        flushCharactersBuffer();
+        if (m_doIndent) {
+            flushCharactersBuffer();
+        }
         flushPending();
         if (m_doIndent && !m_isprevtext)
         {
@@ -235,11 +235,6 @@
      */
     public void startPreserving() throws org.xml.sax.SAXException
     {
-
-        // Not sure this is really what we want.  -sb
-        m_preserves.push(true);
-
-        m_ispreserve = true;
     }
 
     /**
@@ -251,9 +246,6 @@
      */
     public void endPreserving() throws org.xml.sax.SAXException
     {
-
-        // Not sure this is really what we want.  -sb
-        m_ispreserve = m_preserves.isEmpty() ? false : m_preserves.pop();
     }
 
     /**
@@ -273,8 +265,10 @@
         if (isInEntityRef())
             return;
 
-        m_childNodeNum++;
-        flushCharactersBuffer();
+        if (m_doIndent) {
+            m_childNodeNum++;
+            flushCharactersBuffer();
+        }
         flushPending();
 
         if (target.equals(Result.PI_DISABLE_OUTPUT_ESCAPING))
--- a/jaxp/src/java.xml/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jaxp/src/java.xml/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -26,6 +26,8 @@
 /**
  * Defines the Java API for XML Processing (JAXP), the Streaming API for XML (StAX),
  * the Simple API for XML (SAX), and the W3C Document Object Model (DOM) API.
+ *
+ * @since 9
  */
 module java.xml {
     exports javax.xml;
--- a/jaxp/test/javax/xml/jaxp/module/ServiceProviderTest/LayerModularXMLParserTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jaxp/test/javax/xml/jaxp/module/ServiceProviderTest/LayerModularXMLParserTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -96,7 +96,7 @@
     public void testOneLayer() throws Exception {
         ModuleFinder finder1 = ModuleFinder.of(MOD_DIR1);
         Configuration cf1 = Layer.boot().configuration()
-                .resolveRequiresAndUses(finder1, ModuleFinder.of(), Set.of("test"));
+                .resolveAndBind(finder1, ModuleFinder.of(), Set.of("test"));
         ClassLoader scl = ClassLoader.getSystemClassLoader();
         Layer layer1 = Layer.boot().defineModulesWithManyLoaders(cf1, scl);
         ClassLoader cl1 = layer1.findLoader("test");
@@ -126,12 +126,12 @@
     public void testTwoLayer() throws Exception {
         ModuleFinder finder1 = ModuleFinder.of(MOD_DIR1);
         Configuration cf1 = Layer.boot().configuration()
-                .resolveRequiresAndUses(finder1, ModuleFinder.of(), Set.of("test"));
+                .resolveAndBind(finder1, ModuleFinder.of(), Set.of("test"));
         ClassLoader scl = ClassLoader.getSystemClassLoader();
         Layer layer1 = Layer.boot().defineModulesWithManyLoaders(cf1, scl);
 
         ModuleFinder finder2 = ModuleFinder.of(MOD_DIR2);
-        Configuration cf2 = cf1.resolveRequiresAndUses(finder2, ModuleFinder.of(), Set.of("test"));
+        Configuration cf2 = cf1.resolveAndBind(finder2, ModuleFinder.of(), Set.of("test"));
         Layer layer2 = layer1.defineModulesWithOneLoader(cf2, layer1.findLoader("test"));
         ClassLoader cl2 = layer2.findLoader("test");
 
@@ -160,12 +160,12 @@
     public void testTwoLayerWithDuplicate() throws Exception {
         ModuleFinder finder1 = ModuleFinder.of(MOD_DIR1, MOD_DIR2);
         Configuration cf1 = Layer.boot().configuration()
-                .resolveRequiresAndUses(finder1, ModuleFinder.of(), Set.of("test"));
+                .resolveAndBind(finder1, ModuleFinder.of(), Set.of("test"));
         ClassLoader scl = ClassLoader.getSystemClassLoader();
         Layer layer1 = Layer.boot().defineModulesWithManyLoaders(cf1, scl);
 
         ModuleFinder finder2 = ModuleFinder.of(MOD_DIR2);
-        Configuration cf2 = cf1.resolveRequiresAndUses(finder2, ModuleFinder.of(), Set.of("test"));
+        Configuration cf2 = cf1.resolveAndBind(finder2, ModuleFinder.of(), Set.of("test"));
         Layer layer2 = layer1.defineModulesWithOneLoader(cf2, layer1.findLoader("test"));
         ClassLoader cl2 = layer2.findLoader("test");
 
--- a/jaxws/.hgtags	Mon Feb 13 11:57:56 2017 +0100
+++ b/jaxws/.hgtags	Wed Jul 05 22:52:01 2017 +0200
@@ -401,3 +401,4 @@
 7a532a9a227137155b905341d4b99939db51220e jdk-9+153
 34af95c7dbff74f3448fcdb7d745524e8a1cc88a jdk-9+154
 9b9918656c97724fd89c04a8547043bbd37f5935 jdk-9+155
+7c829eba781409b4fe15392639289af1553dcf63 jdk-9+156
--- a/jaxws/src/java.activation/share/classes/META-INF/mimetypes.default	Mon Feb 13 11:57:56 2017 +0100
+++ b/jaxws/src/java.activation/share/classes/META-INF/mimetypes.default	Wed Jul 05 22:52:01 2017 +0200
@@ -7,6 +7,7 @@
 image/ief		ief
 image/jpeg		jpeg jpg jpe JPG
 image/tiff		tiff tif
+image/png		png PNG
 image/x-xwindowdump	xwd
 application/postscript	ai eps ps
 application/rtf		rtf
--- a/jaxws/src/java.activation/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jaxws/src/java.activation/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Defines the JavaBeans Activation Framework (JAF) API.
+ *
+ * @since 9
  */
 module java.activation {
     requires transitive java.datatransfer;
--- a/jaxws/src/java.xml.bind/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jaxws/src/java.xml.bind/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Defines the Java Architecture for XML Binding (JAXB) API.
+ *
+ * @since 9
  */
 module java.xml.bind {
     requires transitive java.activation;
--- a/jaxws/src/java.xml.ws.annotation/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jaxws/src/java.xml.ws.annotation/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -26,6 +26,8 @@
 /**
  * Defines a subset of the Common Annotations API to support programs running
  * on the Java SE Platform.
+ *
+ * @since 9
  */
 module java.xml.ws.annotation {
     exports javax.annotation;
--- a/jaxws/src/java.xml.ws/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jaxws/src/java.xml.ws/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -26,6 +26,8 @@
 /**
  * Defines the Java API for XML-Based Web Services (JAX-WS), and
  * the Web Services Metadata API.
+ *
+ * @since 9
  */
 module java.xml.ws {
     requires transitive java.activation;
--- a/jdk/.hgtags	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/.hgtags	Wed Jul 05 22:52:01 2017 +0200
@@ -398,3 +398,4 @@
 1c4411322327aea3f91011ec3977a12a05b09629 jdk-9+153
 c97e7a8b8da062b9070df442f9cf308e10845fb7 jdk-9+154
 e170c858888e83d5c0994504599b6ed7a1fb0cfc jdk-9+155
+7d64e541a6c04c714bcad4c8b553db912f827cd5 jdk-9+156
--- a/jdk/make/src/classes/build/tools/jigsaw/GenGraphs.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/make/src/classes/build/tools/jigsaw/GenGraphs.java	Wed Jul 05 22:52:01 2017 +0200
@@ -153,9 +153,9 @@
      */
     void genDotFile(String name, Set<String> roots) throws IOException {
         Configuration cf =
-            Configuration.empty().resolveRequires(ModuleFinder.ofSystem(),
-                                                  ModuleFinder.of(),
-                                                  roots);
+            Configuration.empty().resolve(ModuleFinder.ofSystem(),
+                                          ModuleFinder.of(),
+                                          roots);
 
         Set<ModuleDescriptor> mds = cf.modules().stream()
                 .map(ResolvedModule::reference)
--- a/jdk/make/src/classes/build/tools/jigsaw/ModuleSummary.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/make/src/classes/build/tools/jigsaw/ModuleSummary.java	Wed Jul 05 22:52:01 2017 +0200
@@ -291,9 +291,9 @@
 
     static Configuration resolve(Set<String> roots) {
         return Configuration.empty()
-            .resolveRequires(ModuleFinder.ofSystem(),
-                             ModuleFinder.of(),
-                             roots);
+            .resolve(ModuleFinder.ofSystem(),
+                     ModuleFinder.of(),
+                     roots);
     }
 
     static class HtmlDocument {
--- a/jdk/src/java.base/share/classes/java/lang/Class.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/Class.java	Wed Jul 05 22:52:01 2017 +0200
@@ -425,6 +425,7 @@
      *         </ul>
      *
      * @since 9
+     * @spec JPMS
      */
     @CallerSensitive
     public static Class<?> forName(Module module, String name) {
@@ -819,6 +820,7 @@
      * @return the module that this class or interface is a member of
      *
      * @since 9
+     * @spec JPMS
      */
     public Module getModule() {
         return module;
@@ -924,6 +926,8 @@
      * this method returns {@code null}.
      *
      * @return the package of this class.
+     * @revised 9
+     * @spec JPMS
      */
     public Package getPackage() {
         if (isPrimitive() || isArray()) {
@@ -951,20 +955,30 @@
      * declaring class} of the {@link #getEnclosingMethod enclosing method} or
      * {@link #getEnclosingConstructor enclosing constructor}.
      *
-     * <p> This method returns {@code null} if this class represents an array type,
-     * a primitive type or void.
+     * <p> If this class represents an array type then this method returns the
+     * package name of the element type. If this class represents a primitive
+     * type or void then the package name "{@code java.lang}" is returned.
      *
      * @return the fully qualified package name
      *
      * @since 9
+     * @spec JPMS
      * @jls 6.7  Fully Qualified Names
      */
     public String getPackageName() {
         String pn = this.packageName;
-        if (pn == null && !isArray() && !isPrimitive()) {
-            String cn = getName();
-            int dot = cn.lastIndexOf('.');
-            pn = (dot != -1) ? cn.substring(0, dot).intern() : "";
+        if (pn == null) {
+            Class<?> c = this;
+            while (c.isArray()) {
+                c = c.getComponentType();
+            }
+            if (c.isPrimitive()) {
+                pn = "java.lang";
+            } else {
+                String cn = c.getName();
+                int dot = cn.lastIndexOf('.');
+                pn = (dot != -1) ? cn.substring(0, dot).intern() : "";
+            }
             this.packageName = pn;
         }
         return pn;
@@ -2491,10 +2505,16 @@
      * Finds a resource with a given name.
      *
      * <p> If this class is in a named {@link Module Module} then this method
-     * will attempt to find the resource in the module by means of the absolute
-     * resource name, subject to the rules for encapsulation specified in the
-     * {@code Module} {@link Module#getResourceAsStream getResourceAsStream}
-     * method.
+     * will attempt to find the resource in the module. This is done by
+     * delegating to the module's class loader {@link
+     * ClassLoader#findResource(String,String) findResource(String,String)}
+     * method, invoking it with the module name and the absolute name of the
+     * resource. Resources in named modules are subject to the rules for
+     * encapsulation specified in the {@code Module} {@link
+     * Module#getResourceAsStream getResourceAsStream} method and so this
+     * method returns {@code null} when the resource is a
+     * non-"{@code .class}" resource in a package that is not open to the
+     * caller's module.
      *
      * <p> Otherwise, if this class is not in a named module then the rules for
      * searching resources associated with a given class are implemented by the
@@ -2503,9 +2523,8 @@
      * the bootstrap class loader, the method delegates to {@link
      * ClassLoader#getSystemResourceAsStream}.
      *
-     * <p> Before finding a resource in the caller's module or delegation to a
-     * class loader, an absolute resource name is constructed from the given
-     * resource name using this algorithm:
+     * <p> Before delegation, an absolute resource name is constructed from the
+     * given resource name using this algorithm:
      *
      * <ul>
      *
@@ -2532,7 +2551,11 @@
      *          least the caller module, or access to the resource is denied
      *          by the security manager.
      * @throws  NullPointerException If {@code name} is {@code null}
+     *
+     * @see Module#getResourceAsStream(String)
      * @since  1.1
+     * @revised 9
+     * @spec JPMS
      */
     @CallerSensitive
     public InputStream getResourceAsStream(String name) {
@@ -2585,10 +2608,16 @@
      * Finds a resource with a given name.
      *
      * <p> If this class is in a named {@link Module Module} then this method
-     * will attempt to find the resource in the module by means of the absolute
-     * resource name, subject to the rules for encapsulation specified in the
-     * {@code Module} {@link Module#getResourceAsStream getResourceAsStream}
-     * method.
+     * will attempt to find the resource in the module. This is done by
+     * delegating to the module's class loader {@link
+     * ClassLoader#findResource(String,String) findResource(String,String)}
+     * method, invoking it with the module name and the absolute name of the
+     * resource. Resources in named modules are subject to the rules for
+     * encapsulation specified in the {@code Module} {@link
+     * Module#getResourceAsStream getResourceAsStream} method and so this
+     * method returns {@code null} when the resource is a
+     * non-"{@code .class}" resource in a package that is not open to the
+     * caller's module.
      *
      * <p> Otherwise, if this class is not in a named module then the rules for
      * searching resources associated with a given class are implemented by the
@@ -2627,6 +2656,8 @@
      *         manager.
      * @throws NullPointerException If {@code name} is {@code null}
      * @since  1.1
+     * @revised 9
+     * @spec JPMS
      */
     @CallerSensitive
     public URL getResource(String name) {
--- a/jdk/src/java.base/share/classes/java/lang/ClassLoader.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/ClassLoader.java	Wed Jul 05 22:52:01 2017 +0200
@@ -207,6 +207,8 @@
  * @jls 13.1 The Form of a Binary
  * @see      #resolveClass(Class)
  * @since 1.0
+ * @revised 9
+ * @spec JPMS
  */
 public abstract class ClassLoader {
 
@@ -380,12 +382,12 @@
      *         method doesn't allow creation of a new class loader.
      *
      * @since  9
+     * @spec JPMS
      */
     protected ClassLoader(String name, ClassLoader parent) {
         this(checkCreateClassLoader(name), name, parent);
     }
 
-
     /**
      * Creates a new class loader using the specified parent class loader for
      * delegation.
@@ -440,6 +442,7 @@
      * this class loader is not named.
      *
      * @since 9
+     * @spec JPMS
      */
     public String getName() {
         return name;
@@ -710,6 +713,7 @@
      *         if the class could not be found.
      *
      * @since 9
+     * @spec JPMS
      */
     protected Class<?> findClass(String moduleName, String name) {
         if (moduleName == null) {
@@ -834,6 +838,8 @@
      * @see  java.security.SecureClassLoader
      *
      * @since  1.1
+     * @revised 9
+     * @spec JPMS
      */
     protected final Class<?> defineClass(String name, byte[] b, int off, int len)
         throws ClassFormatError
@@ -967,6 +973,9 @@
      *          certificates than this class, or if {@code name} begins with
      *          "{@code java.}" and this class loader is not the platform
      *          class loader or its ancestor.
+     *
+     * @revised 9
+     * @spec JPMS
      */
     protected final Class<?> defineClass(String name, byte[] b, int off, int len,
                                          ProtectionDomain protectionDomain)
@@ -1041,6 +1050,8 @@
      * @see      #defineClass(String, byte[], int, int, ProtectionDomain)
      *
      * @since  1.5
+     * @revised 9
+     * @spec JPMS
      */
     protected final Class<?> defineClass(String name, java.nio.ByteBuffer b,
                                          ProtectionDomain protectionDomain)
@@ -1264,11 +1275,11 @@
      * Class loader implementations that support the loading from modules
      * should override this method.
      *
-     * @apiNote This method is the basis for the {@code Class} {@link
-     * Class#getResource getResource} and {@link Class#getResourceAsStream
-     * getResourceAsStream} methods. It is not subject to the rules for
-     * encapsulation specified by {@code Module} {@link
-     * Module#getResourceAsStream getResourceAsStream}.
+     * @apiNote This method is the basis for the {@link
+     * Class#getResource Class.getResource}, {@link Class#getResourceAsStream
+     * Class.getResourceAsStream}, and {@link Module#getResourceAsStream
+     * Module.getResourceAsStream} methods. It is not subject to the rules for
+     * encapsulation specified by {@code Module.getResourceAsStream}.
      *
      * @implSpec The default implementation attempts to find the resource by
      * invoking {@link #findResource(String)} when the {@code moduleName} is
@@ -1292,6 +1303,7 @@
      *
      * @see java.lang.module.ModuleReader#find(String)
      * @since 9
+     * @spec JPMS
      */
     protected URL findResource(String moduleName, String name) throws IOException {
         if (moduleName == null) {
@@ -1342,6 +1354,8 @@
      * @throws  NullPointerException If {@code name} is {@code null}
      *
      * @since  1.1
+     * @revised 9
+     * @spec JPMS
      */
     public URL getResource(String name) {
         Objects.requireNonNull(name);
@@ -1403,6 +1417,8 @@
      * @see  #findResources(String)
      *
      * @since  1.2
+     * @revised 9
+     * @spec JPMS
      */
     public Enumeration<URL> getResources(String name) throws IOException {
         Objects.requireNonNull(name);
@@ -1499,6 +1515,8 @@
      *          denied by the security manager.
      *
      * @since  1.2
+     * @revised 9
+     * @spec JPMS
      */
     protected URL findResource(String name) {
         return null;
@@ -1531,6 +1549,8 @@
      *          If I/O errors occur
      *
      * @since  1.2
+     * @revised 9
+     * @spec JPMS
      */
     protected Enumeration<URL> findResources(String name) throws IOException {
         return Collections.emptyEnumeration();
@@ -1601,6 +1621,8 @@
      *          denied by the security manager.
      *
      * @since  1.1
+     * @revised 9
+     * @spec JPMS
      */
     public static URL getSystemResource(String name) {
         return getSystemClassLoader().getResource(name);
@@ -1636,6 +1658,8 @@
      *          If I/O errors occur
      *
      * @since  1.2
+     * @revised 9
+     * @spec JPMS
      */
     public static Enumeration<URL> getSystemResources(String name)
         throws IOException
@@ -1667,6 +1691,8 @@
      * @throws  NullPointerException If {@code name} is {@code null}
      *
      * @since  1.1
+     * @revised 9
+     * @spec JPMS
      */
     public InputStream getResourceAsStream(String name) {
         Objects.requireNonNull(name);
@@ -1699,6 +1725,8 @@
      *          denied by the security manager.
      *
      * @since  1.1
+     * @revised 9
+     * @spec JPMS
      */
     public static InputStream getSystemResourceAsStream(String name) {
         URL url = getSystemResource(name);
@@ -1749,6 +1777,7 @@
      *
      * @see Module#isNamed()
      * @since 9
+     * @spec JPMS
      */
     public final Module getUnnamedModule() {
         return unnamedModule;
@@ -1772,6 +1801,7 @@
      *          {@link RuntimePermission}{@code ("getClassLoader")}
      *
      * @since 9
+     * @spec JPMS
      */
     @CallerSensitive
     public static ClassLoader getPlatformClassLoader() {
@@ -1847,6 +1877,8 @@
      *          {@link Throwable#getCause()} method.
      *
      * @revised  1.4
+     * @revised 9
+     * @spec JPMS
      */
     @CallerSensitive
     public static ClassLoader getSystemClassLoader() {
@@ -2101,6 +2133,8 @@
      *          defined by this class loader
      *
      * @since  1.2
+     * @revised 9
+     * @spec JPMS
      *
      * @see <a href="../../../technotes/guides/jar/jar.html#versioning">
      *      The JAR File Specification: Package Versioning</a>
@@ -2138,6 +2172,7 @@
      *          if {@code name} is {@code null}.
      *
      * @since  9
+     * @spec JPMS
      */
     public final Package getDefinedPackage(String name) {
         Objects.requireNonNull(name, "name cannot be null");
@@ -2160,6 +2195,7 @@
      *         or an zero length array if no package has been defined by this class loader.
      *
      * @since  9
+     * @spec JPMS
      */
     public final Package[] getDefinedPackages() {
         return packages().toArray(Package[]::new);
@@ -2196,6 +2232,8 @@
      * a {@code Package} for the specified class loader.
      *
      * @since  1.2
+     * @revised 9
+     * @spec JPMS
      */
     @Deprecated(since="9")
     protected Package getPackage(String name) {
@@ -2220,6 +2258,8 @@
      *          class loader and its ancestors
      *
      * @since  1.2
+     * @revised 9
+     * @spec JPMS
      */
     protected Package[] getPackages() {
         Stream<Package> pkgs = packages();
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/java/lang/IllegalCallerException.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,76 @@
+/*
+ * Copyright (c) 2017, 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;
+
+/**
+ * Thrown to indicate that a method has been called by an inappropriate caller.
+ *
+ * @since 9
+ * @spec JPMS
+ * @see StackWalker#getCallerClass
+ */
+public class IllegalCallerException extends RuntimeException {
+    /**
+     * Constructs an IllegalCallerException with no detail message.
+     */
+    public IllegalCallerException() {
+        super();
+    }
+
+    /**
+     * Constructs an IllegalCallerException with the specified detail
+     * message.
+     *
+     * @param s the String that contains a detailed message (can be null)
+     */
+    public IllegalCallerException(String s) {
+        super(s);
+    }
+
+    /**
+     * Constructs a new exception with the specified detail message and
+     * cause.
+     *
+     * @param  message the detail message (can be null)
+     * @param  cause the cause (can be null)
+     */
+    public IllegalCallerException(String message, Throwable cause) {
+        super(message, cause);
+    }
+
+    /**
+     * Constructs a new exception with the specified cause and a detail
+     * message of {@code (cause==null ? null : cause.toString())} (which
+     * typically contains the class and detail message of {@code cause}).
+     *
+     * @param  cause the cause (can be null)
+     */
+    public IllegalCallerException(Throwable cause) {
+        super(cause);
+    }
+
+    static final long serialVersionUID = -2349421918363102232L;
+}
--- a/jdk/src/java.base/share/classes/java/lang/LiveStackFrame.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/LiveStackFrame.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2017, 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
@@ -55,14 +55,36 @@
      *
      * <p>A single local variable can hold a value of type boolean, byte, char,
      * short, int, float, reference or returnAddress.  A pair of local variables
-     * can hold a value of type long or double.  In other words,
-     * a value of type long or type double occupies two consecutive local
-     * variables.  For a value of primitive type, the element in the
-     * local variable array is an {@link PrimitiveValue} object;
-     * otherwise, the element is an {@code Object}.
+     * can hold a value of type long or double (JVMS section 2.6.1).  Primitive
+     * locals are represented in the returned array as {@code PrimitiveSlot}s,
+     * with longs and doubles occupying a pair of consecutive
+     * {@code PrimitiveSlot}s.
+     *
+     * <p>The current VM implementation does not provide specific type
+     * information for primitive locals.  This method simply returns the raw
+     * contents of the VM's primitive locals on a best-effort basis, without
+     * indicating a specific type.
+     *
+     * <p>The returned array may contain null entries for local variables that
+     * are not live.
      *
-     * <p>The returned array may contain null entries if a local variable is not
-     * live.
+     * @implNote
+     * <p> The specific subclass of {@code PrimitiveSlot} will reflect the
+     * underlying architecture, and will be either {@code PrimitiveSlot32} or
+     * {@code PrimitiveSlot64}.
+     *
+     * <p>How a long or double value is stored in the pair of
+     * {@code PrimitiveSlot}s can vary based on the underlying architecture and
+     * VM implementation.  On 32-bit architectures, long/double values are split
+     * between the two {@code PrimitiveSlot32}s.
+     * On 64-bit architectures, the entire value may be stored in one of the
+     * {@code PrimitiveSlot64}s, with the other {@code PrimitiveSlot64} being
+     * unused.
+     *
+     * <p>The contents of the unused, high-order portion of a
+     * {@code PrimitiveSlot64} (when storing a primitive other than a long or
+     * double) is unspecified.  In particular, the unused bits are not
+     * necessarily zeroed out.
      *
      * @return  the local variable array of this stack frame.
      */
@@ -78,7 +100,7 @@
      * <p>Each entry on the operand stack can hold a value of any Java Virtual
      * Machine Type.
      * For a value of primitive type, the element in the returned array is
-     * an {@link PrimitiveValue} object; otherwise, the element is the {@code Object}
+     * a {@link PrimitiveSlot} object; otherwise, the element is the {@code Object}
      * on the operand stack.
      *
      * @return the operand stack of this stack frame.
@@ -87,107 +109,37 @@
 
     /**
      * <em>UNSUPPORTED</em> This interface is intended to be package-private
-     * or move to an internal package.<p>
+     * or moved to an internal package.<p>
      *
-     * Represents a local variable or an entry on the operand whose value is
+     * Represents a local variable or an entry on the operand stack whose value is
      * of primitive type.
      */
-    public abstract class PrimitiveValue {
+    public abstract class PrimitiveSlot {
         /**
-         * Returns the base type of this primitive value, one of
-         * {@code B, D, C, F, I, J, S, Z}.
-         *
-         * @return Name of a base type
-         * @jvms table 4.3-A
+         * Returns the size, in bytes, of the slot.
          */
-        abstract char type();
+        public abstract int size();
 
         /**
-         * Returns the boolean value if this primitive value is of type boolean.
-         * @return the boolean value if this primitive value is of type boolean.
+         * Returns the int value if this primitive value is of size 4
+         * @return the int value if this primitive value is of size 4
          *
          * @throws UnsupportedOperationException if this primitive value is not
-         * of type boolean.
-         */
-        public boolean booleanValue() {
-            throw new UnsupportedOperationException("this primitive of type " + type());
-        }
-
-        /**
-         * Returns the int value if this primitive value is of type int.
-         * @return the int value if this primitive value is of type int.
-         *
-         * @throws UnsupportedOperationException if this primitive value is not
-         * of type int.
+         * of size 4.
          */
         public int intValue() {
-            throw new UnsupportedOperationException("this primitive of type " + type());
-        }
-
-        /**
-         * Returns the long value if this primitive value is of type long.
-         * @return the long value if this primitive value is of type long.
-         *
-         * @throws UnsupportedOperationException if this primitive value is not
-         * of type long.
-         */
-        public long longValue() {
-            throw new UnsupportedOperationException("this primitive of type " + type());
+            throw new UnsupportedOperationException("this " + size() + "-byte primitive");
         }
 
         /**
-         * Returns the char value if this primitive value is of type char.
-         * @return the char value if this primitive value is of type char.
-         *
-         * @throws UnsupportedOperationException if this primitive value is not
-         * of type char.
-         */
-        public char charValue() {
-            throw new UnsupportedOperationException("this primitive of type " + type());
-        }
-
-        /**
-         * Returns the byte value if this primitive value is of type byte.
-         * @return the byte value if this primitive value is of type byte.
-         *
-         * @throws UnsupportedOperationException if this primitive value is not
-         * of type byte.
-         */
-        public byte byteValue() {
-            throw new UnsupportedOperationException("this primitive of type " + type());
-        }
-
-        /**
-         * Returns the short value if this primitive value is of type short.
-         * @return the short value if this primitive value is of type short.
+         * Returns the long value if this primitive value is of size 8
+         * @return the long value if this primitive value is of size 8
          *
          * @throws UnsupportedOperationException if this primitive value is not
-         * of type short.
-         */
-        public short shortValue() {
-            throw new UnsupportedOperationException("this primitive of type " + type());
-        }
-
-        /**
-         * Returns the float value if this primitive value is of type float.
-         * @return the float value if this primitive value is of type float.
-         *
-         * @throws UnsupportedOperationException if this primitive value is not
-         * of type float.
+         * of size 8.
          */
-        public float floatValue() {
-            throw new UnsupportedOperationException("this primitive of type " + type());
-        }
-
-        /**
-         * Returns the double value if this primitive value is of type double.
-         * @return the double value if this primitive value is of type double.
-         *
-         * @throws UnsupportedOperationException if this primitive value is not
-         * of type double.
-         */
-        public double doubleValue() {
-            throw new UnsupportedOperationException("this primitive of type " + type());
+        public long longValue() {
+            throw new UnsupportedOperationException("this " + size() + "-byte primitive");
         }
     }
 
--- a/jdk/src/java.base/share/classes/java/lang/LiveStackFrameInfo.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/LiveStackFrameInfo.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2017, 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
@@ -24,15 +24,13 @@
  */
 package java.lang;
 
-import java.lang.StackWalker.Option;
-import java.util.EnumSet;
-import java.util.Set;
-
-import static java.lang.StackWalker.ExtendedOption.*;
-
 final class LiveStackFrameInfo extends StackFrameInfo implements LiveStackFrame {
     private static Object[] EMPTY_ARRAY = new Object[0];
 
+    // These flags must match the values maintained in the VM
+    private static final int MODE_INTERPRETED = 0x01;
+    private static final int MODE_COMPILED    = 0x02;
+
     LiveStackFrameInfo(StackWalker walker) {
         super(walker);
     }
@@ -41,6 +39,7 @@
     private Object[] monitors = EMPTY_ARRAY;
     private Object[] locals = EMPTY_ARRAY;
     private Object[] operands = EMPTY_ARRAY;
+    private int mode = 0;
 
     @Override
     public Object[] getMonitors() {
@@ -57,51 +56,44 @@
         return operands;
     }
 
-    /*
-     * Convert primitive value to {@code Primitive} object to represent
-     * a local variable or an element on the operand stack of primitive type.
-     */
-    static PrimitiveValue asPrimitive(boolean value) {
-        return new BooleanPrimitive(value);
-    }
-
-    static PrimitiveValue asPrimitive(int value) {
-        return new IntPrimitive(value);
-    }
-
-    static PrimitiveValue asPrimitive(short value) {
-        return new ShortPrimitive(value);
-    }
-
-    static PrimitiveValue asPrimitive(char value) {
-        return new CharPrimitive(value);
+    @Override
+    public String toString() {
+        StringBuilder retVal = new StringBuilder(super.toString());
+        if (mode != 0) {
+            retVal.append("(");
+            if ((mode & MODE_INTERPRETED) == MODE_INTERPRETED) {
+                retVal.append(" interpreted ");
+            }
+            if ((mode & MODE_COMPILED) == MODE_COMPILED) {
+                retVal.append(" compiled ");
+            }
+            retVal.append(")");
+        }
+        return retVal.toString();
     }
 
-    static PrimitiveValue asPrimitive(byte value) {
-        return new BytePrimitive(value);
-    }
+    /*
+     * Convert primitive value to {@code PrimitiveSlot} object to represent
+     * a local variable or an element on the operand stack of primitive type.
+     */
 
-    static PrimitiveValue asPrimitive(long value) {
-        return new LongPrimitive(value);
+    static PrimitiveSlot asPrimitive(int value) {
+        return new PrimitiveSlot32(value);
     }
 
-    static PrimitiveValue asPrimitive(float value) {
-        return new FloatPrimitive(value);
+    static PrimitiveSlot asPrimitive(long value) {
+        return new PrimitiveSlot64(value);
     }
 
-    static PrimitiveValue asPrimitive(double value) {
-        return new DoublePrimitive(value);
-    }
-
-    private static class IntPrimitive extends PrimitiveValue {
+    private static class PrimitiveSlot32 extends PrimitiveSlot {
         final int value;
-        IntPrimitive(int value) {
+        PrimitiveSlot32(int value) {
             this.value = value;
         }
 
         @Override
-        public char type() {
-            return 'I';
+        public int size() {
+            return 4;
         }
 
         @Override
@@ -115,103 +107,15 @@
         }
     }
 
-    private static class ShortPrimitive extends PrimitiveValue {
-        final short value;
-        ShortPrimitive(short value) {
-            this.value = value;
-        }
-
-        @Override
-        public char type() {
-            return 'S';
-        }
-
-        @Override
-        public short shortValue() {
-            return value;
-        }
-
-        @Override
-        public String toString() {
-            return String.valueOf(value);
-        }
-    }
-
-    private static class BooleanPrimitive extends PrimitiveValue {
-        final boolean value;
-        BooleanPrimitive(boolean value) {
+    private static class PrimitiveSlot64 extends PrimitiveSlot {
+        final long value;
+        PrimitiveSlot64(long value) {
             this.value = value;
         }
 
         @Override
-        public char type() {
-            return 'Z';
-        }
-
-        @Override
-        public boolean booleanValue()  {
-            return value;
-        }
-
-        @Override
-        public String toString() {
-            return String.valueOf(value);
-        }
-    }
-
-    private static class CharPrimitive extends PrimitiveValue {
-        final char value;
-        CharPrimitive(char value) {
-            this.value = value;
-        }
-
-        @Override
-        public char type() {
-            return 'C';
-        }
-
-        @Override
-        public char charValue() {
-            return value;
-        }
-
-        @Override
-        public String toString() {
-            return String.valueOf(value);
-        }
-    }
-
-    private static class BytePrimitive extends PrimitiveValue {
-        final byte value;
-        BytePrimitive(byte value) {
-            this.value = value;
-        }
-
-        @Override
-        public char type() {
-            return 'B';
-        }
-
-        @Override
-        public byte byteValue() {
-            return value;
-        }
-
-        @Override
-        public String toString() {
-            return String.valueOf(value);
-        }
-    }
-
-    private static class LongPrimitive extends PrimitiveValue {
-        final long value;
-        LongPrimitive(long value) {
-            this.value = value;
-        }
-
-        @Override
-        public char type() {
-            return 'J';
+        public int size() {
+            return 8;
         }
 
         @Override
@@ -224,48 +128,4 @@
             return String.valueOf(value);
         }
     }
-
-    private static class FloatPrimitive extends PrimitiveValue {
-        final float value;
-        FloatPrimitive(float value) {
-            this.value = value;
-        }
-
-        @Override
-        public char type() {
-            return 'F';
-        }
-
-        @Override
-        public float floatValue() {
-            return value;
-        }
-
-        @Override
-        public String toString() {
-            return String.valueOf(value);
-        }
-    }
-
-    private static class DoublePrimitive extends PrimitiveValue {
-        final double value;
-        DoublePrimitive(double value) {
-            this.value = value;
-        }
-
-        @Override
-        public char type() {
-            return 'D';
-        }
-
-        @Override
-        public double doubleValue() {
-            return value;
-        }
-
-        @Override
-        public String toString() {
-            return String.valueOf(value);
-        }
-    }
 }
--- a/jdk/src/java.base/share/classes/java/lang/Package.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/Package.java	Wed Jul 05 22:52:01 2017 +0200
@@ -111,6 +111,8 @@
  * @see ClassLoader#definePackage(String, String, String, String, String, String, String, URL)
  *
  * @since 1.2
+ * @revised 9
+ * @spec JPMS
  */
 public class Package extends NamedPackage implements java.lang.reflect.AnnotatedElement {
     /**
@@ -207,6 +209,9 @@
      * is returned if it is not known.
      * @return the vendor that implemented this package, {@code null}
      * is returned if it is not known.
+     *
+     * @revised 9
+     * @spec JPMS
      */
     public String getImplementationVendor() {
         return versionInfo.implVendor;
@@ -334,6 +339,9 @@
      * a {@code Package} for the specified class loader.
      *
      * @see ClassLoader#getDefinedPackage
+     *
+     * @revised 9
+     * @spec JPMS
      */
     @CallerSensitive
     @Deprecated(since="9")
@@ -356,6 +364,9 @@
      *          class loader and its ancestors
      *
      * @see ClassLoader#getDefinedPackages
+     *
+     * @revised 9
+     * @spec JPMS
      */
     @CallerSensitive
     public static Package[] getPackages() {
--- a/jdk/src/java.base/share/classes/java/lang/SecurityManager.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/SecurityManager.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1458,6 +1458,18 @@
     }
 
     /**
+     * Called by java.security.Security
+     */
+    static void invalidatePackageAccessCache() {
+        synchronized (packageAccessLock) {
+            packageAccessValid = false;
+        }
+        synchronized (packageDefinitionLock) {
+            packageDefinitionValid = false;
+        }
+    }
+
+    /**
      * Returns true if the module's loader is the boot or platform loader.
      */
     private static boolean isBootOrPlatformModule(Module m) {
--- a/jdk/src/java.base/share/classes/java/lang/StackStreamFactory.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/StackStreamFactory.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,11 +25,13 @@
 package java.lang;
 
 import jdk.internal.reflect.MethodAccessor;
+import jdk.internal.reflect.ConstructorAccessor;
 import java.lang.StackWalker.Option;
 import java.lang.StackWalker.StackFrame;
 
 import java.lang.annotation.Native;
 import java.lang.reflect.Method;
+import java.lang.reflect.Constructor;
 import java.util.HashSet;
 import java.util.NoSuchElementException;
 import java.util.Objects;
@@ -684,7 +686,7 @@
                 frames[n++] = caller;
             }
             if (frames[1] == null) {
-                throw new IllegalStateException("no caller frame");
+                throw new IllegalCallerException("no caller frame");
             }
             return n;
         }
@@ -922,7 +924,8 @@
          */
         final void setBatch(int depth, int startIndex, int endIndex) {
             if (startIndex <= 0 || endIndex <= 0)
-                throw new IllegalArgumentException("startIndex=" + startIndex + " endIndex=" + endIndex);
+                throw new IllegalArgumentException("startIndex=" + startIndex
+                        + " endIndex=" + endIndex);
 
             this.origin = startIndex;
             this.fence = endIndex;
@@ -980,13 +983,18 @@
 
     private static boolean isReflectionFrame(Class<?> c) {
         if (c.getName().startsWith("jdk.internal.reflect") &&
-                !MethodAccessor.class.isAssignableFrom(c)) {
-            throw new InternalError("Not jdk.internal.reflect.MethodAccessor: " + c.toString());
+                !MethodAccessor.class.isAssignableFrom(c) &&
+                !ConstructorAccessor.class.isAssignableFrom(c)) {
+            throw new InternalError("Not jdk.internal.reflect.MethodAccessor"
+                    + " or jdk.internal.reflect.ConstructorAccessor: "
+                    + c.toString());
         }
         // ## should filter all @Hidden frames?
         return c == Method.class ||
-                MethodAccessor.class.isAssignableFrom(c) ||
-                c.getName().startsWith("java.lang.invoke.LambdaForm");
+               c == Constructor.class ||
+               MethodAccessor.class.isAssignableFrom(c) ||
+               ConstructorAccessor.class.isAssignableFrom(c) ||
+               c.getName().startsWith("java.lang.invoke.LambdaForm");
     }
 
 }
--- a/jdk/src/java.base/share/classes/java/lang/StackTraceElement.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/StackTraceElement.java	Wed Jul 05 22:52:01 2017 +0200
@@ -92,6 +92,8 @@
      * @throws NullPointerException if {@code declaringClass} or
      *         {@code methodName} is null
      * @since 1.5
+     * @revised 9
+     * @spec JPMS
      */
     public StackTraceElement(String declaringClass, String methodName,
                              String fileName, int lineNumber) {
@@ -128,6 +130,7 @@
      *         or {@code methodName} is {@code null}
      *
      * @since 9
+     * @spec JPMS
      */
     public StackTraceElement(String classLoaderName,
                              String moduleName, String moduleVersion,
@@ -187,6 +190,7 @@
      *         point represented by this stack trace element; {@code null}
      *         if the module name is not available.
      * @since 9
+     * @spec JPMS
      * @see java.lang.reflect.Module#getName()
      */
     public String getModuleName() {
@@ -201,6 +205,7 @@
      *         point represented by this stack trace element; {@code null}
      *         if the module version is not available.
      * @since 9
+     * @spec JPMS
      * @see java.lang.module.ModuleDescriptor.Version
      */
     public String getModuleVersion() {
@@ -216,6 +221,7 @@
      *         if the class loader is not named.
      *
      * @since 9
+     * @spec JPMS
      * @see java.lang.ClassLoader#getName()
      */
     public String getClassLoaderName() {
@@ -329,6 +335,8 @@
      * {@link java.lang.StackWalker.StackFrame}, where an implementation may
      * choose to omit some element in the returned string.
      *
+     * @revised 9
+     * @spec JPMS
      * @see    Throwable#printStackTrace()
      */
     public String toString() {
@@ -376,6 +384,9 @@
      * @return true if the specified object is another
      *         {@code StackTraceElement} instance representing the same
      *         execution point as this instance.
+     *
+     * @revised 9
+     * @spec JPMS
      */
     public boolean equals(Object obj) {
         if (obj==this)
--- a/jdk/src/java.base/share/classes/java/lang/StackWalker.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/StackWalker.java	Wed Jul 05 22:52:01 2017 +0200
@@ -29,6 +29,7 @@
 import java.util.*;
 import java.util.function.Consumer;
 import java.util.function.Function;
+import java.util.function.Predicate;
 import java.util.stream.Stream;
 
 /**
@@ -207,13 +208,23 @@
         /**
          * Shows all reflection frames.
          *
-         * <p>By default, reflection frames are hidden.  This includes the
-         * {@link java.lang.reflect.Method#invoke} method
-         * and the reflection implementation classes. A {@code StackWalker} with
-         * this {@code SHOW_REFLECT_FRAMES} option will show all reflection frames.
-         * The {@link #SHOW_HIDDEN_FRAMES} option can also be used to show all
+         * <p>By default, reflection frames are hidden.  A {@code StackWalker}
+         * configured with this {@code SHOW_REFLECT_FRAMES} option
+         * will show all reflection frames that
+         * include {@link java.lang.reflect.Method#invoke} and
+         * {@link java.lang.reflect.Constructor#newInstance(Object...)}
+         * and their reflection implementation classes.
+         *
+         * <p>The {@link #SHOW_HIDDEN_FRAMES} option can also be used to show all
          * reflection frames and it will also show other hidden frames that
          * are implementation-specific.
+         *
+         * @apiNote
+         * This option includes the stack frames representing the invocation of
+         * {@code Method} and {@code Constructor}.  Any utility methods that
+         * are equivalent to calling {@code Method.invoke} or
+         * {@code Constructor.newInstance} such as {@code Class.newInstance}
+         * are not filtered or controlled by any stack walking option.
          */
         SHOW_REFLECT_FRAMES,
         /**
@@ -465,28 +476,31 @@
     }
 
     /**
-     * Gets the {@code Class} object of the caller invoking the method
-     * that calls this {@code getCallerClass} method.
+     * Gets the {@code Class} object of the caller who invoked the method
+     * that invoked {@code getCallerClass}.
      *
-     * <p> Reflection frames, {@link java.lang.invoke.MethodHandle}, and
-     * hidden frames are filtered regardless of the
+     * <p> This method filters {@linkplain Option#SHOW_REFLECT_FRAMES reflection
+     * frames}, {@link java.lang.invoke.MethodHandle}, and
+     * {@linkplain Option#SHOW_HIDDEN_FRAMES hidden frames} regardless of the
      * {@link Option#SHOW_REFLECT_FRAMES SHOW_REFLECT_FRAMES}
      * and {@link Option#SHOW_HIDDEN_FRAMES SHOW_HIDDEN_FRAMES} options
      * this {@code StackWalker} has been configured with.
      *
+     * <p> This method should be called when a caller frame is present.  If
+     * it is called from the bottom most frame on the stack,
+     * {@code IllegalCallerException} will be thrown.
+     *
      * <p> This method throws {@code UnsupportedOperationException}
      * if this {@code StackWalker} is not configured with the
      * {@link Option#RETAIN_CLASS_REFERENCE RETAIN_CLASS_REFERENCE} option.
-     * This method should be called when a caller frame is present.  If
-     * it is called from the last frame on the stack,
-     * {@code IllegalStateException} will be thrown.
      *
      * @apiNote
      * For example, {@code Util::getResourceBundle} loads a resource bundle
-     * on behalf of the caller.  It calls this {@code getCallerClass} method
-     * to find the method calling {@code Util::getResourceBundle} and uses the caller's
-     * class loader to load the resource bundle. The caller class in this example
-     * is the {@code MyTool} class.
+     * on behalf of the caller.  It invokes {@code getCallerClass} to identify
+     * the class whose method called {@code Util::getResourceBundle}.
+     * Then, it obtains the class loader of that class, and uses
+     * the class loader to load the resource bundle. The caller class
+     * in this example is {@code MyTool}.
      *
      * <pre>{@code
      * class Util {
@@ -517,17 +531,17 @@
      * }</pre>
      *
      * When the {@code getCallerClass} method is called from a method that
-     * is the last frame on the stack,
+     * is the bottom most frame on the stack,
      * for example, {@code static public void main} method launched by the
      * {@code java} launcher, or a method invoked from a JNI attached thread,
-     * {@code IllegalStateException} is thrown.
+     * {@code IllegalCallerException} is thrown.
      *
      * @return {@code Class} object of the caller's caller invoking this method.
      *
      * @throws UnsupportedOperationException if this {@code StackWalker}
      *         is not configured with {@link Option#RETAIN_CLASS_REFERENCE
      *         Option.RETAIN_CLASS_REFERENCE}.
-     * @throws IllegalStateException if there is no caller frame, i.e.
+     * @throws IllegalCallerException if there is no caller frame, i.e.
      *         when this {@code getCallerClass} method is called from a method
      *         which is the last frame on the stack.
      */
--- a/jdk/src/java.base/share/classes/java/lang/System.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/System.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1942,13 +1942,12 @@
      * the application classpath or modulepath.
      */
     private static void initPhase3() {
-        // Initialize publicLookup early, to avoid bootstrapping circularities
-        // with security manager using java.lang.invoke infrastructure.
-        java.lang.invoke.MethodHandles.publicLookup();
-
         // set security manager
         String cn = System.getProperty("java.security.manager");
         if (cn != null) {
+            // ensure image reader for java.base is initialized before security manager
+            Object.class.getResource("module-info.class");
+
             if (cn.isEmpty() || "default".equals(cn)) {
                 System.setSecurityManager(new SecurityManager());
             } else {
@@ -2053,6 +2052,9 @@
             public String fastUUID(long lsb, long msb) {
                 return Long.fastUUID(lsb, msb);
             }
+            public void invalidatePackageAccessCache() {
+                SecurityManager.invalidatePackageAccessCache();
+            }
         });
     }
 }
--- a/jdk/src/java.base/share/classes/java/lang/invoke/AbstractValidatingLambdaMetafactory.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/invoke/AbstractValidatingLambdaMetafactory.java	Wed Jul 05 22:52:01 2017 +0200
@@ -141,6 +141,18 @@
         this.markerInterfaces = markerInterfaces;
         this.additionalBridges = additionalBridges;
 
+        if (samMethodName.isEmpty() ||
+                samMethodName.indexOf('.') >= 0 ||
+                samMethodName.indexOf(';') >= 0 ||
+                samMethodName.indexOf('[') >= 0 ||
+                samMethodName.indexOf('/') >= 0 ||
+                samMethodName.indexOf('<') >= 0 ||
+                samMethodName.indexOf('>') >= 0) {
+            throw new LambdaConversionException(String.format(
+                    "Method name '%s' is not legal",
+                    samMethodName));
+        }
+
         if (!samBase.isInterface()) {
             throw new LambdaConversionException(String.format(
                     "Functional interface %s is not an interface",
@@ -275,25 +287,39 @@
                 (implKind == MethodHandleInfo.REF_newInvokeSpecial)
                   ? implDefiningClass
                   : implMethodType.returnType();
-        Class<?> samReturnType = samMethodType.returnType();
         if (!isAdaptableToAsReturn(actualReturnType, expectedType)) {
             throw new LambdaConversionException(
                     String.format("Type mismatch for lambda return: %s is not convertible to %s",
                                   actualReturnType, expectedType));
         }
-        if (!isAdaptableToAsReturnStrict(expectedType, samReturnType)) {
-            throw new LambdaConversionException(
-                    String.format("Type mismatch for lambda expected return: %s is not convertible to %s",
-                                  expectedType, samReturnType));
+
+        // Check descriptors of generated methods
+        checkDescriptor(samMethodType);
+        for (MethodType bridgeMT : additionalBridges) {
+            checkDescriptor(bridgeMT);
         }
-        for (MethodType bridgeMT : additionalBridges) {
-            if (!isAdaptableToAsReturnStrict(expectedType, bridgeMT.returnType())) {
-                throw new LambdaConversionException(
-                        String.format("Type mismatch for lambda expected return: %s is not convertible to %s",
-                                      expectedType, bridgeMT.returnType()));
+    }
+
+    /** Validate that the given descriptor's types are compatible with {@code instantiatedMethodType} **/
+    private void checkDescriptor(MethodType descriptor) throws LambdaConversionException {
+        for (int i = 0; i < instantiatedMethodType.parameterCount(); i++) {
+            Class<?> instantiatedParamType = instantiatedMethodType.parameterType(i);
+            Class<?> descriptorParamType = descriptor.parameterType(i);
+            if (!descriptorParamType.isAssignableFrom(instantiatedParamType)) {
+                String msg = String.format("Type mismatch for instantiated parameter %d: %s is not a subtype of %s",
+                                           i, instantiatedParamType, descriptorParamType);
+                throw new LambdaConversionException(msg);
             }
         }
-     }
+
+        Class<?> instantiatedReturnType = instantiatedMethodType.returnType();
+        Class<?> descriptorReturnType = descriptor.returnType();
+        if (!isAdaptableToAsReturnStrict(instantiatedReturnType, descriptorReturnType)) {
+            String msg = String.format("Type mismatch for lambda expected return: %s is not convertible to %s",
+                                       instantiatedReturnType, descriptorReturnType);
+            throw new LambdaConversionException(msg);
+        }
+    }
 
     /**
      * Check type adaptability for parameter types.
@@ -345,8 +371,8 @@
                || !fromType.equals(void.class) && isAdaptableTo(fromType, toType, false);
     }
     private boolean isAdaptableToAsReturnStrict(Class<?> fromType, Class<?> toType) {
-        if (fromType.equals(void.class)) return toType.equals(void.class);
-        return isAdaptableTo(fromType, toType, true);
+        if (fromType.equals(void.class) || toType.equals(void.class)) return fromType.equals(toType);
+        else return isAdaptableTo(fromType, toType, true);
     }
 
 
--- a/jdk/src/java.base/share/classes/java/lang/invoke/MethodHandles.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/invoke/MethodHandles.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,8 +25,6 @@
 
 package java.lang.invoke;
 
-import jdk.internal.org.objectweb.asm.ClassWriter;
-import jdk.internal.org.objectweb.asm.Opcodes;
 import jdk.internal.reflect.CallerSensitive;
 import jdk.internal.reflect.Reflection;
 import jdk.internal.vm.annotation.ForceInline;
@@ -111,13 +109,17 @@
 
     /**
      * Returns a {@link Lookup lookup object} which is trusted minimally.
-     * It can only be used to create method handles to public members in
+     * The lookup has the {@code PUBLIC} and {@code UNCONDITIONAL} modes.
+     * It can only be used to create method handles to public members of
      * public classes in packages that are exported unconditionally.
      * <p>
-     * For now, the {@linkplain Lookup#lookupClass lookup class} of this lookup
-     * object is in an unnamed module.
-     * Consequently, the lookup context of this lookup object will be the bootstrap
-     * class loader, which means it cannot find user classes.
+     * As a matter of pure convention, the {@linkplain Lookup#lookupClass lookup class}
+     * of this lookup object will be {@link java.lang.Object}.
+     *
+     * @apiNote The use of Object is conventional, and because the lookup modes are
+     * limited, there is no special access provided to the internals of Object, its package
+     * or its module. Consequently, the lookup context of this lookup object will be the
+     * bootstrap class loader, which means it cannot find user classes.
      *
      * <p style="font-size:smaller;">
      * <em>Discussion:</em>
@@ -129,17 +131,12 @@
      * Also, it cannot access
      * <a href="MethodHandles.Lookup.html#callsens">caller sensitive methods</a>.
      * @return a lookup object which is trusted minimally
+     *
+     * @revised 9
+     * @spec JPMS
      */
     public static Lookup publicLookup() {
-        // During VM startup then only classes in the java.base module can be
-        // loaded and linked. This is because java.base exports aren't setup until
-        // the module system is initialized, hence types in the unnamed module
-        // (or any named module) can't link to java/lang/Object.
-        if (!jdk.internal.misc.VM.isModuleSystemInited()) {
-            return new Lookup(Object.class, Lookup.PUBLIC);
-        } else {
-            return LookupHelper.PUBLIC_LOOKUP;
-        }
+        return Lookup.PUBLIC_LOOKUP;
     }
 
     /**
@@ -172,6 +169,7 @@
      * @throws IllegalAccessException if the access check specified above fails
      * @throws SecurityException if denied by the security manager
      * @since 9
+     * @spec JPMS
      * @see Lookup#dropLookupMode
      */
     public static Lookup privateLookupIn(Class<?> targetClass, Lookup lookup) throws IllegalAccessException {
@@ -183,11 +181,11 @@
             throw new IllegalArgumentException(targetClass + " is an array class");
         Module targetModule = targetClass.getModule();
         Module callerModule = lookup.lookupClass().getModule();
-        if (callerModule != targetModule && targetModule.isNamed()) {
-            if (!callerModule.canRead(targetModule))
-                throw new IllegalAccessException(callerModule + " does not read " + targetModule);
+        if (!callerModule.canRead(targetModule))
+            throw new IllegalAccessException(callerModule + " does not read " + targetModule);
+        if (targetModule.isNamed()) {
             String pn = targetClass.getPackageName();
-            assert pn != null && pn.length() > 0 : "unnamed package cannot be in named module";
+            assert pn.length() > 0 : "unnamed package cannot be in named module";
             if (!targetModule.isOpen(pn, callerModule))
                 throw new IllegalAccessException(targetModule + " does not open " + pn + " to " + callerModule);
         }
@@ -601,6 +599,8 @@
      * so that there can be a secure foundation for lookups.
      * Nearly all other methods in the JSR 292 API rely on lookup
      * objects to check access requests.
+     *
+     * @revised 9
      */
     public static final
     class Lookup {
@@ -647,15 +647,33 @@
          *  lookup class and public types in packages exported by other modules
          *  to the module of the lookup class.
          *  @since 9
+         *  @spec JPMS
          */
         public static final int MODULE = PACKAGE << 1;
 
-        private static final int ALL_MODES = (PUBLIC | PRIVATE | PROTECTED | PACKAGE | MODULE);
+        /** A single-bit mask representing {@code unconditional} access
+         *  which may contribute to the result of {@link #lookupModes lookupModes}.
+         *  The value is {@code 0x20}, which does not correspond meaningfully to
+         *  any particular {@linkplain java.lang.reflect.Modifier modifier bit}.
+         *  A {@code Lookup} with this lookup mode assumes {@linkplain
+         *  java.lang.reflect.Module#canRead(java.lang.reflect.Module) readability}.
+         *  In conjunction with the {@code PUBLIC} modifier bit, a {@code Lookup}
+         *  with this lookup mode can access all public members of public types
+         *  of all modules where the type is in a package that is {@link
+         *  java.lang.reflect.Module#isExported(String) exported unconditionally}.
+         *  @since 9
+         *  @spec JPMS
+         *  @see #publicLookup()
+         */
+        public static final int UNCONDITIONAL = PACKAGE << 2;
+
+        private static final int ALL_MODES = (PUBLIC | PRIVATE | PROTECTED | PACKAGE | MODULE | UNCONDITIONAL);
+        private static final int FULL_POWER_MODES = (ALL_MODES & ~UNCONDITIONAL);
         private static final int TRUSTED   = -1;
 
         private static int fixmods(int mods) {
-            mods &= (ALL_MODES - PACKAGE - MODULE);
-            return (mods != 0) ? mods : (PACKAGE | MODULE);
+            mods &= (ALL_MODES - PACKAGE - MODULE - UNCONDITIONAL);
+            return (mods != 0) ? mods : (PACKAGE | MODULE | UNCONDITIONAL);
         }
 
         /** Tells which class is performing the lookup.  It is this class against
@@ -682,13 +700,14 @@
          *  {@linkplain #PRIVATE PRIVATE (0x02)},
          *  {@linkplain #PROTECTED PROTECTED (0x04)},
          *  {@linkplain #PACKAGE PACKAGE (0x08)},
-         *  and {@linkplain #MODULE MODULE (0x10)}.
+         *  {@linkplain #MODULE MODULE (0x10)},
+         *  and {@linkplain #UNCONDITIONAL UNCONDITIONAL (0x20)}.
          *  <p>
          *  A freshly-created lookup object
-         *  on the {@linkplain java.lang.invoke.MethodHandles#lookup() caller's class}
-         *  has all possible bits set, since the caller class can access all its own members,
-         *  all public types in the caller's module, and all public types in packages exported
-         *  by other modules to the caller's module.
+         *  on the {@linkplain java.lang.invoke.MethodHandles#lookup() caller's class} has
+         *  all possible bits set, except {@code UNCONDITIONAL}. The lookup can be used to
+         *  access all members of the caller's class, all public types in the caller's module,
+         *  and all public types in packages exported by other modules to the caller's module.
          *  A lookup object on a new lookup class
          *  {@linkplain java.lang.invoke.MethodHandles.Lookup#in created from a previous lookup object}
          *  may have some mode bits set to zero.
@@ -701,6 +720,9 @@
          *  @return the lookup modes, which limit the kinds of access performed by this lookup object
          *  @see #in
          *  @see #dropLookupMode
+         *
+         *  @revised 9
+         *  @spec JPMS
          */
         public int lookupModes() {
             return allowedModes & ALL_MODES;
@@ -712,9 +734,9 @@
          * which in turn is called by a method not in this package.
          */
         Lookup(Class<?> lookupClass) {
-            this(lookupClass, ALL_MODES);
+            this(lookupClass, FULL_POWER_MODES);
             // make sure we haven't accidentally picked up a privileged class:
-            checkUnprivilegedlookupClass(lookupClass, ALL_MODES);
+            checkUnprivilegedlookupClass(lookupClass, FULL_POWER_MODES);
         }
 
         private Lookup(Class<?> lookupClass, int allowedModes) {
@@ -730,19 +752,20 @@
          * However, the resulting {@code Lookup} object is guaranteed
          * to have no more access capabilities than the original.
          * In particular, access capabilities can be lost as follows:<ul>
-         * <li>If the lookup class for this {@code Lookup} is not in a named module,
-         * and the new lookup class is in a named module {@code M}, then no members in
-         * {@code M}'s non-exported packages will be accessible.
-         * <li>If the lookup for this {@code Lookup} is in a named module, and the
-         * new lookup class is in a different module {@code M}, then no members, not even
-         * public members in {@code M}'s exported packages, will be accessible.
-         * <li>If the new lookup class differs from the old one,
-         * protected members will not be accessible by virtue of inheritance.
-         * (Protected members may continue to be accessible because of package sharing.)
+         * <li>If the old lookup class is in a {@link Module#isNamed() named} module, and
+         * the new lookup class is in a different module {@code M}, then no members, not
+         * even public members in {@code M}'s exported packages, will be accessible.
+         * The exception to this is when this lookup is {@link #publicLookup()
+         * publicLookup}, in which case {@code PUBLIC} access is not lost.
+         * <li>If the old lookup class is in an unnamed module, and the new lookup class
+         * is a different module then {@link #MODULE MODULE} access is lost.
+         * <li>If the new lookup class differs from the old one then {@code UNCONDITIONAL} is lost.
          * <li>If the new lookup class is in a different package
          * than the old one, protected and default (package) members will not be accessible.
          * <li>If the new lookup class is not within the same package member
-         * as the old one, private members will not be accessible.
+         * as the old one, private members will not be accessible, and protected members
+         * will not be accessible by virtue of inheritance.
+         * (Protected members may continue to be accessible because of package sharing.)
          * <li>If the new lookup class is not accessible to the old lookup class,
          * then no members, not even public members, will be accessible.
          * (In all other cases, public members will continue to be accessible.)
@@ -757,32 +780,34 @@
          * @return a lookup object which reports the desired lookup class, or the same object
          * if there is no change
          * @throws NullPointerException if the argument is null
+         *
+         * @revised 9
+         * @spec JPMS
          */
         public Lookup in(Class<?> requestedLookupClass) {
             Objects.requireNonNull(requestedLookupClass);
             if (allowedModes == TRUSTED)  // IMPL_LOOKUP can make any lookup at all
-                return new Lookup(requestedLookupClass, ALL_MODES);
+                return new Lookup(requestedLookupClass, FULL_POWER_MODES);
             if (requestedLookupClass == this.lookupClass)
                 return this;  // keep same capabilities
-
-            int newModes = (allowedModes & (ALL_MODES & ~PROTECTED));
+            int newModes = (allowedModes & FULL_POWER_MODES);
             if (!VerifyAccess.isSameModule(this.lookupClass, requestedLookupClass)) {
-                // Allowed to teleport from an unnamed to a named module but resulting
-                // Lookup has no access to module private members
-                if (this.lookupClass.getModule().isNamed()) {
+                // Need to drop all access when teleporting from a named module to another
+                // module. The exception is publicLookup where PUBLIC is not lost.
+                if (this.lookupClass.getModule().isNamed()
+                    && (this.allowedModes & UNCONDITIONAL) == 0)
                     newModes = 0;
-                } else {
-                    newModes &= ~MODULE;
-                }
+                else
+                    newModes &= ~(MODULE|PACKAGE|PRIVATE|PROTECTED);
             }
             if ((newModes & PACKAGE) != 0
                 && !VerifyAccess.isSamePackage(this.lookupClass, requestedLookupClass)) {
-                newModes &= ~(PACKAGE|PRIVATE);
+                newModes &= ~(PACKAGE|PRIVATE|PROTECTED);
             }
             // Allow nestmate lookups to be created without special privilege:
             if ((newModes & PRIVATE) != 0
                 && !VerifyAccess.isSamePackageMember(this.lookupClass, requestedLookupClass)) {
-                newModes &= ~PRIVATE;
+                newModes &= ~(PRIVATE|PROTECTED);
             }
             if ((newModes & PUBLIC) != 0
                 && !VerifyAccess.isClassAccessible(requestedLookupClass, this.lookupClass, allowedModes)) {
@@ -801,28 +826,29 @@
          * finds members, but with a lookup mode that has lost the given lookup mode.
          * The lookup mode to drop is one of {@link #PUBLIC PUBLIC}, {@link #MODULE
          * MODULE}, {@link #PACKAGE PACKAGE}, {@link #PROTECTED PROTECTED} or {@link #PRIVATE PRIVATE}.
-         * {@link #PROTECTED PROTECTED} is always dropped and so the resulting lookup
-         * mode will never have this access capability. When dropping {@code PACKAGE}
-         * then the resulting lookup will not have {@code PACKAGE} or {@code PRIVATE}
-         * access. When dropping {@code MODULE} then the resulting lookup will not
-         * have {@code MODULE}, {@code PACKAGE}, or {@code PRIVATE} access. If {@code
-         * PUBLIC} is dropped then the resulting lookup has no access.
+         * {@link #PROTECTED PROTECTED} and {@link #UNCONDITIONAL UNCONDITIONAL} are always
+         * dropped and so the resulting lookup mode will never have these access capabilities.
+         * When dropping {@code PACKAGE} then the resulting lookup will not have {@code PACKAGE}
+         * or {@code PRIVATE} access. When dropping {@code MODULE} then the resulting lookup will
+         * not have {@code MODULE}, {@code PACKAGE}, or {@code PRIVATE} access. If {@code PUBLIC}
+         * is dropped then the resulting lookup has no access.
          * @param modeToDrop the lookup mode to drop
          * @return a lookup object which lacks the indicated mode, or the same object if there is no change
          * @throws IllegalArgumentException if {@code modeToDrop} is not one of {@code PUBLIC},
-         * {@code MODULE}, {@code PACKAGE}, {@code PROTECTED} or {@code PRIVATE}
+         * {@code MODULE}, {@code PACKAGE}, {@code PROTECTED}, {@code PRIVATE} or {@code UNCONDITIONAL}
+         * @see MethodHandles#privateLookupIn
          * @since 9
-         * @see MethodHandles#privateLookupIn
          */
         public Lookup dropLookupMode(int modeToDrop) {
             int oldModes = lookupModes();
-            int newModes = oldModes & ~(modeToDrop | PROTECTED);
+            int newModes = oldModes & ~(modeToDrop | PROTECTED | UNCONDITIONAL);
             switch (modeToDrop) {
                 case PUBLIC: newModes &= ~(ALL_MODES); break;
                 case MODULE: newModes &= ~(PACKAGE | PRIVATE); break;
                 case PACKAGE: newModes &= ~(PRIVATE); break;
                 case PROTECTED:
-                case PRIVATE: break;
+                case PRIVATE:
+                case UNCONDITIONAL: break;
                 default: throw new IllegalArgumentException(modeToDrop + " is not a valid mode to drop");
             }
             if (newModes == oldModes) return this;  // return self if no change
@@ -835,6 +861,12 @@
         /** Package-private version of lookup which is trusted. */
         static final Lookup IMPL_LOOKUP = new Lookup(Object.class, TRUSTED);
 
+        /** Version of lookup which is trusted minimally.
+         *  It can only be used to create method handles to publicly accessible
+         *  members in packages that are exported unconditionally.
+         */
+        static final Lookup PUBLIC_LOOKUP = new Lookup(Object.class, (PUBLIC|UNCONDITIONAL));
+
         private static void checkUnprivilegedlookupClass(Class<?> lookupClass, int allowedModes) {
             String name = lookupClass.getName();
             if (name.startsWith("java.lang.invoke."))
@@ -845,7 +877,7 @@
             // TODO replace with a more formal and less fragile mechanism
             // that does not bluntly restrict classes under packages within
             // java.base from looking up MethodHandles or VarHandles.
-            if (allowedModes == ALL_MODES && lookupClass.getClassLoader() == null) {
+            if (allowedModes == FULL_POWER_MODES && lookupClass.getClassLoader() == null) {
                 if ((name.startsWith("java.") &&
                      !name.equals("java.lang.Thread") &&
                      !name.startsWith("java.util.concurrent.")) ||
@@ -866,6 +898,7 @@
          * <ul>
          * <li>If no access is allowed, the suffix is "/noaccess".
          * <li>If only public access to types in exported packages is allowed, the suffix is "/public".
+         * <li>If only public access and unconditional access are allowed, the suffix is "/publicLookup".
          * <li>If only public and module access are allowed, the suffix is "/module".
          * <li>If only public, module and package access are allowed, the suffix is "/package".
          * <li>If only public, module, package, and private access are allowed, the suffix is "/private".
@@ -884,6 +917,9 @@
          * because it requires a direct subclass relationship between
          * caller and callee.)
          * @see #in
+         *
+         * @revised 9
+         * @spec JPMS
          */
         @Override
         public String toString() {
@@ -893,13 +929,15 @@
                 return cname + "/noaccess";
             case PUBLIC:
                 return cname + "/public";
+            case PUBLIC|UNCONDITIONAL:
+                return cname  + "/publicLookup";
             case PUBLIC|MODULE:
                 return cname + "/module";
             case PUBLIC|MODULE|PACKAGE:
                 return cname + "/package";
-            case ALL_MODES & ~PROTECTED:
+            case FULL_POWER_MODES & ~PROTECTED:
                 return cname + "/private";
-            case ALL_MODES:
+            case FULL_POWER_MODES:
                 return cname;
             case TRUSTED:
                 return "/trusted";  // internal only; not exported
@@ -1580,6 +1618,7 @@
             if (refKind == REF_invokeSpecial)
                 refKind = REF_invokeVirtual;
             assert(method.isMethod());
+            @SuppressWarnings("deprecation")
             Lookup lookup = m.isAccessible() ? IMPL_LOOKUP : this;
             return lookup.getDirectMethodNoSecurityManager(refKind, method.getDeclaringClass(), method, findBoundCallerClass(method));
         }
@@ -1662,6 +1701,7 @@
         public MethodHandle unreflectConstructor(Constructor<?> c) throws IllegalAccessException {
             MemberName ctor = new MemberName(c);
             assert(ctor.isConstructor());
+            @SuppressWarnings("deprecation")
             Lookup lookup = c.isAccessible() ? IMPL_LOOKUP : this;
             return lookup.getDirectConstructorNoSecurityManager(ctor.getDeclaringClass(), ctor);
         }
@@ -1692,6 +1732,7 @@
             assert(isSetter
                     ? MethodHandleNatives.refKindIsSetter(field.getReferenceKind())
                     : MethodHandleNatives.refKindIsGetter(field.getReferenceKind()));
+            @SuppressWarnings("deprecation")
             Lookup lookup = f.isAccessible() ? IMPL_LOOKUP : this;
             return lookup.getDirectFieldNoSecurityManager(field.getReferenceKind(), f.getDeclaringClass(), field);
         }
@@ -2033,9 +2074,9 @@
                                (defc == refc ||
                                 Modifier.isPublic(refc.getModifiers())));
             if (!classOK && (allowedModes & PACKAGE) != 0) {
-                classOK = (VerifyAccess.isClassAccessible(defc, lookupClass(), ALL_MODES) &&
+                classOK = (VerifyAccess.isClassAccessible(defc, lookupClass(), FULL_POWER_MODES) &&
                            (defc == refc ||
-                            VerifyAccess.isClassAccessible(refc, lookupClass(), ALL_MODES)));
+                            VerifyAccess.isClassAccessible(refc, lookupClass(), FULL_POWER_MODES)));
             }
             if (!classOK)
                 return "class is not public";
@@ -2348,53 +2389,6 @@
     }
 
     /**
-     * Helper class used to lazily create PUBLIC_LOOKUP with a lookup class
-     * in an <em>unnamed module</em>.
-     *
-     * @see Lookup#publicLookup
-     */
-    private static class LookupHelper {
-        private static final String UNNAMED = "Unnamed";
-        private static final String OBJECT  = "java/lang/Object";
-
-        private static Class<?> createClass() {
-            try {
-                ClassWriter cw = new ClassWriter(0);
-                cw.visit(Opcodes.V1_8,
-                         Opcodes.ACC_FINAL + Opcodes.ACC_SUPER,
-                         UNNAMED,
-                         null,
-                         OBJECT,
-                         null);
-                cw.visitSource(UNNAMED, null);
-                cw.visitEnd();
-                byte[] bytes = cw.toByteArray();
-                ClassLoader loader = new ClassLoader(null) {
-                    @Override
-                    protected Class<?> findClass(String cn) throws ClassNotFoundException {
-                        if (cn.equals(UNNAMED))
-                            return super.defineClass(UNNAMED, bytes, 0, bytes.length);
-                        throw new ClassNotFoundException(cn);
-                    }
-                };
-                return loader.loadClass(UNNAMED);
-            } catch (Exception e) {
-                throw new InternalError(e);
-            }
-        }
-
-        private static final Class<?> PUBLIC_LOOKUP_CLASS = createClass();
-
-        /**
-         * Lookup that is trusted minimally. It can only be used to create
-         * method handles to publicly accessible members in exported packages.
-         *
-         * @see MethodHandles#publicLookup
-         */
-        static final Lookup PUBLIC_LOOKUP = new Lookup(PUBLIC_LOOKUP_CLASS, Lookup.PUBLIC);
-    }
-
-    /**
      * Produces a method handle constructing arrays of a desired type.
      * The return type of the method handle will be the array type.
      * The type of its sole argument will be {@code int}, which specifies the size of the array.
--- a/jdk/src/java.base/share/classes/java/lang/module/Configuration.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/module/Configuration.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2014, 2017, 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
@@ -42,126 +42,48 @@
 import java.util.stream.Stream;
 
 /**
- * The configuration that is the result of resolution or resolution with
- * service binding.
- *
- * <h2><a name="resolution">Resolution</a></h2>
- *
- * <p> Resolution is the process of computing the transitive closure of a set
- * of root modules over a set of observable modules by resolving the
- * dependences expressed by {@code requires} clauses.
- *
- * The <em>dependence graph</em> is augmented with edges that take account of
- * implicitly declared dependences ({@code requires transitive}) to create a
- * <em>readability graph</em>. A {@code Configuration} encapsulates the
- * resulting graph of {@link ResolvedModule resolved modules}.
- *
- * <p> Suppose we have the following observable modules: </p>
- * <pre> {@code
- *     module m1 { requires m2; }
- *     module m2 { requires transitive m3; }
- *     module m3 { }
- *     module m4 { }
- * } </pre>
+ * A configuration that is the result of <a href="package-summary.html#resolution">
+ * resolution</a> or resolution with <a href="package-summary.html#servicebinding">
+ * service binding</a>.
  *
- * <p> If the module {@code m1} is resolved then the resulting configuration
- * contains three modules ({@code m1}, {@code m2}, {@code m3}). The edges in
- * its readability graph are: </p>
- * <pre> {@code
- *     m1 --> m2  (meaning m1 reads m2)
- *     m1 --> m3
- *     m2 --> m3
- * } </pre>
- *
- * <p> Resolution is an additive process. When computing the transitive closure
- * then the dependence relation may include dependences on modules in parent
- * configurations. The result is a <em>relative configuration</em> that is
- * relative to one or more parent configurations and where the readability graph
- * may have edges from modules in the configuration to modules in parent
- * configurations.
- *
- * </p>
- *
- * <p> Suppose we have the following observable modules: </p>
- * <pre> {@code
- *     module m1 { requires m2; requires java.xml; }
- *     module m2 { }
- * } </pre>
+ * <p> A configuration encapsulates the <em>readability graph</em> that is the
+ * output of resolution. A readability graph is a directed graph where the nodes
+ * are of type {@link ResolvedModule} and the edges represent the readability
+ * amongst the modules. {@code Configuration} defines the {@link #modules()
+ * modules()} method to get the set of resolved modules in the graph. {@code
+ * ResolvedModule} defines the {@link ResolvedModule#reads() reads()} method to
+ * get the set of modules that a resolved module reads. The modules that are
+ * read may be in the same configuration or may be in {@link #parents() parent}
+ * configurations. </p>
  *
- * <p> If module {@code m1} is resolved with the configuration for the {@link
- * java.lang.reflect.Layer#boot() boot} layer as the parent then the resulting
- * configuration contains two modules ({@code m1}, {@code m2}). The edges in
- * its readability graph are:
- * <pre> {@code
- *     m1 --> m2
- *     m1 --> java.xml
- * } </pre>
- * where module {@code java.xml} is in the parent configuration. For
- * simplicity, this example omits the implicitly declared dependence on the
- * {@code java.base} module.
- *
- * <a name="automaticmoduleresolution"></a>
- * <p> {@link ModuleDescriptor#isAutomatic() Automatic} modules receive special
- * treatment during resolution. Each automatic module is resolved so that it
- * reads all other modules in the configuration and all parent configurations.
- * Each automatic module is also resolved as if it {@code requires transitive}
- * all other automatic modules in the configuration (and all automatic modules
- * in parent configurations). </p>
-
- * <h2><a name="servicebinding">Service binding</a></h2>
+ * <p> Configuration defines the {@link #resolve(ModuleFinder,List,ModuleFinder,Collection)
+ * resolve} method to resolve a collection of root modules, and the {@link
+ * #resolveAndBind(ModuleFinder,List,ModuleFinder,Collection) resolveAndBind}
+ * method to do resolution with service binding. There are instance and
+ * static variants of both methods. The instance methods create a configuration
+ * with the receiver as the parent configuration. The static methods are for
+ * more advanced cases where there can be more than one parent configuration. </p>
  *
- * <p> Service binding is the process of augmenting a graph of resolved modules
- * from the set of observable modules induced by the service-use dependence
- * ({@code uses} and {@code provides} clauses). Any module that was not
- * previously in the graph requires resolution to compute its transitive
- * closure. Service binding is an iterative process in that adding a module
- * that satisfies some service-use dependence may introduce new service-use
- * dependences. </p>
- *
- * <p> Suppose we have the following observable modules: </p>
- * <pre> {@code
- *     module m1 { exports p; uses p.S; }
- *     module m2 { requires m1; provides p.S with p2.S2; }
- *     module m3 { requires m1; requires m4; provides p.S with p3.S3; }
- *     module m4 { }
- * } </pre>
- *
- * <p> If the module {@code m1} is resolved then the resulting graph of modules
- * has one module ({@code m1}). If the graph is augmented with modules induced
- * by the service-use dependence relation then the configuration will contain
- * four modules ({@code m1}, {@code m2}, {@code m3}, {@code m4}). The edges in
- * its readability graph are: </p>
- * <pre> {@code
- *     m2 --> m1
- *     m3 --> m1
- *     m3 --> m4
- * } </pre>
- * <p> The edges in the conceptual service-use graph are: </p>
- * <pre> {@code
- *     m1 --> m2  (meaning m1 uses a service that is provided by m2)
- *     m1 --> m3
- * } </pre>
- *
- * <p> If this configuration is instantiated as a {@code Layer}, and if code in
- * module {@code m1} uses {@link java.util.ServiceLoader ServiceLoader} to
- * iterate over implementations of {@code p.S.class}, then it will iterate over
- * an instance of {@code p2.S2} and {@code p3.S3}. </p>
+ * <p> Each {@link java.lang.reflect.Layer layer} of modules in the Java virtual
+ * machine is created from a configuration. The configuration for the {@link
+ * java.lang.reflect.Layer#boot() boot} layer is obtained by invoking {@code
+ * Layer.boot().configuration()}. The configuration for the boot layer will
+ * often be the parent when creating new configurations. </p>
  *
  * <h3> Example </h3>
  *
- * <p> The following example uses the {@code resolveRequires} method to resolve
- * a module named <em>myapp</em> with the configuration for the boot layer as
- * the parent configuration. It prints the name of each resolved module and
- * the names of the modules that each module reads. </p>
+ * <p> The following example uses the {@link
+ * #resolve(ModuleFinder,ModuleFinder,Collection) resolve} method to resolve a
+ * module named <em>myapp</em> with the configuration for the boot layer as the
+ * parent configuration. It prints the name of each resolved module and the
+ * names of the modules that each module reads. </p>
  *
  * <pre>{@code
  *    ModuleFinder finder = ModuleFinder.of(dir1, dir2, dir3);
  *
  *    Configuration parent = Layer.boot().configuration();
  *
- *    Configuration cf = parent.resolveRequires(finder,
- *                                              ModuleFinder.of(),
- *                                              Set.of("myapp"));
+ *    Configuration cf = parent.resolve(finder, ModuleFinder.of(), Set.of("myapp"));
  *    cf.modules().forEach(m -> {
  *        System.out.format("%s -> %s%n",
  *            m.name(),
@@ -172,6 +94,7 @@
  * }</pre>
  *
  * @since 9
+ * @spec JPMS
  * @see java.lang.reflect.Layer
  */
 public final class Configuration {
@@ -186,11 +109,23 @@
     private final Set<ResolvedModule> modules;
     private final Map<String, ResolvedModule> nameToModule;
 
+    // module constraints on target
+    private final String osName;
+    private final String osArch;
+    private final String osVersion;
+
+    String osName() { return osName; }
+    String osArch() { return osArch; }
+    String osVersion() { return osVersion; }
+
     private Configuration() {
         this.parents = Collections.emptyList();
         this.graph = Collections.emptyMap();
         this.modules = Collections.emptySet();
         this.nameToModule = Collections.emptyMap();
+        this.osName = null;
+        this.osArch = null;
+        this.osVersion = null;
     }
 
     private Configuration(List<Configuration> parents,
@@ -214,27 +149,30 @@
         this.graph = g;
         this.modules = Set.of(moduleArray);
         this.nameToModule = Map.ofEntries(nameEntries);
+
+        this.osName = resolver.osName();
+        this.osArch = resolver.osArch();
+        this.osVersion = resolver.osVersion();
     }
 
-
     /**
      * Resolves a collection of root modules, with this configuration as its
      * parent, to create a new configuration. This method works exactly as
      * specified by the static {@link
-     * #resolveRequires(ModuleFinder,List,ModuleFinder,Collection) resolveRequires}
+     * #resolve(ModuleFinder,List,ModuleFinder,Collection) resolve}
      * method when invoked with this configuration as the parent. In other words,
      * if this configuration is {@code cf} then this method is equivalent to
      * invoking:
      * <pre> {@code
-     *     Configuration.resolveRequires(before, List.of(cf), after, roots);
+     *     Configuration.resolve(before, List.of(cf), after, roots);
      * }</pre>
      *
      * @param  before
      *         The <em>before</em> module finder to find modules
      * @param  after
-     *         The <em>after</em> module finder to locate modules when a
-     *         module cannot be located by the {@code before} module finder
-     *         and the module is not in this configuration
+     *         The <em>after</em> module finder to locate modules when not
+     *         located by the {@code before} module finder or in parent
+     *         configurations
      * @param  roots
      *         The possibly-empty collection of module names of the modules
      *         to resolve
@@ -242,16 +180,20 @@
      * @return The configuration that is the result of resolving the given
      *         root modules
      *
+     * @throws FindException
+     *         If resolution fails for any of the observability-related reasons
+     *         specified by the static {@code resolve} method
      * @throws ResolutionException
-     *         If resolution or the post-resolution checks fail
+     *         If any of the post-resolution consistency checks specified by
+     *         the  static {@code resolve} method fail
      * @throws SecurityException
      *         If locating a module is denied by the security manager
      */
-    public Configuration resolveRequires(ModuleFinder before,
-                                         ModuleFinder after,
-                                         Collection<String> roots)
+    public Configuration resolve(ModuleFinder before,
+                                 ModuleFinder after,
+                                 Collection<String> roots)
     {
-        return resolveRequires(before, List.of(this), after, roots);
+        return resolve(before, List.of(this), after, roots);
     }
 
 
@@ -259,12 +201,12 @@
      * Resolves a collection of root modules, with service binding, and with
      * this configuration as its parent, to create a new configuration.
      * This method works exactly as specified by the static {@link
-     * #resolveRequiresAndUses(ModuleFinder,List,ModuleFinder,Collection)
-     * resolveRequiresAndUses} method when invoked with this configuration
+     * #resolveAndBind(ModuleFinder,List,ModuleFinder,Collection)
+     * resolveAndBind} method when invoked with this configuration
      * as the parent. In other words, if this configuration is {@code cf} then
      * this method is equivalent to invoking:
      * <pre> {@code
-     *     Configuration.resolveRequiresAndUses(before, List.of(cf), after, roots);
+     *     Configuration.resolveAndBind(before, List.of(cf), after, roots);
      * }</pre>
      *
      *
@@ -272,25 +214,29 @@
      *         The <em>before</em> module finder to find modules
      * @param  after
      *         The <em>after</em> module finder to locate modules when not
-     *         located by the {@code before} module finder and this
-     *         configuration
+     *         located by the {@code before} module finder or in parent
+     *         configurations
      * @param  roots
      *         The possibly-empty collection of module names of the modules
      *         to resolve
      *
-     * @return The configuration that is the result of resolving the given
-     *         root modules
+     * @return The configuration that is the result of resolving, with service
+     *         binding, the given root modules
      *
+     * @throws FindException
+     *         If resolution fails for any of the observability-related reasons
+     *         specified by the static {@code resolve} method
      * @throws ResolutionException
-     *         If resolution or the post-resolution checks fail
+     *         If any of the post-resolution consistency checks specified by
+     *         the  static {@code resolve} method fail
      * @throws SecurityException
      *         If locating a module is denied by the security manager
      */
-    public Configuration resolveRequiresAndUses(ModuleFinder before,
-                                                ModuleFinder after,
-                                                Collection<String> roots)
+    public Configuration resolveAndBind(ModuleFinder before,
+                                        ModuleFinder after,
+                                        Collection<String> roots)
     {
-        return resolveRequiresAndUses(before, List.of(this), after, roots);
+        return resolveAndBind(before, List.of(this), after, roots);
     }
 
 
@@ -301,14 +247,14 @@
      *
      * This method is used to create the configuration for the boot layer.
      */
-    static Configuration resolveRequiresAndUses(ModuleFinder finder,
-                                                Collection<String> roots,
-                                                boolean check,
-                                                PrintStream traceOutput)
+    static Configuration resolveAndBind(ModuleFinder finder,
+                                        Collection<String> roots,
+                                        boolean check,
+                                        PrintStream traceOutput)
     {
         List<Configuration> parents = List.of(empty());
         Resolver resolver = new Resolver(finder, parents, ModuleFinder.of(), traceOutput);
-        resolver.resolveRequires(roots).resolveUses();
+        resolver.resolve(roots).bind();
 
         return new Configuration(parents, resolver, check);
     }
@@ -328,11 +274,11 @@
      *
      * <p> When all modules have been resolved then the resulting dependency
      * graph is checked to ensure that it does not contain cycles. A
-     * readability graph is constructed and in conjunction with the module
+     * readability graph is constructed, and in conjunction with the module
      * exports and service use, checked for consistency. </p>
      *
-     * <p> Resolution and the (post-resolution) consistency checks may fail for
-     * following reasons: </p>
+     * <p> Resolution may fail with {@code FindException} for the following
+     * <em>observability-related</em> reasons: </p>
      *
      * <ul>
      *     <li><p> A root module, or a direct or transitive dependency, is not
@@ -343,6 +289,20 @@
      *     descriptor ({@code module-info.class}) or two versions of the same
      *     module are found in the same directory. </p></li>
      *
+     *     <li><p> A module with the required name is found but the module
+     *     requires a different {@link ModuleDescriptor#osName() operating
+     *     system}, {@link ModuleDescriptor#osArch() architecture}, or {@link
+     *     ModuleDescriptor#osVersion() version} to other modules that have
+     *     been resolved for the new configuration or modules in the parent
+     *     configurations. </p></li>
+     *
+     * </ul>
+     *
+     * <p> Post-resolution consistency checks may fail with {@code
+     * ResolutionException} for the following reasons: </p>
+     *
+     * <ul>
+     *
      *     <li><p> A cycle is detected, say where module {@code m1} requires
      *     module {@code m2} and {@code m2} requires {@code m1}. </p></li>
      *
@@ -356,20 +316,11 @@
      *     module {@code M} nor exported to {@code M} by any module that
      *     {@code M} reads. </p></li>
      *
-     *     <li><p> A module {@code M} declares that it
-     *     "{@code provides ... with q.T}" but package {@code q} is not in
-     *     module {@code M}. </p></li>
+     * </ul>
      *
-     *     <li><p> Two or more modules in the configuration are specific to
-     *     different {@link ModuleDescriptor#osName() operating systems},
-     *     {@link ModuleDescriptor#osArch() architectures}, or {@link
-     *     ModuleDescriptor#osVersion() versions}. </p></li>
-     *
-     *     <li><p> Other implementation specific checks, for example referential
-     *     integrity checks to ensure that different versions of tighly coupled
-     *     modules cannot be combined in the same configuration. </p></li>
-     *
-     * </ul>
+     * @implNote In the implementation then observability of modules may depend
+     * on referential integrity checks that ensure different builds of tightly
+     * coupled modules are not combined in the same configuration.
      *
      * @param  before
      *         The <em>before</em> module finder to find modules
@@ -386,17 +337,22 @@
      * @return The configuration that is the result of resolving the given
      *         root modules
      *
+     * @throws FindException
+     *         If resolution fails for an observability-related reason
      * @throws ResolutionException
-     *         If resolution or the post-resolution checks fail
+     *         If a post-resolution consistency checks fails
      * @throws IllegalArgumentException
-     *         If the list of parents is empty
+     *         If the list of parents is empty, or the list has two or more
+     *         parents with modules for different target operating systems,
+     *         architectures, or versions
+     *
      * @throws SecurityException
      *         If locating a module is denied by the security manager
      */
-    public static Configuration resolveRequires(ModuleFinder before,
-                                                List<Configuration> parents,
-                                                ModuleFinder after,
-                                                Collection<String> roots)
+    public static Configuration resolve(ModuleFinder before,
+                                        List<Configuration> parents,
+                                        ModuleFinder after,
+                                        Collection<String> roots)
     {
         Objects.requireNonNull(before);
         Objects.requireNonNull(after);
@@ -407,7 +363,7 @@
             throw new IllegalArgumentException("'parents' is empty");
 
         Resolver resolver = new Resolver(before, parentList, after, null);
-        resolver.resolveRequires(roots);
+        resolver.resolve(roots);
 
         return new Configuration(parentList, resolver, true);
     }
@@ -417,24 +373,24 @@
      * configuration.
      *
      * <p> This method works exactly as specified by {@link
-     * #resolveRequires(ModuleFinder,List,ModuleFinder,Collection)
-     * resolveRequires} except that the graph of resolved modules is augmented
+     * #resolve(ModuleFinder,List,ModuleFinder,Collection)
+     * resolve} except that the graph of resolved modules is augmented
      * with modules induced by the service-use dependence relation. </p>
      *
      * <p> More specifically, the root modules are resolved as if by calling
-     * {@code resolveRequires}. The resolved modules, and all modules in the
+     * {@code resolve}. The resolved modules, and all modules in the
      * parent configurations, with {@link ModuleDescriptor#uses() service
      * dependences} are then examined. All modules found by the given module
      * finders that {@link ModuleDescriptor#provides() provide} an
      * implementation of one or more of the service types are added to the
      * module graph and then resolved as if by calling the {@code
-     * resolveRequires} method. Adding modules to the module graph may
-     * introduce new service-use dependences and so the process works
-     * iteratively until no more modules are added. </p>
+     * resolve} method. Adding modules to the module graph may introduce new
+     * service-use dependences and so the process works iteratively until no
+     * more modules are added. </p>
      *
-     * <p> As service binding involves resolution then it may fail with {@link
-     * ResolutionException} for exactly the same reasons specified in
-     * {@code resolveRequires}.  </p>
+     * <p> As service binding involves resolution then it may fail with {@code
+     * FindException} or {@code ResolutionException} for exactly the same
+     * reasons specified in {@code resolve}. </p>
      *
      * @param  before
      *         The <em>before</em> module finder to find modules
@@ -448,20 +404,26 @@
      *         The possibly-empty collection of module names of the modules
      *         to resolve
      *
-     * @return The configuration that is the result of resolving the given
-     *         root modules
+     * @return The configuration that is the result of resolving, with service
+     *         binding, the given root modules
      *
+     * @throws FindException
+     *         If resolution fails for any of the observability-related reasons
+     *         specified by the static {@code resolve} method
      * @throws ResolutionException
-     *         If resolution or the post-resolution checks fail
+     *         If any of the post-resolution consistency checks specified by
+     *         the  static {@code resolve} method fail
      * @throws IllegalArgumentException
-     *         If the list of parents is empty
+     *         If the list of parents is empty, or the list has two or more
+     *         parents with modules for different target operating systems,
+     *         architectures, or versions
      * @throws SecurityException
      *         If locating a module is denied by the security manager
      */
-    public static Configuration resolveRequiresAndUses(ModuleFinder before,
-                                                       List<Configuration> parents,
-                                                       ModuleFinder after,
-                                                       Collection<String> roots)
+    public static Configuration resolveAndBind(ModuleFinder before,
+                                               List<Configuration> parents,
+                                               ModuleFinder after,
+                                               Collection<String> roots)
     {
         Objects.requireNonNull(before);
         Objects.requireNonNull(after);
@@ -472,7 +434,7 @@
             throw new IllegalArgumentException("'parents' is empty");
 
         Resolver resolver = new Resolver(before, parentList, after, null);
-        resolver.resolveRequires(roots).resolveUses();
+        resolver.resolve(roots).bind();
 
         return new Configuration(parentList, resolver, true);
     }
--- a/jdk/src/java.base/share/classes/java/lang/module/FindException.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/module/FindException.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2017, 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
@@ -26,10 +26,14 @@
 package java.lang.module;
 
 /**
- * Thrown by module finders when finding a module fails.
+ * Thrown by a {@link ModuleFinder ModuleFinder} when an error occurs finding
+ * a module. Also thrown by {@link
+ * Configuration#resolve(ModuleFinder,java.util.List,ModuleFinder,java.util.Collection)
+ * Configuration.resolve} when resolution fails for observability-related
+ * reasons.
  *
- * @see ModuleFinder
  * @since 9
+ * @spec JPMS
  */
 
 public class FindException extends RuntimeException {
--- a/jdk/src/java.base/share/classes/java/lang/module/InvalidModuleDescriptorException.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/module/InvalidModuleDescriptorException.java	Wed Jul 05 22:52:01 2017 +0200
@@ -31,6 +31,7 @@
  *
  * @see ModuleDescriptor#read
  * @since 9
+ * @spec JPMS
  */
 public class InvalidModuleDescriptorException extends RuntimeException {
     private static final long serialVersionUID = 4863390386809347380L;
--- a/jdk/src/java.base/share/classes/java/lang/module/ModuleDescriptor.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/module/ModuleDescriptor.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2009, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2009, 2017, 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
@@ -32,6 +32,7 @@
 import java.nio.ByteBuffer;
 import java.nio.file.Path;
 import java.util.ArrayList;
+import java.util.Arrays;
 import java.util.Collection;
 import java.util.Collections;
 import java.util.EnumSet;
@@ -56,18 +57,37 @@
 /**
  * A module descriptor.
  *
- * <p> A {@code ModuleDescriptor} is typically created from the binary form
- * of a module declaration. Alternatively, the {@link ModuleDescriptor.Builder}
- * class can be used to create a {@code ModuleDescriptor} from its components.
- * The {@link #module module}, {@link #openModule openModule}, and {@link
- * #automaticModule automaticModule} methods create builders for building
- * different kinds of modules. </p>
+ * <p> A module descriptor describes a named module and defines methods to
+ * obtain each of its components. The module descriptor for a named module
+ * in the Java virtual machine is obtained by invoking the {@link
+ * java.lang.reflect.Module Module}'s {@link java.lang.reflect.Module#getDescriptor
+ * getDescriptor} method. Module descriptors can also be created using the
+ * {@link ModuleDescriptor.Builder} class or by reading the binary form of a
+ * module declaration ({@code module-info.class}) using the {@link
+ * #read(InputStream,Supplier) read} methods defined here. </p>
+ *
+ * <p> A module descriptor describes a <em>normal</em>, open, or automatic
+ * module. <em>Normal</em> modules and open modules describe their {@link
+ * #requires() dependences}, {@link #exports() exported-packages}, the services
+ * that they {@link #uses() use} or {@link #provides() provide}, and other
+ * components. <em>Normal</em> modules may {@link #opens() open} specific
+ * packages. The module descriptor for an open modules does not declare any
+ * open packages (its {@code opens} method returns an empty set) but when
+ * instantiated in the Java virtual machine then it is treated as if all
+ * packages are open. The module descriptor for an automatic module does not
+ * declare any dependences (except for the mandatory dependency on {@code
+ * java.base}), and does not declare any exported or open packages. Automatic
+ * module receive special treatment during resolution so that they read all
+ * other modules in the configuration. When an automatic module is instantiated
+ * in the Java virtual machine then it reads every unnamed module and is
+ * treated as if all packages are exported and open. </p>
  *
  * <p> {@code ModuleDescriptor} objects are immutable and safe for use by
  * multiple concurrent threads.</p>
  *
+ * @see java.lang.reflect.Module
  * @since 9
- * @see java.lang.reflect.Module
+ * @spec JPMS
  */
 
 public class ModuleDescriptor
@@ -75,10 +95,45 @@
 {
 
     /**
+     * A modifier on a module.
+     *
+     * @see ModuleDescriptor#modifiers()
+     * @since 9
+     */
+    public static enum Modifier {
+        /**
+         * An open module. An open module does not declare any open packages
+         * but the resulting module is treated as if all packages are open.
+         */
+        OPEN,
+
+        /**
+         * An automatic module. An automatic module is treated as if it exports
+         * and opens all packages.
+         *
+         * @apiNote This modifier does not correspond to a module flag in the
+         * binary form of a module declaration ({@code module-info.class}).
+         */
+        AUTOMATIC,
+
+        /**
+         * The module was not explicitly or implicitly declared.
+         */
+        SYNTHETIC,
+
+        /**
+         * The module was implicitly declared.
+         */
+        MANDATED;
+    }
+
+
+    /**
      * <p> A dependence upon a module </p>
      *
      * @see ModuleDescriptor#requires()
      * @since 9
+     * @spec JPMS
      */
 
     public final static class Requires
@@ -88,7 +143,9 @@
         /**
          * A modifier on a module dependence.
          *
+         * @see Requires#modifiers()
          * @since 9
+         * @spec JPMS
          */
         public static enum Modifier {
 
@@ -171,14 +228,18 @@
          * Compares this module dependence to another.
          *
          * <p> Two {@code Requires} objects are compared by comparing their
-         * module name lexicographically.  Where the module names are equal then
-         * the sets of modifiers are compared based on a value computed from the
-         * ordinal of each modifier. Where the module names are equal and the
-         * set of modifiers are equal then the version of the modules recorded
-         * at compile-time are compared. When comparing the versions recorded
-         * at compile-time then a dependence that has a recorded version is
-         * considered to succeed a dependence that does not have a recorded
-         * version. </p>
+         * module names lexicographically. Where the module names are equal
+         * then the sets of modifiers are compared in the same way that
+         * module modifiers are compared (see {@link ModuleDescriptor#compareTo
+         * ModuleDescriptor.compareTo}). Where the module names are equal and
+         * the set of modifiers are equal then the version of the modules
+         * recorded at compile-time are compared. When comparing the versions
+         * recorded at compile-time then a dependence that has a recorded
+         * version is considered to succeed a dependence that does not have a
+         * recorded version. </p>
+         *
+         * @param  that
+         *         The module dependence to compare
          *
          * @return A negative integer, zero, or a positive integer if this module
          *         dependence is less than, equal to, or greater than the given
@@ -186,39 +247,22 @@
          */
         @Override
         public int compareTo(Requires that) {
+            if (this == that) return 0;
+
             int c = this.name().compareTo(that.name());
-            if (c != 0)
-                return c;
+            if (c != 0) return c;
 
             // modifiers
-            c = Long.compare(this.modsValue(), that.modsValue());
-            if (c != 0)
-                return c;
+            long v1 = modsValue(this.modifiers());
+            long v2 = modsValue(that.modifiers());
+            c = Long.compare(v1, v2);
+            if (c != 0) return c;
 
             // compiledVersion
-            if (this.compiledVersion != null) {
-                if (that.compiledVersion != null)
-                    c = this.compiledVersion.compareTo(that.compiledVersion);
-                else
-                    c = 1;
-            } else {
-                if (that.compiledVersion != null)
-                    c = -1;
-            }
+            c = compare(this.compiledVersion, that.compiledVersion);
+            if (c != 0) return c;
 
-            return c;
-        }
-
-        /**
-         * Return a value for the modifiers to allow sets of modifiers to be
-         * compared.
-         */
-        private long modsValue() {
-            long value = 0;
-            for (Modifier m : mods) {
-                value += 1 << m.ordinal();
-            }
-            return value;
+            return 0;
         }
 
         /**
@@ -266,9 +310,9 @@
         }
 
         /**
-         * Returns a string describing module dependence.
+         * Returns a string describing this module dependence.
          *
-         * @return A string describing module dependence
+         * @return A string describing this module dependence
          */
         @Override
         public String toString() {
@@ -285,18 +329,23 @@
 
 
     /**
-     * <p> A module export, may be qualified or unqualified. </p>
+     * <p> A package exported by a module, may be qualified or unqualified. </p>
      *
      * @see ModuleDescriptor#exports()
      * @since 9
+     * @spec JPMS
      */
 
-    public final static class Exports {
+    public final static class Exports
+        implements Comparable<Exports>
+    {
 
         /**
-         * A modifier on a module export.
+         * A modifier on an exported package.
          *
+         * @see Exports#modifiers()
          * @since 9
+         * @spec JPMS
          */
         public static enum Modifier {
 
@@ -381,6 +430,52 @@
         }
 
         /**
+         * Compares this module export to another.
+         *
+         * <p> Two {@code Exports} objects are compared by comparing the package
+         * names lexicographically. Where the packages names are equal then the
+         * sets of modifiers are compared in the same way that module modifiers
+         * are compared (see {@link ModuleDescriptor#compareTo
+         * ModuleDescriptor.compareTo}). Where the package names are equal and
+         * the set of modifiers are equal then the set of target modules are
+         * compared. This is done by sorting the names of the target modules
+         * in ascending order, and according to their natural ordering, and then
+         * comparing the corresponding elements lexicographically. Where the
+         * sets differ in size, and the larger set contains all elements of the
+         * smaller set, then the larger set is considered to succeed the smaller
+         * set. </p>
+         *
+         * @param  that
+         *         The module export to compare
+         *
+         * @return A negative integer, zero, or a positive integer if this module
+         *         export is less than, equal to, or greater than the given
+         *         export dependence
+         */
+        @Override
+        public int compareTo(Exports that) {
+            if (this == that) return 0;
+
+            int c = source.compareTo(that.source);
+            if (c != 0)
+                return c;
+
+            // modifiers
+            long v1 = modsValue(this.modifiers());
+            long v2 = modsValue(that.modifiers());
+            c = Long.compare(v1, v2);
+            if (c != 0)
+                return c;
+
+            // targets
+            c = compare(targets, that.targets);
+            if (c != 0)
+                return c;
+
+            return 0;
+        }
+
+        /**
          * Computes a hash code for this module export.
          *
          * <p> The hash code is based upon the modifiers, the package name,
@@ -425,9 +520,9 @@
         }
 
         /**
-         * Returns a string describing module export.
+         * Returns a string describing the exported package.
          *
-         * @return A string describing module export
+         * @return A string describing the exported package
          */
         @Override
         public String toString() {
@@ -441,8 +536,7 @@
 
 
     /**
-     * <p> Represents a module <em>opens</em> directive, may be qualified or
-     * unqualified. </p>
+     * <p> A package opened by a module, may be qualified or unqualified. </p>
      *
      * <p> The <em>opens</em> directive in a module declaration declares a
      * package to be open to allow all types in the package, and all their
@@ -452,26 +546,30 @@
      *
      * @see ModuleDescriptor#opens()
      * @since 9
+     * @spec JPMS
      */
 
-    public final static class Opens {
-
+    public final static class Opens
+        implements Comparable<Opens>
+    {
         /**
-         * A modifier on a module <em>opens</em> directive.
+         * A modifier on an open package.
          *
+         * @see Opens#modifiers()
          * @since 9
+         * @spec JPMS
          */
         public static enum Modifier {
 
             /**
-             * The opens was not explicitly or implicitly declared in the
-             * source of the module declaration.
+             * The open package was not explicitly or implicitly declared in
+             * the source of the module declaration.
              */
             SYNTHETIC,
 
             /**
-             * The opens was implicitly declared in the source of the module
-             * declaration.
+             * The open package was implicitly declared in the source of the
+             * module declaration.
              */
             MANDATED;
 
@@ -544,6 +642,52 @@
         }
 
         /**
+         * Compares this module opens to another.
+         *
+         * <p> Two {@code Opens} objects are compared by comparing the package
+         * names lexicographically. Where the packages names are equal then the
+         * sets of modifiers are compared in the same way that module modifiers
+         * are compared (see {@link ModuleDescriptor#compareTo
+         * ModuleDescriptor.compareTo}). Where the package names are equal and
+         * the set of modifiers are equal then the set of target modules are
+         * compared. This is done by sorting the names of the target modules
+         * in ascending order, and according to their natural ordering, and then
+         * comparing the corresponding elements lexicographically. Where the
+         * sets differ in size, and the larger set contains all elements of the
+         * smaller set, then the larger set is considered to succeed the smaller
+         * set. </p>
+         *
+         * @param  that
+         *         The module opens to compare
+         *
+         * @return A negative integer, zero, or a positive integer if this module
+         *         opens is less than, equal to, or greater than the given
+         *         module opens
+         */
+        @Override
+        public int compareTo(Opens that) {
+            if (this == that) return 0;
+
+            int c = source.compareTo(that.source);
+            if (c != 0)
+                return c;
+
+            // modifiers
+            long v1 = modsValue(this.modifiers());
+            long v2 = modsValue(that.modifiers());
+            c = Long.compare(v1, v2);
+            if (c != 0)
+                return c;
+
+            // targets
+            c = compare(targets, that.targets);
+            if (c != 0)
+                return c;
+
+            return 0;
+        }
+
+        /**
          * Computes a hash code for this module opens.
          *
          * <p> The hash code is based upon the modifiers, the package name,
@@ -588,9 +732,9 @@
         }
 
         /**
-         * Returns a string describing module opens.
+         * Returns a string describing the open package.
          *
-         * @return A string describing module opens
+         * @return A string describing the open package
          */
         @Override
         public String toString() {
@@ -608,10 +752,12 @@
      *
      * @see ModuleDescriptor#provides()
      * @since 9
+     * @spec JPMS
      */
 
-    public final static class Provides {
-
+    public final static class Provides
+        implements Comparable<Provides>
+    {
         private final String service;
         private final List<String> providers;
 
@@ -642,6 +788,46 @@
         public List<String> providers() { return providers; }
 
         /**
+         * Compares this provides to another.
+         *
+         * <p> Two {@code Provides} objects are compared by comparing the fully
+         * qualified class name of the service type lexicographically. Where the
+         * class names are equal then the list of the provider class names are
+         * compared by comparing the corresponding elements of both lists
+         * lexicographically and in sequence. Where the lists differ in size,
+         * {@code N} is the size of the shorter list, and the first {@code N}
+         * corresponding elements are equal, then the longer list is considered
+         * to succeed the shorter list. </p>
+         *
+         * @param  that
+         *         The {@code Provides} to compare
+         *
+         * @return A negative integer, zero, or a positive integer if this provides
+         *         is less than, equal to, or greater than the given provides
+         */
+        public int compareTo(Provides that) {
+            if (this == that) return 0;
+
+            int c = service.compareTo(that.service);
+            if (c != 0) return c;
+
+            // compare provider class names in sequence
+            int size1 = this.providers.size();
+            int size2 = that.providers.size();
+            for (int index=0; index<Math.min(size1, size2); index++) {
+                String e1 = this.providers.get(index);
+                String e2 = that.providers.get(index);
+                c = e1.compareTo(e2);
+                if (c != 0) return c;
+            }
+            if (size1 == size2) {
+                return 0;
+            } else {
+                return (size1 > size2) ? 1 : -1;
+            }
+        }
+
+        /**
          * Computes a hash code for this provides.
          *
          * <p> The hash code is based upon the service type and the set of
@@ -699,7 +885,7 @@
      *
      * <p> A version string has three components: The version number itself, an
      * optional pre-release version, and an optional build version.  Each
-     * component is sequence of tokens; each token is either a non-negative
+     * component is a sequence of tokens; each token is either a non-negative
      * integer or a string.  Tokens are separated by the punctuation characters
      * {@code '.'}, {@code '-'}, or {@code '+'}, or by transitions from a
      * sequence of digits to a sequence of characters that are neither digits
@@ -740,6 +926,7 @@
      *
      * @see ModuleDescriptor#version()
      * @since 9
+     * @spec JPMS
      */
 
     public final static class Version
@@ -1009,36 +1196,26 @@
 
     }
 
-
+
     private final String name;
     private final Version version;
-    private final boolean open;
-
-    // Indicates if synthesised for a JAR file found on the module path
-    private final boolean automatic;
-
-    // Not generated from a module-info.java
-    private final boolean synthetic;
-
+    private final Set<Modifier> modifiers;
+    private final boolean open;  // true if modifiers contains OPEN
+    private final boolean automatic;  // true if modifiers contains AUTOMATIC
     private final Set<Requires> requires;
     private final Set<Exports> exports;
     private final Set<Opens> opens;
     private final Set<String> uses;
     private final Set<Provides> provides;
-
-    // Added post-compilation by tools
     private final Set<String> packages;
     private final String mainClass;
     private final String osName;
     private final String osArch;
     private final String osVersion;
 
-
     private ModuleDescriptor(String name,
                              Version version,
-                             boolean open,
-                             boolean automatic,
-                             boolean synthetic,
+                             Set<Modifier> modifiers,
                              Set<Requires> requires,
                              Set<Exports> exports,
                              Set<Opens> opens,
@@ -1052,10 +1229,9 @@
     {
         this.name = name;
         this.version = version;
-        this.open = open;
-        this.automatic = automatic;
-        this.synthetic = synthetic;
-
+        this.modifiers = emptyOrUnmodifiableSet(modifiers);
+        this.open = modifiers.contains(Modifier.OPEN);
+        this.automatic = modifiers.contains(Modifier.AUTOMATIC);
         assert (requires.stream().map(Requires::name).distinct().count()
                 == requires.size());
         this.requires = emptyOrUnmodifiableSet(requires);
@@ -1072,40 +1248,12 @@
     }
 
     /**
-     * Clones the given module descriptor with an augmented set of packages
-     */
-    ModuleDescriptor(ModuleDescriptor md, Set<String> pkgs) {
-        this.name = md.name;
-        this.version = md.version;
-        this.open = md.open;
-        this.automatic = md.automatic;
-        this.synthetic = md.synthetic;
-
-        this.requires = md.requires;
-        this.exports = md.exports;
-        this.opens = md.opens;
-        this.uses = md.uses;
-        this.provides = md.provides;
-
-        Set<String> packages = new HashSet<>(md.packages);
-        packages.addAll(pkgs);
-        this.packages = emptyOrUnmodifiableSet(packages);
-
-        this.mainClass = md.mainClass;
-        this.osName = md.osName;
-        this.osArch = md.osArch;
-        this.osVersion = md.osVersion;
-    }
-
-    /**
      * Creates a module descriptor from its components.
      * The arguments are pre-validated and sets are unmodifiable sets.
      */
     ModuleDescriptor(String name,
                      Version version,
-                     boolean open,
-                     boolean automatic,
-                     boolean synthetic,
+                     Set<Modifier> modifiers,
                      Set<Requires> requires,
                      Set<Exports> exports,
                      Set<Opens> opens,
@@ -1120,9 +1268,9 @@
                      boolean unused) {
         this.name = name;
         this.version = version;
-        this.open = open;
-        this.automatic = automatic;
-        this.synthetic = synthetic;
+        this.modifiers = modifiers;
+        this.open = modifiers.contains(Modifier.OPEN);
+        this.automatic = modifiers.contains(Modifier.AUTOMATIC);
         this.requires = requires;
         this.exports = exports;
         this.opens = opens;
@@ -1137,7 +1285,7 @@
     }
 
     /**
-     * <p> The module name. </p>
+     * <p> Returns the module name. </p>
      *
      * @return The module name
      */
@@ -1146,11 +1294,19 @@
     }
 
     /**
+     * <p> Returns the set of module modifiers. </p>
+     *
+     * @return A possibly-empty unmodifiable set of modifiers
+     */
+    public Set<Modifier> modifiers() {
+        return modifiers;
+    }
+
+    /**
      * <p> Returns {@code true} if this is an open module. </p>
      *
-     * <p> An open module does not declare any open packages (the {@link #opens()
-     * opens} method returns an empty set) but the resulting module is treated
-     * as if all packages are open. </p>
+     * <p> This method is equivalent to testing if the set of {@link #modifiers
+     * modifiers} contains the {@link Modifier#OPEN OPEN} modifier. </p>
      *
      * @return  {@code true} if this is an open module
      */
@@ -1161,12 +1317,8 @@
     /**
      * <p> Returns {@code true} if this is an automatic module. </p>
      *
-     * <p> An automatic module is defined implicitly rather than explicitly
-     * and therefore does not have a module declaration. JAR files located on
-     * the application module path, or by the {@link ModuleFinder} returned by
-     * {@link ModuleFinder#of(java.nio.file.Path[]) ModuleFinder.of}, are
-     * treated as automatic modules if they do have not have a module
-     * declaration. </p>
+     * <p> This method is equivalent to testing if the set of {@link #modifiers
+     * modifiers} contains the {@link Modifier#OPEN AUTOMATIC} modifier. </p>
      *
      * @return  {@code true} if this is an automatic module
      */
@@ -1175,20 +1327,13 @@
     }
 
     /**
-     * <p> Returns {@code true} if this module descriptor was not generated
-     * from an explicit module declaration ({@code module-info.java})
-     * or an implicit module declaration (an {@link #isAutomatic() automatic}
-     * module). </p>
+     * <p> Returns the set of {@code Requires} objects representing the module
+     * dependences. </p>
      *
-     * @return  {@code true} if this module descriptor was not generated by
-     *          an explicit or implicit module declaration
-     */
-    public boolean isSynthetic() {
-        return synthetic;
-    }
-
-    /**
-     * <p> The dependences of this module. </p>
+     * <p> The set includes a dependency on "{@code java.base}" when this
+     * module is not named "{@code java.base}". If this module is an automatic
+     * module then it does not have a dependency on any module other than
+     * "{@code java.base}". </p>
      *
      * @return  A possibly-empty unmodifiable set of {@link Requires} objects
      */
@@ -1197,7 +1342,11 @@
     }
 
     /**
-     * <p> The module exports. </p>
+     * <p> Returns the set of {@code Exports} objects representing the exported
+     * packages. </p>
+     *
+     * <p> If this module is an automatic module then the set of exports
+     * is empty. </p>
      *
      * @return  A possibly-empty unmodifiable set of exported packages
      */
@@ -1206,16 +1355,11 @@
     }
 
     /**
-     * <p> The module <em>opens</em> directives. </p>
+     * <p> Returns the set of {@code Opens} objects representing the open
+     * packages. </p>
      *
-     * <p> Each {@code Opens} object in the set represents a package (and
-     * the set of target module names when qualified) where all types in the
-     * package, and all their members, not just public types and their public
-     * members, can be reflected on when using APIs that bypass or suppress
-     * default Java language access control checks. </p>
-     *
-     * <p> This method returns an empty set when invoked on {@link #isOpen()
-     * open} module. </p>
+     * <p> If this module is an open module or an automatic module then the
+     * set of open packages is empty. </p>
      *
      * @return  A possibly-empty unmodifiable set of open packages
      */
@@ -1224,7 +1368,10 @@
     }
 
     /**
-     * <p> The service dependences of this module. </p>
+     * <p> Returns the set of service dependences. </p>
+     *
+     * <p> If this module is an automatic module then the set of service
+     * dependences is empty. </p>
      *
      * @return  A possibly-empty unmodifiable set of the fully qualified class
      *          names of the service types used
@@ -1234,7 +1381,8 @@
     }
 
     /**
-     * <p> The services that this module provides. </p>
+     * <p> Returns the set of {@code Provides} objects representing the
+     * services that the module provides. </p>
      *
      * @return The possibly-empty unmodifiable set of the services that this
      *         module provides
@@ -1244,7 +1392,7 @@
     }
 
     /**
-     * Returns this module's version.
+     * <p> Returns the module version. </p>
      *
      * @return This module's version
      */
@@ -1253,10 +1401,10 @@
     }
 
     /**
-     * Returns a string containing this module's name and, if present, its
-     * version.
+     * <p> Returns a string containing the module name and, if present, its
+     * version. </p>
      *
-     * @return A string containing this module's name and, if present, its
+     * @return A string containing the module name and, if present, its
      *         version.
      */
     public String toNameAndVersion() {
@@ -1268,51 +1416,51 @@
     }
 
     /**
-     * Returns the module's main class.
+     * <p> Returns the module main class. </p>
      *
-     * @return The fully qualified class name of this module's main class
+     * @return The fully qualified class name of the module's main class
      */
     public Optional<String> mainClass() {
         return Optional.ofNullable(mainClass);
     }
 
     /**
-     * Returns the operating system name if this module is operating system
+     * Returns the operating system name if the module is operating system
      * specific.
      *
      * @return The operating system name or an empty {@code Optional}
-     *         if this module is not operating system specific
+     *         if the module is not operating system specific
      */
     public Optional<String> osName() {
         return Optional.ofNullable(osName);
     }
 
     /**
-     * Returns the operating system architecture if this module is operating
+     * Returns the operating system architecture if the module is operating
      * system architecture specific.
      *
      * @return The operating system architecture or an empty {@code Optional}
-     *         if this module is not operating system architecture specific
+     *         if the module is not operating system architecture specific
      */
     public Optional<String> osArch() {
         return Optional.ofNullable(osArch);
     }
 
     /**
-     * Returns the operating system version if this module is operating
+     * Returns the operating system version if the module is operating
      * system version specific.
      *
      * @return The operating system version or an empty {@code Optional}
-     *         if this module is not operating system version specific
+     *         if the module is not operating system version specific
      */
     public Optional<String> osVersion() {
         return Optional.ofNullable(osVersion);
     }
 
     /**
-     * Returns the names of all packages in this module.
+     * Returns the set of packages in the module.
      *
-     * @return A possibly-empty unmodifiable set of all packages in the module
+     * @return A possibly-empty unmodifiable set of the packages in the module
      */
     public Set<String> packages() {
         return packages;
@@ -1320,37 +1468,53 @@
 
 
     /**
-     * A builder used for building {@link ModuleDescriptor} objects.
+     * A builder for building {@link ModuleDescriptor} objects.
+     *
+     * <p> {@code ModuleDescriptor} defines the {@link #newModule newModule},
+     * {@link #newOpenModule newOpenModule}, and {@link #newAutomaticModule
+     * newAutomaticModule} methods to create builders for building
+     * <em>normal</em>, open, and automatic modules. </p>
      *
-     * <p> {@code ModuleDescriptor} defines the {@link #module module}, {@link
-     * #openModule openModule}, and {@link #automaticModule automaticModule}
-     * methods to create builders for building different kinds of modules. </p>
+     * <p> The set of packages in the module are accumulated by the {@code
+     * Builder} as the {@link ModuleDescriptor.Builder#exports(String) exports},
+     * {@link ModuleDescriptor.Builder#opens(String) opens},
+     * {@link ModuleDescriptor.Builder#packages(Set) packages},
+     * {@link ModuleDescriptor.Builder#provides(String,List) provides}, and
+     * {@link ModuleDescriptor.Builder#mainClass(String) mainClass} methods are
+     * invoked. </p>
+     *
+     * <p> The module names, package names, and class names that are parameters
+     * specified to the builder methods are the module names, package names,
+     * and qualified names of classes (in named packages) as defined in the
+     * <cite>The Java&trade; Language Specification</cite>. </p>
      *
      * <p> Example usage: </p>
-     * <pre>{@code    ModuleDescriptor descriptor = ModuleDescriptor.module("m1")
-     *         .exports("p")
-     *         .requires("m2")
+     * <pre>{@code    ModuleDescriptor descriptor = ModuleDescriptor.newModule("stats.core")
+     *         .requires("java.base")
+     *         .exports("org.acme.stats.core.clustering")
+     *         .exports("org.acme.stats.core.regression")
+     *         .packages(Set.of("org.acme.stats.core.internal"))
      *         .build();
      * }</pre>
      *
      * @apiNote A {@code Builder} checks the components and invariants as
-     * components are added to the builder. The rational for this is to detect
+     * components are added to the builder. The rationale for this is to detect
      * errors as early as possible and not defer all validation to the
-     * {@link #build build} method. A {@code Builder} cannot be used to create
-     * a {@link ModuleDescriptor#isSynthetic() synthetic} module.
+     * {@link #build build} method.
      *
      * @since 9
+     * @spec JPMS
      */
     public static final class Builder {
         final String name;
-        final boolean strict; // true if module names are checked
+        final boolean strict;
+        final Set<Modifier> modifiers;
         final boolean open;
-        final boolean synthetic;
-        boolean automatic;
+        final boolean automatic;
+        final Set<String> packages = new HashSet<>();
         final Map<String, Requires> requires = new HashMap<>();
         final Map<String, Exports> exports = new HashMap<>();
         final Map<String, Opens> opens = new HashMap<>();
-        final Set<String> concealedPackages = new HashSet<>();
         final Set<String> uses = new HashSet<>();
         final Map<String, Provides> provides = new HashMap<>();
         Version version;
@@ -1362,35 +1526,25 @@
         /**
          * Initializes a new builder with the given module name.
          *
-         * @param strict
-         *        Indicates whether module names are checked or not
+         * If {@code strict} is {@code true} then module, package, and class
+         * names are checked to ensure they are legal names. In addition, the
+         * {@link #build buid} method will add "{@code requires java.base}" if
+         * the dependency is not declared.
          */
-        Builder(String name, boolean strict, boolean open, boolean synthetic) {
+        Builder(String name, boolean strict, Set<Modifier> modifiers) {
             this.name = (strict) ? requireModuleName(name) : name;
             this.strict = strict;
-            this.open = open;
-            this.synthetic = synthetic;
-        }
-
-        /* package */ Builder automatic(boolean automatic) {
-            this.automatic = automatic;
-            return this;
+            this.modifiers = modifiers;
+            this.open = modifiers.contains(Modifier.OPEN);
+            this.automatic = modifiers.contains(Modifier.AUTOMATIC);
+            assert !open || !automatic;
         }
 
         /**
-         * Returns the set of packages that are exported (unconditionally or
-         * unconditionally).
+         * Returns a snapshot of the packages in the module.
          */
-        /* package */ Set<String> exportedPackages() {
-            return exports.keySet();
-        }
-
-        /**
-         * Returns the set of packages that are opened (unconditionally or
-         * unconditionally).
-         */
-        /* package */Set<String> openPackages() {
-            return opens.keySet();
+        /* package */ Set<String> packages() {
+            return Collections.unmodifiableSet(packages);
         }
 
         /**
@@ -1406,8 +1560,12 @@
          *         initialized to build
          * @throws IllegalStateException
          *         If the dependence on the module has already been declared
+         *         or this builder is for an automatic module
          */
         public Builder requires(Requires req) {
+            if (automatic)
+                throw new IllegalStateException("Automatic modules cannot declare"
+                                                + " dependences");
             String mn = req.name();
             if (name.equals(mn))
                 throw new IllegalArgumentException("Dependence on self");
@@ -1433,11 +1591,12 @@
          * @return This builder
          *
          * @throws IllegalArgumentException
-         *         If the module name is {@code null}, is not a legal Java
-         *         identifier, or is equal to the module name that this builder
+         *         If the module name is {@code null}, is not a legal module
+         *         name, or is equal to the module name that this builder
          *         was initialized to build
          * @throws IllegalStateException
          *         If the dependence on the module has already been declared
+         *         or this builder is for an automatic module
          */
         public Builder requires(Set<Requires.Modifier> ms,
                                 String mn,
@@ -1448,6 +1607,23 @@
             return requires(new Requires(ms, mn, compiledVersion));
         }
 
+        /* package */Builder requires(Set<Requires.Modifier> ms,
+                                      String mn,
+                                      String compiledVersion) {
+            Version v = null;
+            try {
+                v = Version.parse(compiledVersion);
+            } catch (IllegalArgumentException e) {
+                // for now, drop un-parsable version when non-strict
+                if (strict) throw e;
+            }
+            if (v == null) {
+                return requires(ms, mn);
+            } else {
+                return requires(ms, mn, v);
+            }
+        }
+
         /**
          * Adds a dependence on a module with the given (and possibly empty)
          * set of modifiers.
@@ -1460,11 +1636,12 @@
          * @return This builder
          *
          * @throws IllegalArgumentException
-         *         If the module name is {@code null}, is not a legal Java
-         *         identifier, or is equal to the module name that this builder
+         *         If the module name is {@code null}, is not a legal module
+         *         name, or is equal to the module name that this builder
          *         was initialized to build
          * @throws IllegalStateException
          *         If the dependence on the module has already been declared
+         *         or this builder is for an automatic module
          */
         public Builder requires(Set<Requires.Modifier> ms, String mn) {
             if (strict)
@@ -1481,18 +1658,19 @@
          * @return This builder
          *
          * @throws IllegalArgumentException
-         *         If the module name is {@code null}, is not a legal Java
-         *         identifier, or is equal to the module name that this builder
+         *         If the module name is {@code null}, is not a legal module
+         *         name, or is equal to the module name that this builder
          *         was initialized to build
          * @throws IllegalStateException
          *         If the dependence on the module has already been declared
+         *         or this builder is for an automatic module
          */
         public Builder requires(String mn) {
             return requires(EnumSet.noneOf(Requires.Modifier.class), mn);
         }
 
         /**
-         * Adds an export.
+         * Adds an exported package.
          *
          * @param  e
          *         The export
@@ -1500,29 +1678,27 @@
          * @return This builder
          *
          * @throws IllegalStateException
-         *         If the package is already declared as a package with the
-         *         {@link #contains contains} method or the package is already
-         *         declared as exported
+         *         If the {@link Exports#source package} is already declared as
+         *         exported or this builder is for an automatic module
          */
         public Builder exports(Exports e) {
-            // can't be exported and concealed
+            if (automatic) {
+                throw new IllegalStateException("Automatic modules cannot declare"
+                                                 + " exported packages");
+            }
             String source = e.source();
-            if (concealedPackages.contains(source)) {
-                throw new IllegalStateException("Package " + source
-                                                 + " already declared");
-            }
             if (exports.containsKey(source)) {
                 throw new IllegalStateException("Exported package " + source
                                                  + " already declared");
             }
-
             exports.put(source, e);
+            packages.add(source);
             return this;
         }
 
         /**
-         * Adds an export, with the given (and possibly empty) set of modifiers,
-         * to export a package to a set of target modules.
+         * Adds an exported package with the given (and possibly empty) set of
+         * modifiers. The package is exported to a set of target modules.
          *
          * @param  ms
          *         The set of modifiers
@@ -1534,33 +1710,34 @@
          * @return This builder
          *
          * @throws IllegalArgumentException
-         *         If the package name or any of the target modules is {@code
-         *         null} or is not a legal Java identifier, or the set of
-         *         targets is empty
+         *         If the package name is {@code null} or is not a legal
+         *         package name, the set of target modules is empty, or the set
+         *         of target modules contains a name that is not a legal module
+         *         name
          * @throws IllegalStateException
-         *         If the package is already declared as a package with the
-         *         {@link #contains contains} method or the package is already
-         *         declared as exported
+         *         If the package is already declared as exported
+         *         or this builder is for an automatic module
          */
         public Builder exports(Set<Exports.Modifier> ms,
                                String pn,
                                Set<String> targets)
         {
-            Exports e = new Exports(ms, requirePackageName(pn), targets);
+            Exports e = new Exports(ms, pn, targets);
 
             // check targets
             targets = e.targets();
             if (targets.isEmpty())
                 throw new IllegalArgumentException("Empty target set");
-            if (strict)
+            if (strict) {
+                requirePackageName(e.source());
                 targets.stream().forEach(Checks::requireModuleName);
-
+            }
             return exports(e);
         }
 
         /**
-         * Adds an unqualified export with the given (and possibly empty) set
-         * of modifiers.
+         * Adds an exported package with the given (and possibly empty) set of
+         * modifiers. The package is exported to all modules.
          *
          * @param  ms
          *         The set of modifiers
@@ -1570,20 +1747,23 @@
          * @return This builder
          *
          * @throws IllegalArgumentException
-         *         If the package name is {@code null} or is not a legal Java
-         *         identifier
+         *         If the package name is {@code null} or is not a legal
+         *         package name
          * @throws IllegalStateException
-         *         If the package is already declared as a package with the
-         *         {@link #contains contains} method or the package is already
-         *         declared as exported
+         *         If the package is already declared as exported
+         *         or this builder is for an automatic module
          */
         public Builder exports(Set<Exports.Modifier> ms, String pn) {
-            Exports e = new Exports(ms, requirePackageName(pn), Collections.emptySet());
+            if (strict) {
+                requirePackageName(pn);
+            }
+            Exports e = new Exports(ms, pn, Collections.emptySet());
             return exports(e);
         }
 
         /**
-         * Adds an export to export a package to a set of target modules.
+         * Adds an exported package. The package is exported to a set of target
+         * modules.
          *
          * @param  pn
          *         The package name
@@ -1593,20 +1773,20 @@
          * @return This builder
          *
          * @throws IllegalArgumentException
-         *         If the package name or any of the target modules is {@code
-         *         null} or is not a legal Java identifier, or the set of
-         *         targets is empty
+         *         If the package name is {@code null} or is not a legal
+         *         package name, the set of target modules is empty, or the set
+         *         of target modules contains a name that is not a legal module
+         *         name
          * @throws IllegalStateException
-         *         If the package is already declared as a package with the
-         *         {@link #contains contains} method or the package is already
-         *         declared as exported
+         *         If the package is already declared as exported
+         *         or this builder is for an automatic module
          */
         public Builder exports(String pn, Set<String> targets) {
             return exports(Collections.emptySet(), pn, targets);
         }
 
         /**
-         * Adds an unqualified export.
+         * Adds an exported package. The package is exported to all modules.
          *
          * @param  pn
          *         The package name
@@ -1614,19 +1794,18 @@
          * @return This builder
          *
          * @throws IllegalArgumentException
-         *         If the package name is {@code null} or is not a legal Java
-         *         identifier
+         *         If the package name is {@code null} or is not a legal
+         *         package name
          * @throws IllegalStateException
-         *         If the package is already declared as a package with the
-         *         {@link #contains contains} method or the package is already
-         *         declared as exported
+         *         If the package is already declared as exported
+         *         or this builder is for an automatic module
          */
         public Builder exports(String pn) {
             return exports(Collections.emptySet(), pn);
         }
 
         /**
-         * Adds an <em>opens</em> directive.
+         * Adds an open package.
          *
          * @param  obj
          *         The {@code Opens} object
@@ -1634,35 +1813,28 @@
          * @return This builder
          *
          * @throws IllegalStateException
-         *         If the package is already declared as a package with the
-         *         {@link #contains contains} method, the package is already
-         *         declared as open, or this is a builder for an open module
+         *         If the package is already declared as open, or this is a
+         *         builder for an open module or automatic module
          */
         public Builder opens(Opens obj) {
-            if (open) {
-                throw new IllegalStateException("open modules cannot declare"
-                                                + " open packages");
+            if (open || automatic) {
+                throw new IllegalStateException("Open or automatic modules cannot"
+                                                + " declare open packages");
             }
-
-            // can't be open and concealed
             String source = obj.source();
-            if (concealedPackages.contains(source)) {
-                throw new IllegalStateException("Package " + source
-                                                + " already declared");
-            }
             if (opens.containsKey(source)) {
                 throw new IllegalStateException("Open package " + source
                                                 + " already declared");
             }
-
             opens.put(source, obj);
+            packages.add(source);
             return this;
         }
 
 
         /**
-         * Adds an <em>opens</em> directive, with the given (and possibly empty)
-         * set of modifiers, to open a package to a set of target modules.
+         * Adds an open package with the given (and possibly empty) set of
+         * modifiers. The package is open to a set of target modules.
          *
          * @param  ms
          *         The set of modifiers
@@ -1674,33 +1846,34 @@
          * @return This builder
          *
          * @throws IllegalArgumentException
-         *         If the package name or any of the target modules is {@code
-         *         null} or is not a legal Java identifier, or the set of
-         *         targets is empty
+         *         If the package name is {@code null} or is not a legal
+         *         package name, the set of target modules is empty, or the set
+         *         of target modules contains a name that is not a legal module
+         *         name
          * @throws IllegalStateException
-         *         If the package is already declared as a package with the
-         *         {@link #contains contains} method, the package is already
-         *         declared as open, or this is a builder for an open module
+         *         If the package is already declared as open, or this is a
+         *         builder for an open module or automatic module
          */
         public Builder opens(Set<Opens.Modifier> ms,
                              String pn,
                              Set<String> targets)
         {
-            Opens e = new Opens(ms, requirePackageName(pn), targets);
+            Opens opens = new Opens(ms, pn, targets);
 
             // check targets
-            targets = e.targets();
+            targets = opens.targets();
             if (targets.isEmpty())
                 throw new IllegalArgumentException("Empty target set");
-            if (strict)
+            if (strict) {
+                requirePackageName(opens.source());
                 targets.stream().forEach(Checks::requireModuleName);
-
-            return opens(e);
+            }
+            return opens(opens);
         }
 
         /**
-         * Adds an <em>opens</em> directive to open a package with the given (and
-         * possibly empty) set of modifiers.
+         * Adds an open package with the given (and possibly empty) set of
+         * modifiers. The package is open to all modules.
          *
          * @param  ms
          *         The set of modifiers
@@ -1710,21 +1883,22 @@
          * @return This builder
          *
          * @throws IllegalArgumentException
-         *         If the package name is {@code null} or is not a legal Java
-         *         identifier
+         *         If the package name is {@code null} or is not a legal
+         *         package name
          * @throws IllegalStateException
-         *         If the package is already declared as a package with the
-         *         {@link #contains contains} method, the package is already
-         *         declared as open, or this is a builder for an open module
+         *         If the package is already declared as open, or this is a
+         *         builder for an open module or automatic module
          */
         public Builder opens(Set<Opens.Modifier> ms, String pn) {
-            Opens e = new Opens(ms, requirePackageName(pn), Collections.emptySet());
+            if (strict) {
+                requirePackageName(pn);
+            }
+            Opens e = new Opens(ms, pn, Collections.emptySet());
             return opens(e);
         }
 
         /**
-         * Adds an <em>opens</em> directive to open a package to a set of target
-         * modules.
+         * Adds an open package. The package is open to a set of target modules.
          *
          * @param  pn
          *         The package name
@@ -1734,20 +1908,20 @@
          * @return This builder
          *
          * @throws IllegalArgumentException
-         *         If the package name or any of the target modules is {@code
-         *         null} or is not a legal Java identifier, or the set of
-         *         targets is empty
+         *         If the package name is {@code null} or is not a legal
+         *         package name, the set of target modules is empty, or the set
+         *         of target modules contains a name that is not a legal module
+         *         name
          * @throws IllegalStateException
-         *         If the package is already declared as a package with the
-         *         {@link #contains contains} method, the package is already
-         *         declared as open, or this is a builder for an open module
+         *         If the package is already declared as open, or this is a
+         *         builder for an open module or automatic module
          */
         public Builder opens(String pn, Set<String> targets) {
             return opens(Collections.emptySet(), pn, targets);
         }
 
         /**
-         * Adds an <em>opens</em> directive to open a package.
+         * Adds an open package. The package is open to all modules.
          *
          * @param  pn
          *         The package name
@@ -1755,12 +1929,11 @@
          * @return This builder
          *
          * @throws IllegalArgumentException
-         *         If the package name is {@code null} or is not a legal Java
-         *         identifier
+         *         If the package name is {@code null} or is not a legal
+         *         package name
          * @throws IllegalStateException
-         *         If the package is already declared as a package with the
-         *         {@link #contains contains} method, the package is already
-         *         declared as open, or this is a builder for an open module
+         *         If the package is already declared as open, or this is a
+         *         builder for an open module or automatic module
          */
         public Builder opens(String pn) {
             return opens(Collections.emptySet(), pn);
@@ -1775,12 +1948,16 @@
          * @return This builder
          *
          * @throws IllegalArgumentException
-         *         If the service type is {@code null} or is not a legal Java
-         *         identifier
+         *         If the service type is {@code null} or not a qualified name of
+         *         a class in a named package
          * @throws IllegalStateException
          *         If a dependency on the service type has already been declared
+         *         or this is a builder for an an automatic module
          */
         public Builder uses(String service) {
+            if (automatic)
+                throw new IllegalStateException("Automatic modules can not declare"
+                                                + " service dependences");
             if (uses.contains(requireServiceTypeName(service)))
                 throw new IllegalStateException("Dependence upon service "
                                                 + service + " already declared");
@@ -1789,7 +1966,9 @@
         }
 
         /**
-         * Provides a service with one or more implementations.
+         * Provides a service with one or more implementations. The package for
+         * each {@link Provides#providers provider} (or provider factory) is
+         * added to the module if not already added.
          *
          * @param  p
          *         The provides
@@ -1801,16 +1980,18 @@
          *         declared
          */
         public Builder provides(Provides p) {
-            String st = p.service();
-            if (provides.containsKey(st))
+            String service = p.service();
+            if (provides.containsKey(service))
                 throw new IllegalStateException("Providers of service "
-                                                + st + " already declared");
-            provides.put(st, p);
+                                                + service + " already declared");
+            provides.put(service, p);
+            p.providers().forEach(name -> packages.add(packageName(name)));
             return this;
         }
 
         /**
-         * Provides implementations of a service.
+         * Provides implementations of a service. The package for each provider
+         * (or provider factory) is added to the module if not already added.
          *
          * @param  service
          *         The service type
@@ -1821,103 +2002,59 @@
          *
          * @throws IllegalArgumentException
          *         If the service type or any of the provider class names is
-         *         {@code null} or is not a legal Java identifier, or the list
-         *         of provider class names is empty
+         *         {@code null} or not a qualified name of a class in a named
+         *         package, or the list of provider class names is empty
          * @throws IllegalStateException
          *         If the providers for the service type have already been
          *         declared
          */
         public Builder provides(String service, List<String> providers) {
-            if (provides.containsKey(service))
-                throw new IllegalStateException("Providers of service "
-                                                + service + " already declared by " + name);
-
-            Provides p = new Provides(requireServiceTypeName(service), providers);
+            Provides p = new Provides(service, providers);
 
             // check providers after the set has been copied.
             List<String> providerNames = p.providers();
             if (providerNames.isEmpty())
                 throw new IllegalArgumentException("Empty providers set");
-            providerNames.forEach(Checks::requireServiceProviderName);
-            provides.put(service, p);
-            return this;
+            if (strict) {
+                requireServiceTypeName(p.service());
+                providerNames.forEach(Checks::requireServiceProviderName);
+            } else {
+                // Disallow service/providers in unnamed package
+                String pn = packageName(service);
+                if (pn.isEmpty()) {
+                    throw new IllegalArgumentException(service
+                                                       + ": unnamed package");
+                }
+                for (String name : providerNames) {
+                    pn = packageName(name);
+                    if (pn.isEmpty()) {
+                        throw new IllegalArgumentException(name
+                                                           + ": unnamed package");
+                    }
+                }
+            }
+            return provides(p);
         }
 
         /**
-         * Provides an implementation of a service.
-         *
-         * @param  service
-         *         The service type
-         * @param  provider
-         *         The provider or provider factory class name
-         *
-         * @return This builder
-         *
-         * @throws IllegalArgumentException
-         *         If the service type or the provider class name is {@code
-         *         null} or is not a legal Java identifier
-         * @throws IllegalStateException
-         *         If the providers for the service type have already been
-         *         declared
-         */
-        public Builder provides(String service, String provider) {
-            if (provider == null)
-                throw new IllegalArgumentException("'provider' is null");
-            return provides(service, List.of(provider));
-        }
-
-        /**
-         * Adds a (possible empty) set of packages to the module
+         * Adds packages to the module. All packages in the set of package names
+         * that are not in the module are added to module.
          *
          * @param  pns
-         *         The set of package names
+         *         The (possibly empty) set of package names
          *
          * @return This builder
          *
          * @throws IllegalArgumentException
          *         If any of the package names is {@code null} or is not a
-         *         legal Java identifier
-         * @throws IllegalStateException
-         *         If any of packages are already declared as packages in
-         *         the module. This includes packages that are already
-         *         declared as exported or open packages.
+         *         legal package name
          */
-        public Builder contains(Set<String> pns) {
-            pns.forEach(this::contains);
-            return this;
-        }
-
-        /**
-         * Adds a package to the module.
-         *
-         * @param  pn
-         *         The package name
-         *
-         * @return This builder
-         *
-         * @throws IllegalArgumentException
-         *         If the package name is {@code null}, or is not a legal Java
-         *         identifier
-         * @throws IllegalStateException
-         *         If the package is already declared as a package in the
-         *         module. This includes the package already declared as an
-         *         exported or open package.
-         */
-        public Builder contains(String pn) {
-            Checks.requirePackageName(pn);
-            if (concealedPackages.contains(pn)) {
-                throw new IllegalStateException("Package " + pn
-                                                + " already declared");
+        public Builder packages(Set<String> pns) {
+            if (strict) {
+                pns = new HashSet<>(pns);
+                pns.forEach(Checks::requirePackageName);
             }
-            if (exports.containsKey(pn)) {
-                throw new IllegalStateException("Exported package "
-                                                + pn + " already declared");
-            }
-            if (opens.containsKey(pn)) {
-                throw new IllegalStateException("Open package "
-                                                 + pn + " already declared");
-            }
-            concealedPackages.add(pn);
+            this.packages.addAll(pns);
             return this;
         }
 
@@ -1937,22 +2074,35 @@
         /**
          * Sets the module version.
          *
-         * @param  v
+         * @param  vs
          *         The version string to parse
          *
          * @return This builder
          *
          * @throws IllegalArgumentException
-         *         If {@code v} is null or cannot be parsed as a version string
+         *         If {@code vs} is {@code null} or cannot be parsed as a
+         *         version string
          *
          * @see Version#parse(String)
          */
-        public Builder version(String v) {
-            return version(Version.parse(v));
+        public Builder version(String vs) {
+            Version v;
+            if (strict) {
+                v = Version.parse(vs);
+            } else {
+                try {
+                    v = Version.parse(vs);
+                } catch (IllegalArgumentException ignore) {
+                    // for now, ignore when non-strict
+                    return this;
+                }
+            }
+            return version(v);
         }
 
         /**
-         * Sets the module main class.
+         * Sets the module main class. The package for the main class is added
+         * to the module if not already added.
          *
          * @param  mc
          *         The module main class
@@ -1960,10 +2110,24 @@
          * @return This builder
          *
          * @throws IllegalArgumentException
-         *         If {@code mainClass} is null or is not a legal Java identifier
+         *         If {@code mainClass} is {@code null} or not a qualified
+         *         name of a class in a named package
          */
         public Builder mainClass(String mc) {
-            mainClass = requireBinaryName("main class name", mc);
+            String pn;
+            if (strict) {
+                mc = requireQualifiedClassName("main class name", mc);
+                pn = packageName(mc);
+                assert !pn.isEmpty();
+            } else {
+                // Disallow main class in unnamed package
+                pn = packageName(mc);
+                if (pn.isEmpty()) {
+                    throw new IllegalArgumentException(mc + ": unnamed package");
+                }
+            }
+            mainClass = mc;
+            packages.add(pn);
             return this;
         }
 
@@ -1976,7 +2140,7 @@
          * @return This builder
          *
          * @throws IllegalArgumentException
-         *         If {@code name} is null or the empty String
+         *         If {@code name} is {@code null} or the empty String
          */
         public Builder osName(String name) {
             if (name == null || name.isEmpty())
@@ -1994,7 +2158,7 @@
          * @return This builder
          *
          * @throws IllegalArgumentException
-         *         If {@code name} is null or the empty String
+         *         If {@code name} is {@code null} or the empty String
          */
         public Builder osArch(String arch) {
             if (arch == null || arch.isEmpty())
@@ -2012,7 +2176,7 @@
          * @return This builder
          *
          * @throws IllegalArgumentException
-         *         If {@code name} is null or the empty String
+         *         If {@code name} is {@code null} or the empty String
          */
         public Builder osVersion(String version) {
             if (version == null || version.isEmpty())
@@ -2024,26 +2188,34 @@
         /**
          * Builds and returns a {@code ModuleDescriptor} from its components.
          *
+         * <p> The module will require "{@code java.base}" even if the dependence
+         * has not been declared (the exception is when building a module named
+         * "{@code java.base}" as it cannot require itself). The dependence on
+         * "{@code java.base}" will have the {@link
+         * java.lang.module.ModuleDescriptor.Requires.Modifier#MANDATED MANDATED}
+         * modifier if the dependence was not declared. </p>
+         *
          * @return The module descriptor
          */
         public ModuleDescriptor build() {
             Set<Requires> requires = new HashSet<>(this.requires.values());
-
-            Set<String> packages = new HashSet<>();
-            packages.addAll(exports.keySet());
-            packages.addAll(opens.keySet());
-            packages.addAll(concealedPackages);
-
             Set<Exports> exports = new HashSet<>(this.exports.values());
             Set<Opens> opens = new HashSet<>(this.opens.values());
 
+            // add dependency on java.base
+            if (strict
+                    && !name.equals("java.base")
+                    && !this.requires.containsKey("java.base")) {
+                requires.add(new Requires(Set.of(Requires.Modifier.MANDATED),
+                                          "java.base",
+                                          null));
+            }
+
             Set<Provides> provides = new HashSet<>(this.provides.values());
 
             return new ModuleDescriptor(name,
                                         version,
-                                        open,
-                                        automatic,
-                                        synthetic,
+                                        modifiers,
                                         requires,
                                         exports,
                                         opens,
@@ -2062,16 +2234,20 @@
      * Compares this module descriptor to another.
      *
      * <p> Two {@code ModuleDescriptor} objects are compared by comparing their
-     * module name lexicographically.  Where the module names are equal then
-     * the versions, if present, are compared. </p>
-     *
-     * @apiNote For now, the natural ordering is not consistent with equals.
-     * If two module descriptors have equal module names, equal versions if
-     * present, but their corresponding components are not equal, then they
-     * will be considered equal by this method.
+     * module names lexicographically. Where the module names are equal then the
+     * module versions are compared. When comparing the module versions then a
+     * module descriptor with a version is considered to succeed a module
+     * descriptor that does not have a version. Where the module names are equal
+     * and the versions are equal (or not present in both), then the set of
+     * modifiers are compared. Sets of modifiers are compared by comparing
+     * a <em>binary value</em> computed for each set. If a modifier is present
+     * in the set then the bit at the position of its ordinal is {@code 1}
+     * in the binary value, otherwise {@code 0}. If the two set of modifiers
+     * are also equal then the other components of the module descriptors are
+     * compared in a manner that is consistent with {@code equals}. </p>
      *
      * @param  that
-     *         The object to which this module descriptor is to be compared
+     *         The module descriptor to compare
      *
      * @return A negative integer, zero, or a positive integer if this module
      *         descriptor is less than, equal to, or greater than the given
@@ -2079,16 +2255,50 @@
      */
     @Override
     public int compareTo(ModuleDescriptor that) {
+        if (this == that) return 0;
+
         int c = this.name().compareTo(that.name());
         if (c != 0) return c;
-        if (version == null) {
-            if (that.version == null)
-                return 0;
-            return -1;
-        }
-        if (that.version == null)
-            return +1;
-        return version.compareTo(that.version);
+
+        c = compare(this.version, that.version);
+        if (c != 0) return c;
+
+        long v1 = modsValue(this.modifiers());
+        long v2 = modsValue(that.modifiers());
+        c = Long.compare(v1, v2);
+        if (c != 0) return c;
+
+        c = compare(this.requires, that.requires);
+        if (c != 0) return c;
+
+        c = compare(this.packages, that.packages);
+        if (c != 0) return c;
+
+        c = compare(this.exports, that.exports);
+        if (c != 0) return c;
+
+        c = compare(this.opens, that.opens);
+        if (c != 0) return c;
+
+        c = compare(this.uses, that.uses);
+        if (c != 0) return c;
+
+        c = compare(this.provides, that.provides);
+        if (c != 0) return c;
+
+        c = compare(this.mainClass, that.mainClass);
+        if (c != 0) return c;
+
+        c = compare(this.osName, that.osName);
+        if (c != 0) return c;
+
+        c = compare(this.osArch, that.osArch);
+        if (c != 0) return c;
+
+        c = compare(this.osVersion, that.osVersion);
+        if (c != 0) return c;
+
+        return 0;
     }
 
     /**
@@ -2115,10 +2325,9 @@
             return false;
         ModuleDescriptor that = (ModuleDescriptor)ob;
         return (name.equals(that.name)
-                && open == that.open
-                && automatic == that.automatic
-                && synthetic == that.synthetic
+                && modifiers.equals(that.modifiers)
                 && requires.equals(that.requires)
+                && Objects.equals(packages, that.packages)
                 && exports.equals(that.exports)
                 && opens.equals(that.opens)
                 && uses.equals(that.uses)
@@ -2127,12 +2336,9 @@
                 && Objects.equals(mainClass, that.mainClass)
                 && Objects.equals(osName, that.osName)
                 && Objects.equals(osArch, that.osArch)
-                && Objects.equals(osVersion, that.osVersion)
-                && Objects.equals(packages, that.packages));
+                && Objects.equals(osVersion, that.osVersion));
     }
 
-    private transient int hash;  // cached hash code
-
     /**
      * Computes a hash code for this module descriptor.
      *
@@ -2147,10 +2353,9 @@
         int hc = hash;
         if (hc == 0) {
             hc = name.hashCode();
-            hc = hc * 43 + Boolean.hashCode(open);
-            hc = hc * 43 + Boolean.hashCode(automatic);
-            hc = hc * 43 + Boolean.hashCode(synthetic);
+            hc = hc * 43 + Objects.hashCode(modifiers);
             hc = hc * 43 + requires.hashCode();
+            hc = hc * 43 + Objects.hashCode(packages);
             hc = hc * 43 + exports.hashCode();
             hc = hc * 43 + opens.hashCode();
             hc = hc * 43 + uses.hashCode();
@@ -2160,18 +2365,18 @@
             hc = hc * 43 + Objects.hashCode(osName);
             hc = hc * 43 + Objects.hashCode(osArch);
             hc = hc * 43 + Objects.hashCode(osVersion);
-            hc = hc * 43 + Objects.hashCode(packages);
             if (hc == 0)
                 hc = -1;
             hash = hc;
         }
         return hc;
     }
+    private transient int hash;  // cached hash code
 
     /**
-     * Returns a string describing this descriptor.
+     * <p> Returns a string describing the module. </p>
      *
-     * @return A string describing this descriptor
+     * @return A string describing the module
      */
     @Override
     public String toString() {
@@ -2201,31 +2406,50 @@
      *
      * @param  name
      *         The module name
+     * @param  ms
+     *         The set of module modifiers
      *
      * @return A new builder
      *
      * @throws IllegalArgumentException
-     *         If the module name is {@code null} or is not a legal Java
-     *         identifier
+     *         If the module name is {@code null} or is not a legal module
+     *         name, or the set of modifiers contains {@link
+     *         Modifier#AUTOMATIC AUTOMATIC} with other modifiers
      */
-    public static Builder module(String name) {
-        return new Builder(name, true, false, false);
+    public static Builder newModule(String name, Set<Modifier> ms) {
+        Set<Modifier> mods = new HashSet<>(ms);
+        if (mods.contains(Modifier.AUTOMATIC) && mods.size() > 1)
+            throw new IllegalArgumentException("AUTOMATIC cannot be used with"
+                                               + " other modifiers");
+
+        return new Builder(name, true, mods);
+    }
+
+    /**
+     * Instantiates a builder to build a module descriptor for a <em>normal</em>
+     * module. This method is equivalent to invoking {@link #newModule(String,Set)
+     * newModule} with an empty set of {@link ModuleDescriptor.Modifier modifiers}.
+     *
+     * @param  name
+     *         The module name
+     *
+     * @return A new builder
+     *
+     * @throws IllegalArgumentException
+     *         If the module name is {@code null} or is not a legal module
+     *         name
+     */
+    public static Builder newModule(String name) {
+        return new Builder(name, true, Set.of());
     }
 
     /**
      * Instantiates a builder to build a module descriptor for an open module.
-     * An open module does not declare any open packages but the resulting
-     * module is treated as if all packages are open.
+     * This method is equivalent to invoking {@link #newModule(String,Set)
+     * newModule} with the {@link ModuleDescriptor.Modifier#OPEN OPEN} modifier.
      *
-     * <p> As an example, the following creates a module descriptor for an open
-     * name "{@code m}" containing two packages, one of which is exported. </p>
-     * <pre>{@code
-     *     ModuleDescriptor descriptor = ModuleDescriptor.openModule("m")
-     *         .requires("java.base")
-     *         .exports("p")
-     *         .contains("q")
-     *         .build();
-     * }</pre>
+     * <p> The builder for an open module cannot be used to declare any open
+     * packages. </p>
      *
      * @param  name
      *         The module name
@@ -2233,19 +2457,22 @@
      * @return A new builder that builds an open module
      *
      * @throws IllegalArgumentException
-     *         If the module name is {@code null} or is not a legal Java
-     *         identifier
+     *         If the module name is {@code null} or is not a legal module
+     *         name
      */
-    public static Builder openModule(String name) {
-        return new Builder(name, true, true, false);
+    public static Builder newOpenModule(String name) {
+        return new Builder(name, true, Set.of(Modifier.OPEN));
     }
 
     /**
      * Instantiates a builder to build a module descriptor for an automatic
-     * module. Automatic modules receive special treatment during resolution
-     * (see {@link Configuration}) so that they read all other modules. When
-     * Instantiated in the Java virtual machine as a {@link java.lang.reflect.Module}
-     * then the Module reads every unnamed module in the Java virtual machine.
+     * module. This method is equivalent to invoking {@link #newModule(String,Set)
+     * newModule} with the {@link ModuleDescriptor.Modifier#AUTOMATIC AUTOMATIC}
+     * modifier.
+     *
+     * <p> The builder for an automatic module cannot be used to declare module
+     * or service dependences. It also cannot be used to declare any exported
+     * or open packages. </p>
      *
      * @param  name
      *         The module name
@@ -2253,13 +2480,13 @@
      * @return A new builder that builds an automatic module
      *
      * @throws IllegalArgumentException
-     *         If the module name is {@code null} or is not a legal Java
-     *         identifier
+     *         If the module name is {@code null} or is not a legal module
+     *         name
      *
      * @see ModuleFinder#of(Path[])
      */
-    public static Builder automaticModule(String name) {
-        return new Builder(name, true, false, false).automatic(true);
+    public static Builder newAutomaticModule(String name) {
+        return new Builder(name, true, Set.of(Modifier.AUTOMATIC));
     }
 
 
@@ -2269,8 +2496,12 @@
      *
      * <p> If the descriptor encoded in the input stream does not indicate a
      * set of packages in the module then the {@code packageFinder} will be
-     * invoked. If the {@code packageFinder} throws an {@link UncheckedIOException}
-     * then {@link IOException} cause will be re-thrown. </p>
+     * invoked. The set of packages that the {@code packageFinder} returns
+     * must include all the packages that the module exports, opens, as well
+     * as the packages of the service implementations that the module provides,
+     * and the package of the main class (if the module has a main class). If
+     * the {@code packageFinder} throws an {@link UncheckedIOException} then
+     * {@link IOException} cause will be re-thrown. </p>
      *
      * <p> If there are bytes following the module descriptor then it is
      * implementation specific as to whether those bytes are read, ignored,
@@ -2292,7 +2523,9 @@
      * @return The module descriptor
      *
      * @throws InvalidModuleDescriptorException
-     *         If an invalid module descriptor is detected
+     *         If an invalid module descriptor is detected or the set of
+     *         packages returned by the {@code packageFinder} does not include
+     *         all of the packages obtained from the module descriptor
      * @throws IOException
      *         If an I/O error occurs reading from the input stream or {@code
      *         UncheckedIOException} is thrown by the package finder
@@ -2305,8 +2538,12 @@
     }
 
     /**
-     * Reads the binary form of a module declaration from an input stream
-     * as a module descriptor.
+     * Reads the binary form of a module declaration from an input stream as a
+     * module descriptor. This method works exactly as specified by the 2-arg
+     * {@link #read(InputStream,Supplier) read} method with the exception that
+     * a packager finder is not used to find additional packages when the
+     * module descriptor read from the stream does not indicate the set of
+     * packages.
      *
      * @param  in
      *         The input stream
@@ -2327,7 +2564,13 @@
      * as a module descriptor.
      *
      * <p> If the descriptor encoded in the byte buffer does not indicate a
-     * set of packages then the {@code packageFinder} will be invoked. </p>
+     * set of packages in the module then the {@code packageFinder} will be
+     * invoked. The set of packages that the {@code packageFinder} returns
+     * must include all the packages that the module exports, opens, as well
+     * as the packages of the service implementations that the module provides,
+     * and the package of the main class (if the module has a main class). If
+     * the {@code packageFinder} throws an {@link UncheckedIOException} then
+     * {@link IOException} cause will be re-thrown. </p>
      *
      * <p> The module descriptor is read from the buffer stating at index
      * {@code p}, where {@code p} is the buffer's {@link ByteBuffer#position()
@@ -2353,7 +2596,9 @@
      * @return The module descriptor
      *
      * @throws InvalidModuleDescriptorException
-     *         If an invalid module descriptor is detected
+     *         If an invalid module descriptor is detected or the set of
+     *         packages returned by the {@code packageFinder} does not include
+     *         all of the packages obtained from the module descriptor
      */
     public static ModuleDescriptor read(ByteBuffer bb,
                                         Supplier<Set<String>> packageFinder)
@@ -2362,8 +2607,11 @@
     }
 
     /**
-     * Reads the binary form of a module declaration from a byte buffer
-     * as a module descriptor.
+     * Reads the binary form of a module declaration from a byte buffer as a
+     * module descriptor. This method works exactly as specified by the 2-arg
+     * {@link #read(ByteBuffer,Supplier) read} method with the exception that a
+     * packager finder is not used to find additional packages when the module
+     * descriptor encoded in the buffer does not indicate the set of packages.
      *
      * @param  bb
      *         The byte buffer
@@ -2398,6 +2646,11 @@
         }
     }
 
+    private static String packageName(String cn) {
+        int index = cn.lastIndexOf('.');
+        return (index == -1) ? "" : cn.substring(0, index);
+    }
+
     /**
      * Returns a string containing the given set of modifiers and label.
      */
@@ -2407,6 +2660,36 @@
                 .collect(Collectors.joining(" "));
     }
 
+    private static <T extends Object & Comparable<? super T>>
+    int compare(T obj1, T obj2) {
+        if (obj1 != null) {
+            return (obj2 != null) ? obj1.compareTo(obj2) : 1;
+        } else {
+            return (obj2 == null) ? 0 : -1;
+        }
+    }
+
+    /**
+     * Compares two sets of {@code Comparable} objects.
+     */
+    @SuppressWarnings("unchecked")
+    private static <T extends Object & Comparable<? super T>>
+    int compare(Set<T> s1, Set<T> s2) {
+        T[] a1 = (T[]) s1.toArray();
+        T[] a2 = (T[]) s2.toArray();
+        Arrays.sort(a1);
+        Arrays.sort(a2);
+        return Arrays.compare(a1, a2);
+    }
+
+    private static <E extends Enum<E>> long modsValue(Set<E> set) {
+        long value = 0;
+        for (Enum<E> e : set) {
+            value += 1 << e.ordinal();
+        }
+        return value;
+    }
+
     static {
         /**
          * Setup the shared secret to allow code in other packages access
@@ -2417,19 +2700,21 @@
                 @Override
                 public Builder newModuleBuilder(String mn,
                                                 boolean strict,
-                                                boolean open,
-                                                boolean synthetic) {
-                    return new Builder(mn, strict, open, synthetic);
+                                                Set<ModuleDescriptor.Modifier> modifiers) {
+                    return new Builder(mn, strict, modifiers);
                 }
 
                 @Override
-                public Set<String> exportedPackages(ModuleDescriptor.Builder builder) {
-                    return builder.exportedPackages();
+                public Set<String> packages(ModuleDescriptor.Builder builder) {
+                    return builder.packages();
                 }
 
                 @Override
-                public Set<String> openPackages(ModuleDescriptor.Builder builder) {
-                    return builder.openPackages();
+                public void requires(ModuleDescriptor.Builder builder,
+                                     Set<Requires.Modifier> ms,
+                                     String mn,
+                                     String compiledVersion) {
+                    builder.requires(ms, mn, compiledVersion);
                 }
 
                 @Override
@@ -2467,22 +2752,9 @@
                 }
 
                 @Override
-                public Version newVersion(String v) {
-                    return new Version(v);
-                }
-
-                @Override
-                public ModuleDescriptor newModuleDescriptor(ModuleDescriptor md,
-                                                            Set<String> pkgs) {
-                    return new ModuleDescriptor(md, pkgs);
-                }
-
-                @Override
                 public ModuleDescriptor newModuleDescriptor(String name,
                                                             Version version,
-                                                            boolean open,
-                                                            boolean automatic,
-                                                            boolean synthetic,
+                                                            Set<ModuleDescriptor.Modifier> modifiers,
                                                             Set<Requires> requires,
                                                             Set<Exports> exports,
                                                             Set<Opens> opens,
@@ -2496,9 +2768,7 @@
                                                             int hashCode) {
                     return new ModuleDescriptor(name,
                                                 version,
-                                                open,
-                                                automatic,
-                                                synthetic,
+                                                modifiers,
                                                 requires,
                                                 exports,
                                                 opens,
@@ -2514,12 +2784,12 @@
                 }
 
                 @Override
-                public Configuration resolveRequiresAndUses(ModuleFinder finder,
-                                                            Collection<String> roots,
-                                                            boolean check,
-                                                            PrintStream traceOutput)
+                public Configuration resolveAndBind(ModuleFinder finder,
+                                                    Collection<String> roots,
+                                                    boolean check,
+                                                    PrintStream traceOutput)
                 {
-                    return Configuration.resolveRequiresAndUses(finder, roots, check, traceOutput);
+                    return Configuration.resolveAndBind(finder, roots, check, traceOutput);
                 }
             });
     }
--- a/jdk/src/java.base/share/classes/java/lang/module/ModuleFinder.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/module/ModuleFinder.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2014, 2017, 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
@@ -42,14 +42,15 @@
 import java.util.Optional;
 import java.util.Set;
 
+import jdk.internal.module.ModuleBootstrap;
 import jdk.internal.module.ModulePath;
 import jdk.internal.module.SystemModuleFinder;
 import sun.security.action.GetPropertyAction;
 
 /**
  * A finder of modules. A {@code ModuleFinder} is used to find modules during
- * <a href="Configuration.html#resolution">resolution</a> or
- * <a href="Configuration.html#servicebinding">service binding</a>.
+ * <a href="package-summary.html#resolution">resolution</a> or
+ * <a href="package-summary.html#servicebinding">service binding</a>.
  *
  * <p> A {@code ModuleFinder} can only find one module with a given name. A
  * {@code ModuleFinder} that finds modules in a sequence of directories, for
@@ -85,6 +86,7 @@
  * <p> A {@code ModuleFinder} is not required to be thread safe. </p>
  *
  * @since 9
+ * @spec JPMS
  */
 
 public interface ModuleFinder {
@@ -124,8 +126,8 @@
      * to find that module. </p>
      *
      * @apiNote This is important to have for methods such as {@link
-     * Configuration#resolveRequiresAndUses resolveRequiresAndUses} that need
-     * to scan the module path to find modules that provide a specific service.
+     * Configuration#resolveAndBind resolveAndBind} that need to scan the
+     * module path to find modules that provide a specific service.
      *
      * @return The set of all module references that this finder locates
      *
@@ -172,7 +174,8 @@
         } else {
             Path mlib = Paths.get(home, "modules");
             if (Files.isDirectory(mlib)) {
-                return of(mlib);
+                // exploded build may be patched
+                return ModulePath.of(ModuleBootstrap.patcher(), mlib);
             } else {
                 throw new InternalError("Unable to detect the run-time image");
             }
@@ -198,13 +201,9 @@
      *
      * <p> If an element is a path to a directory of modules then each entry in
      * the directory is a packaged module or the top-level directory of an
-     * exploded module. The module finder's {@link #find(String) find} or
-     * {@link #findAll() findAll} methods throw {@link FindException} if a
-     * directory containing more than one module with the same name is
-     * encountered. </p>
-     *
-     * <p> If an element in the array is a path to a directory, and that
-     * directory contains a file named {@code module-info.class}, then the
+     * exploded module. It it an error if a directory contains more than one
+     * module with the same name. If an element is a path to a directory, and
+     * that directory contains a file named {@code module-info.class}, then the
      * directory is treated as an exploded module rather than a directory of
      * modules. </p>
      *
@@ -214,9 +213,8 @@
      * entry in a {@link java.util.jar.JarFile#isMultiRelease() multi-release}
      * JAR file) is a modular JAR and is an <em>explicit module</em>.
      * A JAR file that does not have a {@code module-info.class} in the
-     * top-level directory is an {@link ModuleDescriptor#isAutomatic automatic}
-     * module. The {@link ModuleDescriptor} for an automatic module is created as
-     * follows:
+     * top-level directory is created as an automatic module. The components
+     * for the automatic module are derived as follows:
      *
      * <ul>
      *
@@ -248,46 +246,48 @@
      *
      *     </ul></li>
      *
-     *     <li><p> It {@link ModuleDescriptor#requires() requires} {@code
-     *     java.base}. </p></li>
-     *
-     *     <li><p> The set of packages in the module is derived from the names
-     *     of non-directory entries in the JAR file. A candidate package name
-     *     is derived from an entry using the characters up to, but not
-     *     including, the last forward slash. All remaining forward slashes are
-     *     replaced with dot ({@code "."}). If the resulting string is a valid
-     *     Java identifier then it is assumed to be a package name. For example,
-     *     if the JAR file contains an entry "{@code p/q/Foo.class}" then the
-     *     package name derived is "{@code p.q}". All packages are {@link
-     *     ModuleDescriptor#exports() exported}. </p></li>
+     *     <li><p> The set of packages in the module is derived from the
+     *     non-directory entries in the JAR file that have names ending in
+     *     "{@code .class}". A candidate package name is derived from the name
+     *     using the characters up to, but not including, the last forward slash.
+     *     All remaining forward slashes are replaced with dot ({@code "."}). If
+     *     the resulting string is a legal package name then it is assumed to be
+     *     a package name. For example, if the JAR file contains the entry
+     *     "{@code p/q/Foo.class}" then the package name derived is
+     *     "{@code p.q}".</p></li>
      *
      *     <li><p> The contents of entries starting with {@code
      *     META-INF/services/} are assumed to be service configuration files
      *     (see {@link java.util.ServiceLoader}). If the name of a file
-     *     (that follows {@code META-INF/services/}) is a legal Java identifier
-     *     then it is assumed to be the fully-qualified binary name of a
-     *     service type. The entries in the file are assumed to be the
-     *     fully-qualified binary names of provider classes. </p></li>
+     *     (that follows {@code META-INF/services/}) is a legal class name
+     *     then it is assumed to be the fully-qualified class name of a service
+     *     type. The entries in the file are assumed to be the fully-qualified
+     *     class names of provider classes. </p></li>
      *
      *     <li><p> If the JAR file has a {@code Main-Class} attribute in its
-     *     main manifest then its value is the {@link
+     *     main manifest then its value is the module {@link
      *     ModuleDescriptor#mainClass() main class}. </p></li>
      *
      * </ul>
      *
      * <p> If a {@code ModuleDescriptor} cannot be created (by means of the
      * {@link ModuleDescriptor.Builder ModuleDescriptor.Builder} API) for an
-     * automatic module then {@code FindException} is thrown. This can arise,
-     * for example, when a legal Java identifier name cannot be derived from
-     * the file name of the JAR file or where the JAR file contains a {@code
-     * .class} in the top-level directory of the JAR file. </p>
+     * automatic module then {@code FindException} is thrown. This can arise
+     * when a legal module name cannot be derived from the file name of the JAR
+     * file, where the JAR file contains a {@code .class} in the top-level
+     * directory of the JAR file, where an entry in a service configuration
+     * file is not a legal class name or its package name is not in the set of
+     * packages derived for the module, or where the module main class is not
+     * a legal class name or its package is not in the module. </p>
      *
      * <p> In addition to JAR files, an implementation may also support modules
-     * that are packaged in other implementation specific module formats. When
-     * a file is encountered that is not recognized as a packaged module then
-     * {@code FindException} is thrown. An implementation may choose to ignore
-     * some files, {@link java.nio.file.Files#isHidden hidden} files for
-     * example. Paths to files that do not exist are always ignored. </p>
+     * that are packaged in other implementation specific module formats. If
+     * an element in the array specified to this method is a path to a directory
+     * of modules then entries in the directory that not recognized as modules
+     * are ignored. If an element in the array is a path to a packaged module
+     * that is not recognized then a {@code FindException} is thrown when the
+     * file is encountered. Paths to files that do not exist are always ignored.
+     * </p>
      *
      * <p> As with automatic modules, the contents of a packaged or exploded
      * module may need to be <em>scanned</em> in order to determine the packages
@@ -325,7 +325,7 @@
             };
         }
 
-        return new ModulePath(entries);
+        return ModulePath.of(entries);
     }
 
     /**
--- a/jdk/src/java.base/share/classes/java/lang/module/ModuleReader.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/module/ModuleReader.java	Wed Jul 05 22:52:01 2017 +0200
@@ -45,7 +45,7 @@
  * module. A module reader is also intended to be used by {@code ClassLoader}
  * implementations that load classes and resources from modules. </p>
  *
- * <p> A resource in a module is identified by a name that is a
+ * <p> A resource in a module is identified by an abstract name that is a
  * '{@code /}'-separated path string. For example, module {@code java.base} may
  * have a resource "{@code java/lang/Object.class}" that, by convention, is the
  * class file for {@code java.lang.Object}. </p>
@@ -61,8 +61,18 @@
  * open}, {@link #read read}, and {@link #list list} methods may throw {@code
  * SecurityException} if access is denied by the security manager. </p>
  *
+ * @implSpec Implementations of {@code ModuleReader} should take great care
+ * when translating an abstract resource name to the location of a resource in
+ * a packaged module or on the file system. Implementations are advised to
+ * treat resource names with elements such as '{@code .},  '{@code ..}',
+ * elements containing file separators, or empty elements as "not found". More
+ * generally, if the resource name is not in the stream of elements that the
+ * {@code list} method returns then the resource should be treated as "not
+ * found" to avoid inconsistencies.
+ *
  * @see ModuleReference
  * @since 9
+ * @spec JPMS
  */
 
 public interface ModuleReader extends Closeable {
@@ -148,6 +158,9 @@
      *         If an I/O error occurs or the module reader is closed
      * @throws SecurityException
      *         If denied by the security manager
+     * @throws OutOfMemoryError
+     *         If the resource is larger than {@code Integer.MAX_VALUE},
+     *         the maximum capacity of a byte buffer
      *
      * @see ClassLoader#defineClass(String, ByteBuffer, java.security.ProtectionDomain)
      */
--- a/jdk/src/java.base/share/classes/java/lang/module/ModuleReference.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/module/ModuleReference.java	Wed Jul 05 22:52:01 2017 +0200
@@ -44,6 +44,7 @@
  * @see ModuleFinder
  * @see ModuleReader
  * @since 9
+ * @spec JPMS
  */
 
 public abstract class ModuleReference {
@@ -76,7 +77,7 @@
     /**
      * Returns the location of this module's content, if known.
      *
-     * <p> This URI, when present, is used as the {@linkplain
+     * <p> This URI, when present, can be used as the {@linkplain
      * java.security.CodeSource#getLocation location} value of a {@link
      * java.security.CodeSource CodeSource} so that a module's classes can be
      * granted specific permissions when loaded by a {@link
--- a/jdk/src/java.base/share/classes/java/lang/module/ResolutionException.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/module/ResolutionException.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2014, 2017, 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
@@ -26,10 +26,12 @@
 package java.lang.module;
 
 /**
- * Thrown when resolving a set of modules or binding fails.
+ * Thrown when resolving a set of modules, or resolving a set of modules with
+ * service binding, fails.
  *
  * @see Configuration
  * @since 9
+ * @spec JPMS
  */
 public class ResolutionException extends RuntimeException {
     private static final long serialVersionUID = -1031186845316729450L;
--- a/jdk/src/java.base/share/classes/java/lang/module/ResolvedModule.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/module/ResolvedModule.java	Wed Jul 05 22:52:01 2017 +0200
@@ -37,6 +37,7 @@
  * module's content.
  *
  * @since 9
+ * @spec JPMS
  * @see Configuration#modules()
  */
 public final class ResolvedModule {
--- a/jdk/src/java.base/share/classes/java/lang/module/Resolver.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/module/Resolver.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013, 2017, 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
@@ -49,8 +49,8 @@
 import jdk.internal.module.ModuleReferenceImpl;
 
 /**
- * The resolver used by {@link Configuration#resolveRequires} and
- * {@link Configuration#resolveRequiresAndUses}.
+ * The resolver used by {@link Configuration#resolve} and {@link
+ * Configuration#resolveAndBind}.
  *
  * @implNote The resolver is used at VM startup and so deliberately avoids
  * using lambda and stream usages in code paths used during startup.
@@ -66,7 +66,19 @@
     // maps module name to module reference
     private final Map<String, ModuleReference> nameToReference = new HashMap<>();
 
+    // module constraints on target platform
+    private String osName;
+    private String osArch;
+    private String osVersion;
 
+    String osName() { return osName; }
+    String osArch() { return osArch; }
+    String osVersion() { return osVersion; }
+
+    /**
+     * @throws IllegalArgumentException if there are more than one parent and
+     *         the constraints on the target platform conflict
+     */
     Resolver(ModuleFinder beforeFinder,
              List<Configuration> parents,
              ModuleFinder afterFinder,
@@ -75,15 +87,54 @@
         this.parents = parents;
         this.afterFinder = afterFinder;
         this.traceOutput = traceOutput;
+
+        // record constraints on target platform, checking that they don't conflict
+        for (Configuration parent : parents) {
+            String value = parent.osName();
+            if (value != null) {
+                if (osName == null) {
+                    osName = value;
+                } else {
+                    if (!value.equals(osName)) {
+                        failParentConflict("Operating System", osName, value);
+                    }
+                }
+            }
+            value = parent.osArch();
+            if (value != null) {
+                if (osArch == null) {
+                    osArch = value;
+                } else {
+                    if (!value.equals(osArch)) {
+                        failParentConflict("OS architecture", osArch, value);
+                    }
+                }
+            }
+            value = parent.osVersion();
+            if (value != null) {
+                if (osVersion == null) {
+                    osVersion  = value;
+                } else {
+                    if (!value.equals(osVersion)) {
+                        failParentConflict("OS version", osVersion, value);
+                    }
+                }
+            }
+        }
     }
 
+    private void failParentConflict(String constraint, String s1, String s2) {
+        String msg = "Parents have conflicting constraints on target "
+                     + constraint + ": " + s1 + ", " + s2;
+        throw new IllegalArgumentException(msg);
+    }
 
     /**
      * Resolves the given named modules.
      *
      * @throws ResolutionException
      */
-    Resolver resolveRequires(Collection<String> roots) {
+    Resolver resolve(Collection<String> roots) {
 
         // create the visit stack to get us started
         Deque<ModuleDescriptor> q = new ArrayDeque<>();
@@ -100,7 +151,7 @@
 
                 mref = findWithAfterFinder(root);
                 if (mref == null) {
-                    fail("Module %s not found", root);
+                    findFail("Module %s not found", root);
                 }
             }
 
@@ -109,8 +160,7 @@
                 mref.location().ifPresent(uri -> trace("  (%s)", uri));
             }
 
-            assert mref.descriptor().name().equals(root);
-            nameToReference.put(root, mref);
+            addFoundModule(mref);
             q.push(mref.descriptor());
         }
 
@@ -152,19 +202,19 @@
 
                     mref = findWithAfterFinder(dn);
                     if (mref == null) {
-                        fail("Module %s not found, required by %s",
-                                dn, descriptor.name());
+                        findFail("Module %s not found, required by %s",
+                                 dn, descriptor.name());
                     }
                 }
 
                 if (!nameToReference.containsKey(dn)) {
-                    nameToReference.put(dn, mref);
+                    addFoundModule(mref);
                     q.offer(mref.descriptor());
                     resolved.add(mref.descriptor());
 
                     if (isTracing()) {
                         trace("Module %s located, required by %s",
-                                dn, descriptor.name());
+                              dn, descriptor.name());
                         mref.location().ifPresent(uri -> trace("  (%s)", uri));
                     }
                 }
@@ -181,7 +231,7 @@
      * Augments the set of resolved modules with modules induced by the
      * service-use relation.
      */
-    Resolver resolveUses() {
+    Resolver bind() {
 
         // Scan the finders for all available service provider modules. As
         // java.base uses services then then module finders will be scanned
@@ -246,7 +296,7 @@
                                             mref.location()
                                                 .ifPresent(uri -> trace("  (%s)", uri));
                                         }
-                                        nameToReference.put(pn, mref);
+                                        addFoundModule(mref);
                                         q.push(provider);
                                     }
                                 }
@@ -264,6 +314,81 @@
 
 
     /**
+     * Add the module to the nameToReference map. Also check any constraints on
+     * the target platform with the constraints of other modules.
+     */
+    private void addFoundModule(ModuleReference mref) {
+        ModuleDescriptor descriptor = mref.descriptor();
+        nameToReference.put(descriptor.name(), mref);
+
+        if (descriptor.osName().isPresent()
+                || descriptor.osArch().isPresent()
+                || descriptor.osVersion().isPresent())
+            checkTargetConstraints(descriptor);
+    }
+
+    /**
+     * Check that the module's constraints on the target platform do not
+     * conflict with the constraints of other modules resolved so far or
+     * modules in parent configurations.
+     */
+    private void checkTargetConstraints(ModuleDescriptor descriptor) {
+        String value = descriptor.osName().orElse(null);
+        if (value != null) {
+            if (osName == null) {
+                osName = value;
+            } else {
+                if (!value.equals(osName)) {
+                    failTargetConstraint(descriptor);
+                }
+            }
+        }
+        value = descriptor.osArch().orElse(null);
+        if (value != null) {
+            if (osArch == null) {
+                osArch = value;
+            } else {
+                if (!value.equals(osArch)) {
+                    failTargetConstraint(descriptor);
+                }
+            }
+        }
+        value = descriptor.osVersion().orElse(null);
+        if (value != null) {
+            if (osVersion == null) {
+                osVersion = value;
+            } else {
+                if (!value.equals(osVersion)) {
+                    failTargetConstraint(descriptor);
+                }
+            }
+        }
+    }
+
+    private void failTargetConstraint(ModuleDescriptor md) {
+        String s1 = targetAsString(osName, osArch, osVersion);
+        String s2 = targetAsString(md);
+        findFail("Module %s has constraints on target platform that conflict" +
+                 " with other modules: %s, %s", md.name(), s1, s2);
+    }
+
+    private String targetAsString(ModuleDescriptor descriptor) {
+        String osName = descriptor.osName().orElse(null);
+        String osArch = descriptor.osArch().orElse(null);
+        String osVersion = descriptor.osVersion().orElse(null);
+        return targetAsString(osName, osArch, osVersion);
+    }
+
+    private String targetAsString(String osName, String osArch, String osVersion) {
+        return new StringJoiner("-")
+                .add(Objects.toString(osName, "*"))
+                .add(Objects.toString(osArch, "*"))
+                .add(Objects.toString(osVersion, "*"))
+                .toString();
+    }
+
+
+    /**
      * Execute post-resolution checks and returns the module graph of resolved
      * modules as {@code Map}. The resolved modules will be in the given
      * configuration.
@@ -281,7 +406,6 @@
 
         if (check) {
             detectCycles();
-            checkPlatformConstraints();
             checkHashes();
         }
 
@@ -319,8 +443,7 @@
         if (!visited.contains(descriptor)) {
             boolean added = visitPath.add(descriptor);
             if (!added) {
-                throw new ResolutionException("Cycle detected: " +
-                        cycleAsString(descriptor));
+                resolveFail("Cycle detected: %s", cycleAsString(descriptor));
             }
             for (ModuleDescriptor.Requires requires : descriptor.requires()) {
                 String dn = requires.name();
@@ -354,86 +477,6 @@
 
 
     /**
-     * If there are platform specific modules then check that the OS name,
-     * architecture and version match.
-     *
-     * @apiNote This method does not currently check if the OS matches
-     *          platform specific modules in parent configurations.
-     */
-    private void checkPlatformConstraints() {
-
-        // first module encountered that is platform specific
-        String savedModuleName = null;
-        String savedOsName = null;
-        String savedOsArch = null;
-        String savedOsVersion = null;
-
-        for (ModuleReference mref : nameToReference.values()) {
-            ModuleDescriptor descriptor = mref.descriptor();
-
-            String osName = descriptor.osName().orElse(null);
-            String osArch = descriptor.osArch().orElse(null);
-            String osVersion = descriptor.osVersion().orElse(null);
-
-            if (osName != null || osArch != null || osVersion != null) {
-
-                if (savedModuleName == null) {
-
-                    savedModuleName = descriptor.name();
-                    savedOsName = osName;
-                    savedOsArch = osArch;
-                    savedOsVersion = osVersion;
-
-                } else {
-
-                    boolean matches = platformMatches(osName, savedOsName)
-                            && platformMatches(osArch, savedOsArch)
-                            && platformMatches(osVersion, savedOsVersion);
-
-                    if (!matches) {
-                        String s1 = platformAsString(savedOsName,
-                                                     savedOsArch,
-                                                     savedOsVersion);
-
-                        String s2 = platformAsString(osName, osArch, osVersion);
-                        fail("Mismatching constraints on target platform: "
-                                + savedModuleName + ": " + s1
-                                + ", " + descriptor.name() + ": " + s2);
-                    }
-
-                }
-
-            }
-        }
-
-    }
-
-    /**
-     * Returns true if the s1 and s2 are equal or one of them is null.
-     */
-    private boolean platformMatches(String s1, String s2) {
-        if (s1 == null || s2 == null)
-            return true;
-        else
-            return Objects.equals(s1, s2);
-    }
-
-    /**
-     * Return a string that encodes the OS name/arch/version.
-     */
-    private String platformAsString(String osName,
-                                    String osArch,
-                                    String osVersion) {
-
-        return new StringJoiner("-")
-                .add(Objects.toString(osName, "*"))
-                .add(Objects.toString(osArch, "*"))
-                .add(Objects.toString(osVersion, "*"))
-                .toString();
-
-    }
-
-    /**
      * Checks the hashes in the module descriptor to ensure that they match
      * any recorded hashes.
      */
@@ -460,7 +503,7 @@
                     continue;
 
                 if (!(mref2 instanceof ModuleReferenceImpl)) {
-                    fail("Unable to compute the hash of module %s", dn);
+                    findFail("Unable to compute the hash of module %s", dn);
                 }
 
                 // skip checking the hash if the module has been patched
@@ -469,11 +512,11 @@
                     byte[] recordedHash = hashes.hashFor(dn);
                     byte[] actualHash = other.computeHash(algorithm);
                     if (actualHash == null)
-                        fail("Unable to compute the hash of module %s", dn);
+                        findFail("Unable to compute the hash of module %s", dn);
                     if (!Arrays.equals(recordedHash, actualHash)) {
-                        fail("Hash of %s (%s) differs to expected hash (%s)" +
-                             " recorded in %s", dn, toHexString(actualHash),
-                             toHexString(recordedHash), descriptor.name());
+                        findFail("Hash of %s (%s) differs to expected hash (%s)" +
+                                 " recorded in %s", dn, toHexString(actualHash),
+                                 toHexString(recordedHash), descriptor.name());
                     }
                 }
             }
@@ -694,37 +737,38 @@
             for (ResolvedModule endpoint : reads) {
                 ModuleDescriptor descriptor2 = endpoint.descriptor();
 
-                for (ModuleDescriptor.Exports export : descriptor2.exports()) {
-
-                    if (export.isQualified()) {
-                        if (!export.targets().contains(descriptor1.name()))
-                            continue;
-                    }
-
-                    // source is exported to descriptor2
-                    String source = export.source();
-                    ModuleDescriptor other
-                        = packageToExporter.putIfAbsent(source, descriptor2);
+                if (descriptor2.isAutomatic()) {
+                    // automatic modules read self and export all packages
+                    if (descriptor2 != descriptor1){
+                        for (String source : descriptor2.packages()) {
+                            ModuleDescriptor supplier
+                                = packageToExporter.putIfAbsent(source, descriptor2);
 
-                    if (other != null && other != descriptor2) {
-                        // package might be local to descriptor1
-                        if (other == descriptor1) {
-                            fail("Module %s contains package %s"
-                                 + ", module %s exports package %s to %s",
-                                    descriptor1.name(),
-                                    source,
-                                    descriptor2.name(),
-                                    source,
-                                    descriptor1.name());
-                        } else {
-                            fail("Modules %s and %s export package %s to module %s",
-                                    descriptor2.name(),
-                                    other.name(),
-                                    source,
-                                    descriptor1.name());
+                            // descriptor2 and 'supplier' export source to descriptor1
+                            if (supplier != null) {
+                                failTwoSuppliers(descriptor1, source, descriptor2, supplier);
+                            }
                         }
 
                     }
+                } else {
+                    for (ModuleDescriptor.Exports export : descriptor2.exports()) {
+                        if (export.isQualified()) {
+                            if (!export.targets().contains(descriptor1.name()))
+                                continue;
+                        }
+
+                        // source is exported by descriptor2
+                        String source = export.source();
+                        ModuleDescriptor supplier
+                            = packageToExporter.putIfAbsent(source, descriptor2);
+
+                        // descriptor2 and 'supplier' export source to descriptor1
+                        if (supplier != null) {
+                            failTwoSuppliers(descriptor1, source, descriptor2, supplier);
+                        }
+                    }
+
                 }
             }
 
@@ -735,8 +779,8 @@
                 for (String service : descriptor1.uses()) {
                     String pn = packageName(service);
                     if (!packageToExporter.containsKey(pn)) {
-                        fail("Module %s does not read a module that exports %s",
-                             descriptor1.name(), pn);
+                        resolveFail("Module %s does not read a module that exports %s",
+                                    descriptor1.name(), pn);
                     }
                 }
 
@@ -744,15 +788,8 @@
                 for (ModuleDescriptor.Provides provides : descriptor1.provides()) {
                     String pn = packageName(provides.service());
                     if (!packageToExporter.containsKey(pn)) {
-                        fail("Module %s does not read a module that exports %s",
-                             descriptor1.name(), pn);
-                    }
-
-                    for (String provider : provides.providers()) {
-                        if (!packages.contains(packageName(provider))) {
-                            fail("Provider %s not in module %s",
-                                 provider, descriptor1.name());
-                        }
+                        resolveFail("Module %s does not read a module that exports %s",
+                                    descriptor1.name(), pn);
                     }
                 }
 
@@ -763,6 +800,42 @@
     }
 
     /**
+     * Fail because a module in the configuration exports the same package to
+     * a module that reads both. This includes the case where a module M
+     * containing a package p reads another module that exports p to at least
+     * module M.
+     */
+    private void failTwoSuppliers(ModuleDescriptor descriptor,
+                                  String source,
+                                  ModuleDescriptor supplier1,
+                                  ModuleDescriptor supplier2) {
+
+        if (supplier2 == descriptor) {
+            ModuleDescriptor tmp = supplier1;
+            supplier1 = supplier2;
+            supplier2 = tmp;
+        }
+
+        if (supplier1 == descriptor) {
+            resolveFail("Module %s contains package %s"
+                         + ", module %s exports package %s to %s",
+                    descriptor.name(),
+                    source,
+                    supplier2.name(),
+                    source,
+                    descriptor.name());
+        } else {
+            resolveFail("Modules %s and %s export package %s to module %s",
+                    supplier1.name(),
+                    supplier2.name(),
+                    source,
+                    descriptor.name());
+        }
+
+    }
+
+
+    /**
      * Find a module of the given name in the parent configurations
      */
     private ResolvedModule findInParent(String mn) {
@@ -779,24 +852,16 @@
      * Invokes the beforeFinder to find method to find the given module.
      */
     private ModuleReference findWithBeforeFinder(String mn) {
-        try {
-            return beforeFinder.find(mn).orElse(null);
-        } catch (FindException e) {
-            // unwrap
-            throw new ResolutionException(e.getMessage(), e.getCause());
-        }
+
+        return beforeFinder.find(mn).orElse(null);
+
     }
 
     /**
      * Invokes the afterFinder to find method to find the given module.
      */
     private ModuleReference findWithAfterFinder(String mn) {
-        try {
-            return afterFinder.find(mn).orElse(null);
-        } catch (FindException e) {
-            // unwrap
-            throw new ResolutionException(e.getMessage(), e.getCause());
-        }
+        return afterFinder.find(mn).orElse(null);
     }
 
     /**
@@ -804,34 +869,27 @@
      * and after ModuleFinders.
      */
     private Set<ModuleReference> findAll() {
-        try {
-
-            Set<ModuleReference> beforeModules = beforeFinder.findAll();
-            Set<ModuleReference> afterModules = afterFinder.findAll();
+        Set<ModuleReference> beforeModules = beforeFinder.findAll();
+        Set<ModuleReference> afterModules = afterFinder.findAll();
 
-            if (afterModules.isEmpty())
-                return beforeModules;
+        if (afterModules.isEmpty())
+            return beforeModules;
 
-            if (beforeModules.isEmpty()
-                    && parents.size() == 1
-                    && parents.get(0) == Configuration.empty())
-                return afterModules;
+        if (beforeModules.isEmpty()
+                && parents.size() == 1
+                && parents.get(0) == Configuration.empty())
+            return afterModules;
 
-            Set<ModuleReference> result = new HashSet<>(beforeModules);
-            for (ModuleReference mref : afterModules) {
-                String name = mref.descriptor().name();
-                if (!beforeFinder.find(name).isPresent()
-                        && findInParent(name) == null) {
-                    result.add(mref);
-                }
+        Set<ModuleReference> result = new HashSet<>(beforeModules);
+        for (ModuleReference mref : afterModules) {
+            String name = mref.descriptor().name();
+            if (!beforeFinder.find(name).isPresent()
+                    && findInParent(name) == null) {
+                result.add(mref);
             }
-
-            return result;
+        }
 
-        } catch (FindException e) {
-            // unwrap
-            throw new ResolutionException(e.getMessage(), e.getCause());
-        }
+        return result;
     }
 
     /**
@@ -843,9 +901,17 @@
     }
 
     /**
+     * Throw FindException with the given format string and arguments
+     */
+    private static void findFail(String fmt, Object ... args) {
+        String msg = String.format(fmt, args);
+        throw new FindException(msg);
+    }
+
+    /**
      * Throw ResolutionException with the given format string and arguments
      */
-    private static void fail(String fmt, Object ... args) {
+    private static void resolveFail(String fmt, Object ... args) {
         String msg = String.format(fmt, args);
         throw new ResolutionException(msg);
     }
--- a/jdk/src/java.base/share/classes/java/lang/module/package-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/module/package-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013, 2017, 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
@@ -27,6 +27,112 @@
  * Classes to support module descriptors and creating configurations of modules
  * by means of resolution and service binding.
  *
+ * <h2><a name="resolution">Resolution</a></h2>
+ *
+ * <p> Resolution is the process of computing the transitive closure of a set
+ * of root modules over a set of observable modules by resolving the
+ * dependences expressed by {@link
+ * java.lang.module.ModuleDescriptor.Requires requires} clauses.
+ * The <em>dependence graph</em> is augmented with edges that take account of
+ * implicitly declared dependences ({@code requires transitive}) to create a
+ * <em>readability graph</em>. The result of resolution is a {@link
+ * java.lang.module.Configuration Configuration} that encapsulates the
+ * readability graph. </p>
+ *
+ * <p> As an example, suppose we have the following observable modules: </p>
+ * <pre> {@code
+ *     module m1 { requires m2; }
+ *     module m2 { requires transitive m3; }
+ *     module m3 { }
+ *     module m4 { }
+ * } </pre>
+ *
+ * <p> If the module {@code m1} is resolved then the resulting configuration
+ * contains three modules ({@code m1}, {@code m2}, {@code m3}). The edges in
+ * its readability graph are: </p>
+ * <pre> {@code
+ *     m1 --> m2  (meaning m1 reads m2)
+ *     m1 --> m3
+ *     m2 --> m3
+ * } </pre>
+ *
+ * <p> Resolution is an additive process. When computing the transitive closure
+ * then the dependence relation may include dependences on modules in {@link
+ * java.lang.module.Configuration#parents() parent} configurations. The result
+ * is a <em>relative configuration</em> that is relative to one or more parent
+ * configurations and where the readability graph may have edges from modules
+ * in the configuration to modules in parent configurations. </p>
+ *
+ * <p> As an example, suppose we have the following observable modules: </p>
+ * <pre> {@code
+ *     module m1 { requires m2; requires java.xml; }
+ *     module m2 { }
+ * } </pre>
+ *
+ * <p> If module {@code m1} is resolved with the configuration for the {@link
+ * java.lang.reflect.Layer#boot() boot} layer as the parent then the resulting
+ * configuration contains two modules ({@code m1}, {@code m2}). The edges in
+ * its readability graph are:
+ * <pre> {@code
+ *     m1 --> m2
+ *     m1 --> java.xml
+ * } </pre>
+ * where module {@code java.xml} is in the parent configuration. For
+ * simplicity, this example omits the implicitly declared dependence on the
+ * {@code java.base} module.
+ *
+ * <p> Requires clauses that are "{@code requires static}" express an optional
+ * dependence (except at compile-time). If a module declares that it
+ * "{@code requires static M}" then resolution does not search the observable
+ * modules for "{@code M}". However, if "{@code M}" is resolved (because resolution
+ * resolves a module that requires "{@code M}" without the {@link
+ * java.lang.module.ModuleDescriptor.Requires.Modifier#STATIC static} modifier)
+ * then the readability graph will contain read edges for each module that
+ * "{@code requires static M}". </p>
+ *
+ * <p> {@link java.lang.module.ModuleDescriptor#isAutomatic() Automatic} modules
+ * receive special treatment during resolution. Each automatic module is resolved
+ * so that it reads all other modules in the configuration and all parent
+ * configurations. Each automatic module is also resolved as if it
+ * "{@code requires transitive}" all other automatic modules in the configuration
+ * (and all automatic modules in parent configurations). </p>
+ *
+ * <h2><a name="servicebinding">Service binding</a></h2>
+ *
+ * <p> Service binding is the process of augmenting a graph of resolved modules
+ * from the set of observable modules induced by the service-use dependence
+ * ({@code uses} and {@code provides} clauses). Any module that was not
+ * previously in the graph requires resolution to compute its transitive
+ * closure. Service binding is an iterative process in that adding a module
+ * that satisfies some service-use dependence may introduce new service-use
+ * dependences. </p>
+ *
+ * <p> Suppose we have the following observable modules: </p>
+ * <pre> {@code
+ *     module m1 { exports p; uses p.S; }
+ *     module m2 { requires m1; provides p.S with p2.S2; }
+ *     module m3 { requires m1; requires m4; provides p.S with p3.S3; }
+ *     module m4 { }
+ * } </pre>
+ *
+ * <p> If the module {@code m1} is resolved then the resulting graph of modules
+ * has one module ({@code m1}). If the graph is augmented with modules induced
+ * by the service-use dependence relation then the configuration will contain
+ * four modules ({@code m1}, {@code m2}, {@code m3}, {@code m4}). The edges in
+ * its readability graph are: </p>
+ * <pre> {@code
+ *     m2 --> m1
+ *     m3 --> m1
+ *     m3 --> m4
+ * } </pre>
+ * <p> The edges in the conceptual service-use graph are: </p>
+ * <pre> {@code
+ *     m1 --> m2  (meaning m1 uses a service that is provided by m2)
+ *     m1 --> m3
+ * } </pre>
+ *
+ * <h2>General Exceptions</h2>
+ *
  * <p> Unless otherwise noted, passing a {@code null} argument to a constructor
  * or method of any class or interface in this package will cause a {@link
  * java.lang.NullPointerException NullPointerException} to be thrown. Additionally,
@@ -34,6 +140,7 @@
  * will cause a {@code NullPointerException}, unless otherwise specified. </p>
  *
  * @since 9
+ * @spec JPMS
  */
 
 package java.lang.module;
--- a/jdk/src/java.base/share/classes/java/lang/reflect/AccessibleObject.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/reflect/AccessibleObject.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 2017, 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
@@ -28,38 +28,44 @@
 import java.lang.annotation.Annotation;
 import java.security.AccessController;
 
-import jdk.internal.misc.VM;
 import jdk.internal.reflect.CallerSensitive;
 import jdk.internal.reflect.Reflection;
 import jdk.internal.reflect.ReflectionFactory;
-import sun.security.action.GetPropertyAction;
 
 /**
- * The AccessibleObject class is the base class for Field, Method and
- * Constructor objects.  It provides the ability to flag a reflected
- * object as suppressing default Java language access control checks
- * when it is used. The access checks -- <em>module boundaries</em>,
- * public, default (package) access, protected, and private members --
- * are performed when Fields, Methods or Constructors are used to set
- * or get fields, to invoke methods or to create and initialize new
- * instances of classes, respectively. Unlike access control specified
- * in the <cite>The Java&trade; Language Specification</cite> and
- * <cite>The Java Virtual Machine Specification</cite>, access checks
- * with reflected objects assume {@link Module#canRead readability}.
+ * The {@code AccessibleObject} class is the base class for {@code Field},
+ * {@code Method}, and {@code Constructor} objects (known as <em>reflected
+ * objects</em>). It provides the ability to flag a reflected object as
+ * suppressing checks for Java language access control when it is used. This
+ * permits sophisticated applications with sufficient privilege, such as Java
+ * Object Serialization or other persistence mechanisms, to manipulate objects
+ * in a manner that would normally be prohibited.
  *
- * <p>Setting the {@code accessible} flag in a reflected object
- * permits sophisticated applications with sufficient privilege, such
- * as Java Object Serialization or other persistence mechanisms, to
- * manipulate objects in a manner that would normally be prohibited.
- *
- * <p>By default, a reflected object is <em>not</em> accessible.
+ * <p> Java language access control prevents use of private members outside
+ * their class; package access members outside their package; protected members
+ * outside their package or subclasses; and public members outside their
+ * module unless they are declared in an {@link Module#isExported(String,Module)
+ * exported} package and the user {@link Module#canRead reads} their module. By
+ * default, Java language access control is enforced (with one variation) when
+ * {@code Field}s, {@code Method}s, or {@code Constructor}s are used to get or
+ * set fields, to invoke methods, or to create and initialize new instances of
+ * classes, respectively. Every reflected object checks that the code using it
+ * is in an appropriate class, package, or module. </p>
  *
- * @see Field
- * @see Method
- * @see Constructor
- * @see ReflectPermission
+ * <p> The one variation from Java language access control is that the checks
+ * by reflected objects assume readability. That is, the module containing
+ * the use of a reflected object is assumed to read the module in which
+ * the underlying field, method, or constructor is declared. </p>
  *
+ * <p> Whether the checks for Java language access control can be suppressed
+ * (and thus, whether access can be enabled) depends on whether the reflected
+ * object corresponds to a member in an exported or open package
+ * (see {@link #setAccessible(boolean)}). </p>
+ *
+ * @jls 6.6 Access Control
  * @since 1.2
+ * @revised 9
+ * @spec JPMS
  */
 public class AccessibleObject implements AnnotatedElement {
 
@@ -78,15 +84,11 @@
 
     /**
      * Convenience method to set the {@code accessible} flag for an
-     * array of objects with a single security check (for efficiency).
+     * array of reflected objects with a single security check (for efficiency).
      *
-     * <p>This method cannot be used to enable access to an object that is a
-     * {@link Member member} of a class in a different module to the caller and
-     * where the class is in a package that is not exported to the caller's
-     * module. Additionally, if the member is non-public or its declaring
-     * class is non-public, then this method can only be used to enable access
-     * if the package is {@link Module#isOpen(String,Module) open} to at least
-     * the caller's module.
+     * <p> This method may be used to enable access to all reflected objects in
+     * the array when access to each reflected object can be enabled as
+     * specified by {@link #setAccessible(boolean) setAccessible(boolean)}. </p>
      *
      * <p>If there is a security manager, its
      * {@code checkPermission} method is first called with a
@@ -99,10 +101,15 @@
      * @param array the array of AccessibleObjects
      * @param flag  the new value for the {@code accessible} flag
      *              in each object
-     * @throws InaccessibleObjectException if access cannot be enabled
-     * @throws SecurityException if the request is denied.
+     * @throws InaccessibleObjectException if access cannot be enabled for all
+     *         objects in the array
+     * @throws SecurityException if the request is denied by the security manager
+     *         or an element in the array is a constructor for {@code
+     *         java.lang.Class}
      * @see SecurityManager#checkPermission
      * @see ReflectPermission
+     * @revised 9
+     * @spec JPMS
      */
     @CallerSensitive
     public static void setAccessible(AccessibleObject[] array, boolean flag) {
@@ -120,41 +127,143 @@
     }
 
     /**
-     * Set the {@code accessible} flag for this object to
+     * Set the {@code accessible} flag for this reflected object to
      * the indicated boolean value.  A value of {@code true} indicates that
-     * the reflected object should suppress Java language access
-     * checking when it is used.  A value of {@code false} indicates
-     * that the reflected object should enforce Java language access checks
-     * while assuming readability (as noted in the class description).
+     * the reflected object should suppress checks for Java language access
+     * control when it is used. A value of {@code false} indicates that
+     * the reflected object should enforce checks for Java language access
+     * control when it is used, with the variation noted in the class description.
+     *
+     * <p> This method may be used by a caller in class {@code C} to enable
+     * access to a {@link Member member} of {@link Member#getDeclaringClass()
+     * declaring class} {@code D} if any of the following hold: </p>
+     *
+     * <ul>
+     *     <li> {@code C} and {@code D} are in the same module. </li>
+     *
+     *     <li> The member is {@code public} and {@code D} is {@code public} in
+     *     a package that the module containing {@code D} {@link
+     *     Module#isExported(String,Module) exports} to at least the module
+     *     containing {@code C}. </li>
      *
-     * <p>This method cannot be used to enable access to an object that is a
-     * {@link Member member} of a class in a different module to the caller and
-     * where the class is in a package that is not exported to the caller's
-     * module. Additionally, if the member is non-public or its declaring
-     * class is non-public, then this method can only be used to enable access
-     * if the package is {@link Module#isOpen(String,Module) open} to at least
-     * the caller's module.
+     *     <li> The member is {@code protected} {@code static}, {@code D} is
+     *     {@code public} in a package that the module containing {@code D}
+     *     exports to at least the module containing {@code C}, and {@code C}
+     *     is a subclass of {@code D}. </li>
      *
-     * <p>If there is a security manager, its
+     *     <li> {@code D} is in a package that the module containing {@code D}
+     *     {@link Module#isOpen(String,Module) opens} to at least the module
+     *     containing {@code C}.
+     *     All packages in unnamed and open modules are open to all modules and
+     *     so this method always succeeds when {@code D} is in an unnamed or
+     *     open module. </li>
+     * </ul>
+     *
+     * <p> This method cannot be used to enable access to private members,
+     * members with default (package) access, protected instance members, or
+     * protected constructors when the declaring class is in a different module
+     * to the caller and the package containing the declaring class is not open
+     * to the caller's module. </p>
+     *
+     * <p> If there is a security manager, its
      * {@code checkPermission} method is first called with a
      * {@code ReflectPermission("suppressAccessChecks")} permission.
      *
      * @param flag the new value for the {@code accessible} flag
      * @throws InaccessibleObjectException if access cannot be enabled
-     * @throws SecurityException if the request is denied
-     * @see SecurityManager#checkPermission
-     * @see ReflectPermission
+     * @throws SecurityException if the request is denied by the security manager
+     * @see #trySetAccessible
      * @see java.lang.invoke.MethodHandles#privateLookupIn
+     * @revised 9
+     * @spec JPMS
      */
     public void setAccessible(boolean flag) {
         AccessibleObject.checkPermission();
         setAccessible0(flag);
     }
 
-    void setAccessible0(boolean flag) {
+    /**
+     * Sets the accessible flag and returns the new value
+     */
+    boolean setAccessible0(boolean flag) {
         this.override = flag;
+        return flag;
     }
 
+    /**
+     * Set the {@code accessible} flag for this reflected object to {@code true}
+     * if possible. This method sets the {@code accessible} flag, as if by
+     * invoking {@link #setAccessible(boolean) setAccessible(true)}, and returns
+     * the possibly-updated value for the {@code accessible} flag. If access
+     * cannot be enabled, i.e. the checks or Java language access control cannot
+     * be suppressed, this method returns {@code false} (as opposed to {@code
+     * setAccessible(true)} throwing {@code InaccessibleObjectException} when
+     * it fails).
+     *
+     * <p> This method is a no-op if the {@code accessible} flag for
+     * this reflected object is {@code true}.
+     *
+     * <p> For example, a caller can invoke {@code trySetAccessible}
+     * on a {@code Method} object for a private instance method
+     * {@code p.T::privateMethod} to suppress the checks for Java language access
+     * control when the {@code Method} is invoked.
+     * If {@code p.T} class is in a different module to the caller and
+     * package {@code p} is open to at least the caller's module,
+     * the code below successfully sets the {@code accessible} flag
+     * to {@code true}.
+     *
+     * <pre>
+     * {@code
+     *     p.T obj = ....;  // instance of p.T
+     *     :
+     *     Method m = p.T.class.getDeclaredMethod("privateMethod");
+     *     if (m.trySetAccessible()) {
+     *         m.invoke(obj);
+     *     } else {
+     *         // package p is not opened to the caller to access private member of T
+     *         ...
+     *     }
+     * }</pre>
+     *
+     * <p> If there is a security manager, its {@code checkPermission} method
+     * is first called with a {@code ReflectPermission("suppressAccessChecks")}
+     * permission. </p>
+     *
+     * @return {@code true} if the {@code accessible} flag is set to {@code true};
+     *         {@code false} if access cannot be enabled.
+     * @throws SecurityException if the request is denied by the security manager
+     *
+     * @since 9
+     * @spec JPMS
+     * @see java.lang.invoke.MethodHandles#privateLookupIn
+     */
+    @CallerSensitive
+    public final boolean trySetAccessible() {
+        AccessibleObject.checkPermission();
+
+        if (override == true) return true;
+
+        // if it's not a Constructor, Method, Field then no access check
+        if (!Member.class.isInstance(this)) {
+            return setAccessible0(true);
+        }
+
+        // does not allow to suppress access check for Class's constructor
+        Class<?> declaringClass = ((Member) this).getDeclaringClass();
+        if (declaringClass == Class.class && this instanceof Constructor) {
+            return false;
+        }
+
+        if (checkCanSetAccessible(Reflection.getCallerClass(),
+                                  declaringClass,
+                                  false)) {
+            return setAccessible0(true);
+        } else {
+            return false;
+        }
+    }
+
+
    /**
     * If the given AccessibleObject is a {@code Constructor}, {@code Method}
     * or {@code Field} then checks that its declaring class is in a package
@@ -164,22 +273,29 @@
         // do nothing, needs to be overridden by Constructor, Method, Field
     }
 
+
     void checkCanSetAccessible(Class<?> caller, Class<?> declaringClass) {
+        checkCanSetAccessible(caller, declaringClass, true);
+    }
+
+    private boolean checkCanSetAccessible(Class<?> caller,
+                                          Class<?> declaringClass,
+                                          boolean throwExceptionIfDenied) {
         Module callerModule = caller.getModule();
         Module declaringModule = declaringClass.getModule();
 
-        if (callerModule == declaringModule) return;
-        if (callerModule == Object.class.getModule()) return;
-        if (!declaringModule.isNamed()) return;
+        if (callerModule == declaringModule) return true;
+        if (callerModule == Object.class.getModule()) return true;
+        if (!declaringModule.isNamed()) return true;
 
         // package is open to caller
         String pn = packageName(declaringClass);
         if (declaringModule.isOpen(pn, callerModule)) {
-            printStackTraceIfOpenedReflectively(declaringModule, pn, callerModule);
-            return;
+            dumpStackIfOpenedReflectively(declaringModule, pn, callerModule);
+            return true;
         }
 
-        // package is exported to caller and class/member is public
+        // package is exported to caller
         boolean isExported = declaringModule.isExported(pn, callerModule);
         boolean isClassPublic = Modifier.isPublic(declaringClass.getModifiers());
         int modifiers;
@@ -188,48 +304,72 @@
         } else {
             modifiers = ((Field) this).getModifiers();
         }
-        boolean isMemberPublic = Modifier.isPublic(modifiers);
-        if (isExported && isClassPublic && isMemberPublic) {
-            printStackTraceIfExportedReflectively(declaringModule, pn, callerModule);
-            return;
+        if (isExported && isClassPublic) {
+
+            // member is public
+            if (Modifier.isPublic(modifiers)) {
+                dumpStackIfExportedReflectively(declaringModule, pn, callerModule);
+                return true;
+            }
+
+            // member is protected-static
+            if (Modifier.isProtected(modifiers)
+                && Modifier.isStatic(modifiers)
+                && isSubclassOf(caller, declaringClass)) {
+                dumpStackIfExportedReflectively(declaringModule, pn, callerModule);
+                return true;
+            }
         }
 
-        // not accessible
-        String msg = "Unable to make ";
-        if (this instanceof Field)
-            msg += "field ";
-        msg += this + " accessible: " + declaringModule + " does not \"";
-        if (isClassPublic && isMemberPublic)
-            msg += "exports";
-        else
-            msg += "opens";
-        msg += " " + pn + "\" to " + callerModule;
-        InaccessibleObjectException e = new InaccessibleObjectException(msg);
-        if (Reflection.printStackTraceWhenAccessFails()) {
-            e.printStackTrace(System.err);
+        if (throwExceptionIfDenied) {
+            // not accessible
+            String msg = "Unable to make ";
+            if (this instanceof Field)
+                msg += "field ";
+            msg += this + " accessible: " + declaringModule + " does not \"";
+            if (isClassPublic && Modifier.isPublic(modifiers))
+                msg += "exports";
+            else
+                msg += "opens";
+            msg += " " + pn + "\" to " + callerModule;
+            InaccessibleObjectException e = new InaccessibleObjectException(msg);
+            if (Reflection.printStackTraceWhenAccessFails()) {
+                e.printStackTrace(System.err);
+            }
+            throw e;
         }
-        throw e;
+        return false;
     }
 
-    private void printStackTraceIfOpenedReflectively(Module module,
-                                                     String pn,
-                                                     Module other) {
-        printStackTraceIfExposedReflectively(module, pn, other, true);
+    private boolean isSubclassOf(Class<?> queryClass, Class<?> ofClass) {
+        while (queryClass != null) {
+            if (queryClass == ofClass) {
+                return true;
+            }
+            queryClass = queryClass.getSuperclass();
+        }
+        return false;
     }
 
-    private void printStackTraceIfExportedReflectively(Module module,
-                                                       String pn,
-                                                       Module other) {
-        printStackTraceIfExposedReflectively(module, pn, other, false);
+    private void dumpStackIfOpenedReflectively(Module module,
+                                               String pn,
+                                               Module other) {
+        dumpStackIfExposedReflectively(module, pn, other, true);
     }
 
-    private void printStackTraceIfExposedReflectively(Module module,
-                                                      String pn,
-                                                      Module other,
-                                                      boolean open)
+    private void dumpStackIfExportedReflectively(Module module,
+                                                 String pn,
+                                                 Module other) {
+        dumpStackIfExposedReflectively(module, pn, other, false);
+    }
+
+    private void dumpStackIfExposedReflectively(Module module,
+                                                String pn,
+                                                Module other,
+                                                boolean open)
     {
         if (Reflection.printStackTraceWhenAccessSucceeds()
-            && !module.isStaticallyExportedOrOpen(pn, other, open))
+                && !module.isStaticallyExportedOrOpen(pn, other, open))
         {
             String msg = other + " allowed to invoke setAccessible on ";
             if (this instanceof Field)
@@ -256,15 +396,100 @@
     }
 
     /**
-     * Get the value of the {@code accessible} flag for this object.
+     * Get the value of the {@code accessible} flag for this reflected object.
      *
      * @return the value of the object's {@code accessible} flag
+     *
+     * @deprecated
+     * This method is deprecated because its name hints that it checks
+     * if the reflected object is accessible when it actually indicates
+     * if the checks for Java language access control are suppressed.
+     * This method may return {@code false} on a reflected object that is
+     * accessible to the caller. To test if this reflected object is accessible,
+     * it should use {@link #canAccess(Object)}.
+     *
+     * @revised 9
      */
+    @Deprecated(since="9")
     public boolean isAccessible() {
         return override;
     }
 
     /**
+     * Test if the caller can access this reflected object. If this reflected
+     * object corresponds to an instance method or field then this method tests
+     * if the caller can access the given {@code obj} with the reflected object.
+     * For instance methods or fields then the {@code obj} argument must be an
+     * instance of the {@link Member#getDeclaringClass() declaring class}. For
+     * static members and constructors then {@code obj} must be {@code null}.
+     *
+     * <p> This method returns {@code true} if the {@code accessible} flag
+     * is set to {@code true}, i.e. the checks for Java language access control
+     * are suppressed, or if the caller can access the member as
+     * specified in <cite>The Java&trade; Language Specification</cite>,
+     * with the variation noted in the class description. </p>
+     *
+     * @param obj an instance object of the declaring class of this reflected
+     *            object if it is an instance method or field
+     *
+     * @return {@code true} if the caller can access this reflected object.
+     *
+     * @throws IllegalArgumentException
+     *         <ul>
+     *         <li> if this reflected object is a static member or constructor and
+     *              the given {@code obj} is non-{@code null}, or </li>
+     *         <li> if this reflected object is an instance method or field
+     *              and the given {@code obj} is {@code null} or of type
+     *              that is not a subclass of the {@link Member#getDeclaringClass()
+     *              declaring class} of the member.</li>
+     *         </ul>
+     *
+     * @since 9
+     * @spec JPMS
+     * @jls 6.6 Access Control
+     * @see #trySetAccessible
+     * @see #setAccessible(boolean)
+     */
+    @CallerSensitive
+    public final boolean canAccess(Object obj) {
+        if (!Member.class.isInstance(this)) {
+            return override;
+        }
+
+        Class<?> declaringClass = ((Member) this).getDeclaringClass();
+        int modifiers = ((Member) this).getModifiers();
+        if (!Modifier.isStatic(modifiers) &&
+                (this instanceof Method || this instanceof Field)) {
+            if (obj == null) {
+                throw new IllegalArgumentException("null object for " + this);
+            }
+            // if this object is an instance member, the given object
+            // must be a subclass of the declaring class of this reflected object
+            if (!declaringClass.isAssignableFrom(obj.getClass())) {
+                throw new IllegalArgumentException("object is not an instance of "
+                                                   + declaringClass.getName());
+            }
+        } else if (obj != null) {
+            throw new IllegalArgumentException("non-null object for " + this);
+        }
+
+        // access check is suppressed
+        if (override) return true;
+
+        Class<?> caller = Reflection.getCallerClass();
+        Class<?> targetClass;
+        if (this instanceof Constructor) {
+            targetClass = declaringClass;
+        } else {
+            targetClass = Modifier.isStatic(modifiers) ? null : obj.getClass();
+        }
+        return Reflection.verifyMemberAccess(caller,
+                                             declaringClass,
+                                             targetClass,
+                                             modifiers);
+    }
+
+    /**
      * Constructor: only used by the Java Virtual Machine.
      */
     protected AccessibleObject() {}
--- a/jdk/src/java.base/share/classes/java/lang/reflect/Constructor.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/reflect/Constructor.java	Wed Jul 05 22:52:01 2017 +0200
@@ -168,6 +168,13 @@
      * is true. </p>
      *
      * @param flag {@inheritDoc}
+     *
+     * @throws InaccessibleObjectException {@inheritDoc}
+     * @throws SecurityException if the request is denied by the security manager
+     *         or this is a constructor for {@code java.lang.Class}
+     *
+     * @since 9
+     * @spec JPMS
      */
     @Override
     @CallerSensitive
--- a/jdk/src/java.base/share/classes/java/lang/reflect/Field.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/reflect/Field.java	Wed Jul 05 22:52:01 2017 +0200
@@ -158,6 +158,10 @@
         return res;
     }
 
+    /**
+     * @throws InaccessibleObjectException {@inheritDoc}
+     * @throws SecurityException {@inheritDoc}
+     */
     @Override
     @CallerSensitive
     public void setAccessible(boolean flag) {
--- a/jdk/src/java.base/share/classes/java/lang/reflect/InaccessibleObjectException.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/reflect/InaccessibleObjectException.java	Wed Jul 05 22:52:01 2017 +0200
@@ -30,6 +30,7 @@
  *
  * @see AccessibleObject#setAccessible(boolean)
  * @since 9
+ * @spec JPMS
  */
 
 public class InaccessibleObjectException extends RuntimeException {
--- a/jdk/src/java.base/share/classes/java/lang/reflect/Layer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/reflect/Layer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -56,20 +56,19 @@
 /**
  * A layer of modules in the Java virtual machine.
  *
- * <p> A layer is created from a graph of modules that is the {@link
- * Configuration} and a function that maps each module to a {@link ClassLoader}.
+ * <p> A layer is created from a graph of modules in a {@link Configuration}
+ * and a function that maps each module to a {@link ClassLoader}.
  * Creating a layer informs the Java virtual machine about the classes that
- * may be loaded from modules so that the Java virtual machine knows which
- * module that each class is a member of. Each layer, except the {@link
- * #empty() empty} layer, has at least one {@link #parents() parent}. </p>
+ * may be loaded from the modules so that the Java virtual machine knows which
+ * module that each class is a member of. </p>
  *
  * <p> Creating a layer creates a {@link Module} object for each {@link
  * ResolvedModule} in the configuration. For each resolved module that is
  * {@link ResolvedModule#reads() read}, the {@code Module} {@link
  * Module#canRead reads} the corresponding run-time {@code Module}, which may
- * be in the same layer or a parent layer. The {@code Module} {@link
- * Module#isExported(String) exports} the packages described by its {@link
- * ModuleDescriptor}. </p>
+ * be in the same layer or a {@link #parents() parent} layer. The {@code Module}
+ * {@link Module#isExported(String) exports} and {@link Module#isOpen(String)
+ * opens} the packages described by its {@link ModuleDescriptor}. </p>
  *
  * <p> The {@link #defineModulesWithOneLoader defineModulesWithOneLoader} and
  * {@link #defineModulesWithManyLoaders defineModulesWithManyLoaders} methods
@@ -80,7 +79,7 @@
  * a function specified to the method. Each of these methods has an instance
  * and static variant. The instance methods create a layer with the receiver
  * as the parent layer. The static methods are for more advanced cases where
- * there can be more than one parent layer or a {@link Layer.Controller
+ * there can be more than one parent layer or where a {@link Layer.Controller
  * Controller} is needed to control modules in the layer. </p>
  *
  * <p> A Java virtual machine has at least one non-empty layer, the {@link
@@ -93,9 +92,8 @@
  * the {@link #parents() parent} when creating additional layers. </p>
  *
  * <p> As when creating a {@code Configuration},
- * {@link ModuleDescriptor#isAutomatic() automatic} modules receive
- * <a href="../module/Configuration.html#automaticmoduleresolution">special
- * treatment</a> when creating a layer. An automatic module is created in the
+ * {@link ModuleDescriptor#isAutomatic() automatic} modules receive special
+ * treatment when creating a layer. An automatic module is created in the
  * Java virtual machine as a {@code Module} that reads every unnamed {@code
  * Module} in the Java virtual machine. </p>
  *
@@ -115,8 +113,7 @@
  *
  *     Layer parent = Layer.boot();
  *
- *     Configuration cf = parent.configuration()
- *         .resolveRequires(finder, ModuleFinder.of(), Set.of("myapp"));
+ *     Configuration cf = parent.configuration().resolve(finder, ModuleFinder.of(), Set.of("myapp"));
  *
  *     ClassLoader scl = ClassLoader.getSystemClassLoader();
  *
@@ -126,6 +123,7 @@
  * }</pre>
  *
  * @since 9
+ * @spec JPMS
  * @see Module#getLayer()
  */
 
@@ -168,10 +166,15 @@
      * module layers return a {@code Controller} that can be used to control
      * modules in the layer.
      *
+     * <p> Unless otherwise specified, passing a {@code null} argument to a
+     * method in this class causes a {@link NullPointerException
+     * NullPointerException} to be thrown. </p>
+     *
      * @apiNote Care should be taken with {@code Controller} objects, they
      * should never be shared with untrusted code.
      *
      * @since 9
+     * @spec JPMS
      */
     public static final class Controller {
         private final Layer layer;
@@ -281,10 +284,8 @@
      *         If the parent of the given configuration is not the configuration
      *         for this layer
      * @throws LayerInstantiationException
-     *         If all modules cannot be defined to the same class loader for any
-     *         of the reasons listed above or the layer cannot be created because
-     *         the configuration contains a module named "{@code java.base}" or
-     *         a module with a package name starting with "{@code java.}"
+     *         If the layer cannot be created for any of the reasons specified
+     *         by the static {@code defineModulesWithOneLoader} method
      * @throws SecurityException
      *         If {@code RuntimePermission("createClassLoader")} or
      *         {@code RuntimePermission("getClassLoader")} is denied by
@@ -325,9 +326,8 @@
      *         If the parent of the given configuration is not the configuration
      *         for this layer
      * @throws LayerInstantiationException
-     *         If the layer cannot be created because the configuration contains
-     *         a module named "{@code java.base}" or a module with a package
-     *         name starting with "{@code java.}"
+     *         If the layer cannot be created for any of the reasons specified
+     *         by the static {@code defineModulesWithManyLoaders} method
      * @throws SecurityException
      *         If {@code RuntimePermission("createClassLoader")} or
      *         {@code RuntimePermission("getClassLoader")} is denied by
@@ -365,14 +365,8 @@
      *         If the parent of the given configuration is not the configuration
      *         for this layer
      * @throws LayerInstantiationException
-     *         If creating the {@code Layer} fails for any of the reasons
-     *         listed above, the layer cannot be created because the
-     *         configuration contains a module named "{@code java.base}",
-     *         a module with a package name starting with "{@code java.}" is
-     *         mapped to a class loader other than the {@link
-     *         ClassLoader#getPlatformClassLoader() platform class loader},
-     *         or the function to map a module name to a class loader returns
-     *         {@code null}
+     *         If the layer cannot be created for any of the reasons specified
+     *         by the static {@code defineModules} method
      * @throws SecurityException
      *         If {@code RuntimePermission("getClassLoader")} is denied by
      *         the security manager
@@ -396,7 +390,6 @@
      * exported to one or more of the modules in this layer. The class
      * loader delegates to the class loader of the module, throwing {@code
      * ClassNotFoundException} if not found by that class loader.
-     *
      * When {@code loadClass} is invoked to load classes that do not map to a
      * module then it delegates to the parent class loader. </p>
      *
@@ -414,6 +407,10 @@
      *
      * </ul>
      *
+     * <p> In addition, a layer cannot be created if the configuration contains
+     * a module named "{@code java.base}" or a module with a package name
+     * starting with "{@code java.}". </p>
+     *
      * <p> If there is a security manager then the class loader created by
      * this method will load classes and resources with privileges that are
      * restricted by the calling context of this method. </p>
@@ -433,9 +430,7 @@
      *         the parent layers, including order
      * @throws LayerInstantiationException
      *         If all modules cannot be defined to the same class loader for any
-     *         of the reasons listed above or the layer cannot be created because
-     *         the configuration contains a module named "{@code java.base}" or
-     *         a module with a package name starting with "{@code java.}"
+     *         of the reasons listed above
      * @throws SecurityException
      *         If {@code RuntimePermission("createClassLoader")} or
      *         {@code RuntimePermission("getClassLoader")} is denied by
@@ -480,7 +475,6 @@
      * module in a parent layer. The class loader delegates to the class loader
      * of the module, throwing {@code ClassNotFoundException} if not found by
      * that class loader.
-     *
      * When {@code loadClass} is invoked to load classes that do not map to a
      * module then it delegates to the parent class loader. </p>
      *
@@ -533,15 +527,19 @@
 
     /**
      * Creates a new layer by defining the modules in the given {@code
-     * Configuration} to the Java virtual machine.
-     * Each module is mapped, by name, to its class loader by means of the
-     * given function. The class loader delegation implemented by these class
-     * loaders must respect module readability. The class loaders should be
+     * Configuration} to the Java virtual machine. The given function maps each
+     * module in the configuration, by name, to a class loader. Creating the
+     * layer informs the Java virtual machine about the classes that may be
+     * loaded so that the Java virtual machine knows which module that each
+     * class is a member of.
+     *
+     * <p> The class loader delegation implemented by the class loaders must
+     * respect module readability. The class loaders should be
      * {@link ClassLoader#registerAsParallelCapable parallel-capable} so as to
      * avoid deadlocks during class loading. In addition, the entity creating
-     * a new layer with this method should arrange that the class loaders are
+     * a new layer with this method should arrange that the class loaders be
      * ready to load from these modules before there are any attempts to load
-     * classes or resources.
+     * classes or resources. </p>
      *
      * <p> Creating a {@code Layer} can fail for the following reasons: </p>
      *
@@ -558,6 +556,13 @@
      *
      * </ul>
      *
+     * <p> In addition, a layer cannot be created if the configuration contains
+     * a module named "{@code java.base}", a configuration contains a module
+     * with a package name starting with "{@code java.}" is mapped to a class
+     * loader other than the {@link ClassLoader#getPlatformClassLoader()
+     * platform class loader}, or the function to map a module name to a class
+     * loader returns {@code null}. </p>
+     *
      * <p> If the function to map a module name to class loader throws an error
      * or runtime exception then it is propagated to the caller of this method.
      * </p>
@@ -565,7 +570,7 @@
      * @apiNote It is implementation specific as to whether creating a Layer
      * with this method is an atomic operation or not. Consequentially it is
      * possible for this method to fail with some modules, but not all, defined
-     * to Java virtual machine.
+     * to the Java virtual machine.
      *
      * @param  cf
      *         The configuration for the layer
@@ -580,14 +585,7 @@
      *         If the parent configurations do not match the configuration of
      *         the parent layers, including order
      * @throws LayerInstantiationException
-     *         If creating the {@code Layer} fails for any of the reasons
-     *         listed above, the layer cannot be created because the
-     *         configuration contains a module named "{@code java.base}",
-     *         a module with a package name starting with "{@code java.}" is
-     *         mapped to a class loader other than the {@link
-     *         ClassLoader#getPlatformClassLoader() platform class loader},
-     *         or the function to map a module name to a class loader returns
-     *         {@code null}
+     *         If creating the layer fails for any of the reasons listed above
      * @throws SecurityException
      *         If {@code RuntimePermission("getClassLoader")} is denied by
      *         the security manager
@@ -763,7 +761,7 @@
 
     /**
      * Returns the module with the given name in this layer, or if not in this
-     * layer, the {@linkplain #parents parents} layers. Finding a module in
+     * layer, the {@linkplain #parents parent} layers. Finding a module in
      * parent layers is equivalent to invoking {@code findModule} on each
      * parent, in search order, until the module is found or all parents have
      * been searched. In a <em>tree of layers</em>  then this is equivalent to
--- a/jdk/src/java.base/share/classes/java/lang/reflect/LayerInstantiationException.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/reflect/LayerInstantiationException.java	Wed Jul 05 22:52:01 2017 +0200
@@ -31,6 +31,7 @@
  * @see Layer
  *
  * @since 9
+ * @spec JPMS
  */
 public class LayerInstantiationException extends RuntimeException {
     private static final long serialVersionUID = -906239691613568347L;
--- a/jdk/src/java.base/share/classes/java/lang/reflect/Method.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/reflect/Method.java	Wed Jul 05 22:52:01 2017 +0200
@@ -179,6 +179,10 @@
         return res;
     }
 
+    /**
+     * @throws InaccessibleObjectException {@inheritDoc}
+     * @throws SecurityException {@inheritDoc}
+     */
     @Override
     @CallerSensitive
     public void setAccessible(boolean flag) {
--- a/jdk/src/java.base/share/classes/java/lang/reflect/Module.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/reflect/Module.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2014, 2017, 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
@@ -39,7 +39,6 @@
 import java.net.URL;
 import java.security.AccessController;
 import java.security.PrivilegedAction;
-import java.util.Collections;
 import java.util.HashMap;
 import java.util.HashSet;
 import java.util.Map;
@@ -74,16 +73,15 @@
  * Java Virtual Machine when a graph of modules is defined to the Java virtual
  * machine to create 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
- * loader's {@link ClassLoader#getUnnamedModule() getUnnamedModule} method. The
- * {@link Class#getModule() getModule} method of all types defined by a class
- * loader that are not in a named module return the class loader's unnamed
+ * <p> An unnamed module does not have a name. There is an unnamed module for
+ * each {@link ClassLoader ClassLoader}, obtained by invoking its {@link
+ * ClassLoader#getUnnamedModule() getUnnamedModule} method. All types that are
+ * not in a named module are members of their defining class loader's unnamed
  * module. </p>
  *
  * <p> The package names that are parameters or returned by methods defined in
  * this class are the fully-qualified names of the packages as defined in
- * section 6.5.3 of <cite>The Java&trade; Language Specification </cite>, for
+ * section 6.5.3 of <cite>The Java&trade; Language Specification</cite>, for
  * example, {@code "java.lang"}. </p>
  *
  * <p> Unless otherwise specified, passing a {@code null} argument to a method
@@ -91,6 +89,7 @@
  * be thrown. </p>
  *
  * @since 9
+ * @spec JPMS
  * @see java.lang.Class#getModule
  */
 
@@ -327,8 +326,9 @@
      *
      * @return this module
      *
-     * @throws IllegalStateException
-     *         If this is a named module and the caller is not this module
+     * @throws IllegalCallerException
+     *         If this is a named module and the caller's module is not this
+     *         module
      *
      * @see #canRead
      */
@@ -338,7 +338,7 @@
         if (this.isNamed()) {
             Module caller = Reflection.getCallerClass().getModule();
             if (caller != this) {
-                throw new IllegalStateException(caller + " != " + this);
+                throw new IllegalCallerException(caller + " != " + this);
             }
             implAddReads(other, true);
         }
@@ -533,8 +533,8 @@
         if (other == this && containsPackage(pn))
             return true;
 
-        // all packages in open modules are open
-        if (descriptor.isOpen())
+        // all packages in open and automatic modules are open
+        if (descriptor.isOpen() || descriptor.isAutomatic())
             return containsPackage(pn);
 
         // exported/opened via module declaration/descriptor
@@ -634,8 +634,7 @@
      * the given package to the given module.
      *
      * <p> This method has no effect if the package is already exported (or
-     * <em>open</em>) to the given module. It also has no effect if
-     * invoked on an {@link ModuleDescriptor#isOpen open} module. </p>
+     * <em>open</em>) to the given module. </p>
      *
      * @apiNote As specified in section 5.4.3 of the <cite>The Java&trade;
      * Virtual Machine Specification </cite>, if an attempt to resolve a
@@ -653,8 +652,9 @@
      * @throws IllegalArgumentException
      *         If {@code pn} is {@code null}, or this is a named module and the
      *         package {@code pn} is not a package in this module
-     * @throws IllegalStateException
-     *         If this is a named module and the caller is not this module
+     * @throws IllegalCallerException
+     *         If this is a named module and the caller's module is not this
+     *         module
      *
      * @jvms 5.4.3 Resolution
      * @see #isExported(String,Module)
@@ -665,10 +665,10 @@
             throw new IllegalArgumentException("package is null");
         Objects.requireNonNull(other);
 
-        if (isNamed() && !descriptor.isOpen()) {
+        if (isNamed()) {
             Module caller = Reflection.getCallerClass().getModule();
             if (caller != this) {
-                throw new IllegalStateException(caller + " != " + this);
+                throw new IllegalCallerException(caller + " != " + this);
             }
             implAddExportsOrOpens(pn, other, /*open*/false, /*syncVM*/true);
         }
@@ -686,8 +686,7 @@
      * access control checks.
      *
      * <p> This method has no effect if the package is already <em>open</em>
-     * to the given module. It also has no effect if invoked on an {@link
-     * ModuleDescriptor#isOpen open} module. </p>
+     * to the given module. </p>
      *
      * @param  pn
      *         The package name
@@ -699,9 +698,9 @@
      * @throws IllegalArgumentException
      *         If {@code pn} is {@code null}, or this is a named module and the
      *         package {@code pn} is not a package in this module
-     * @throws IllegalStateException
+     * @throws IllegalCallerException
      *         If this is a named module and this module has not opened the
-     *         package to at least the caller
+     *         package to at least the caller's module
      *
      * @see #isOpen(String,Module)
      * @see AccessibleObject#setAccessible(boolean)
@@ -713,10 +712,10 @@
             throw new IllegalArgumentException("package is null");
         Objects.requireNonNull(other);
 
-        if (isNamed() && !descriptor.isOpen()) {
+        if (isNamed()) {
             Module caller = Reflection.getCallerClass().getModule();
             if (caller != this && !isOpen(pn, caller))
-                throw new IllegalStateException(pn + " is not open to " + caller);
+                throw new IllegalCallerException(pn + " is not open to " + caller);
             implAddExportsOrOpens(pn, other, /*open*/true, /*syncVM*/true);
         }
 
@@ -767,8 +766,8 @@
         Objects.requireNonNull(other);
         Objects.requireNonNull(pn);
 
-        // all packages are open in unnamed and open modules
-        if (!isNamed() || descriptor.isOpen())
+        // all packages are open in unnamed, open, and automatic modules
+        if (!isNamed() || descriptor.isOpen() || descriptor.isAutomatic())
             return;
 
         // nothing to do if already exported/open to other
@@ -819,17 +818,17 @@
      * passed a reference to the service type by other code. This method is
      * a no-op when invoked on an unnamed module or an automatic module.
      *
-     * <p> This method does not cause {@link
-     * Configuration#resolveRequiresAndUses resolveRequiresAndUses} to be
-     * re-run. </p>
+     * <p> This method does not cause {@link Configuration#resolveAndBind
+     * resolveAndBind} to be re-run. </p>
      *
      * @param  service
      *         The service type
      *
      * @return this module
      *
-     * @throws IllegalStateException
-     *         If this is a named module and the caller is not this module
+     * @throws IllegalCallerException
+     *         If this is a named module and the caller's module is not this
+     *         module
      *
      * @see #canUse(Class)
      * @see ModuleDescriptor#uses()
@@ -841,7 +840,7 @@
         if (isNamed() && !descriptor.isAutomatic()) {
             Module caller = Reflection.getCallerClass().getModule();
             if (caller != this) {
-                throw new IllegalStateException(caller + " != " + this);
+                throw new IllegalCallerException(caller + " != " + this);
             }
             implAddUses(service);
         }
@@ -894,14 +893,13 @@
     // -- packages --
 
     // Additional packages that are added to the module at run-time.
-    // The field is volatile as it may be replaced at run-time
-    private volatile Set<String> extraPackages;
+    private volatile Map<String, Boolean> extraPackages;
 
     private boolean containsPackage(String pn) {
         if (descriptor.packages().contains(pn))
             return true;
-        Set<String> extraPackages = this.extraPackages;
-        if (extraPackages != null && extraPackages.contains(pn))
+        Map<String, Boolean> extraPackages = this.extraPackages;
+        if (extraPackages != null && extraPackages.containsKey(pn))
             return true;
         return false;
     }
@@ -915,7 +913,7 @@
      * added to the module, <a href="Proxy.html#dynamicmodule">dynamic modules</a>
      * for example, after it was loaded.
      *
-     * <p> For unnamed modules, this method is the equivalent of invoking the
+     * <p> For unnamed modules, this method is the equivalent to invoking the
      * {@link ClassLoader#getDefinedPackages() getDefinedPackages} method of
      * this module's class loader and returning the array of package names. </p>
      *
@@ -930,12 +928,12 @@
         if (isNamed()) {
 
             Set<String> packages = descriptor.packages();
-            Set<String> extraPackages = this.extraPackages;
+            Map<String, Boolean> extraPackages = this.extraPackages;
             if (extraPackages == null) {
                 return packages.toArray(new String[0]);
             } else {
                 return Stream.concat(packages.stream(),
-                                     extraPackages.stream())
+                                     extraPackages.keySet().stream())
                         .toArray(String[]::new);
             }
 
@@ -955,10 +953,6 @@
      * Add a package to this module.
      *
      * @apiNote This method is for Proxy use.
-     *
-     * @apiNote This is an expensive operation, not expected to be used often.
-     * At this time then it does not validate that the package name is a
-     * valid java identifier.
      */
     void addPackage(String pn) {
         implAddPackage(pn, true);
@@ -976,49 +970,52 @@
     /**
      * Add a package to this module.
      *
-     * If {@code syncVM} is {@code true} then the VM is notified.
+     * If {@code syncVM} is {@code true} then the VM is notified. This method is
+     * a no-op if this is an unnamed module or the module already contains the
+     * package.
+     *
+     * @throws IllegalArgumentException if the package name is not legal
+     * @throws IllegalStateException if the package is defined to another module
      */
     private void implAddPackage(String pn, boolean syncVM) {
+        // no-op if unnamed module
         if (!isNamed())
-            throw new InternalError("adding package to unnamed module?");
-        if (descriptor.isOpen())
-            throw new InternalError("adding package to open module?");
+            return;
+
+        // no-op if module contains the package
+        if (containsPackage(pn))
+            return;
+
+        // check package name is legal for named modules
         if (pn.isEmpty())
-            throw new InternalError("adding <unnamed> package to module?");
-
-        if (descriptor.packages().contains(pn)) {
-            // already in module
-            return;
+            throw new IllegalArgumentException("Cannot add <unnamed> package");
+        for (int i=0; i<pn.length(); i++) {
+            char c = pn.charAt(i);
+            if (c == '/' || c == ';' || c == '[') {
+                throw new IllegalArgumentException("Illegal character: " + c);
+            }
         }
 
-        Set<String> extraPackages = this.extraPackages;
-        if (extraPackages != null && extraPackages.contains(pn)) {
-            // already added
-            return;
+        // create extraPackages if needed
+        Map<String, Boolean> extraPackages = this.extraPackages;
+        if (extraPackages == null) {
+            synchronized (this) {
+                extraPackages = this.extraPackages;
+                if (extraPackages == null)
+                    this.extraPackages = extraPackages = new ConcurrentHashMap<>();
+            }
         }
-        synchronized (this) {
-            // recheck under lock
-            extraPackages = this.extraPackages;
-            if (extraPackages != null) {
-                if (extraPackages.contains(pn)) {
-                    // already added
-                    return;
-                }
 
-                // copy the set
-                extraPackages = new HashSet<>(extraPackages);
-                extraPackages.add(pn);
-            } else {
-                extraPackages = Collections.singleton(pn);
+        // update VM first in case it fails. This is a no-op if another thread
+        // beats us to add the package first
+        if (syncVM) {
+            // throws IllegalStateException if defined to another module
+            addPackage0(this, pn);
+            if (descriptor.isOpen() || descriptor.isAutomatic()) {
+                addExportsToAll0(this, pn);
             }
-
-            // update VM first, just in case it fails
-            if (syncVM)
-                addPackage0(this, pn);
-
-            // replace with new set
-            this.extraPackages = extraPackages; // volatile write
         }
+        extraPackages.putIfAbsent(pn, Boolean.TRUE);
     }
 
 
@@ -1169,8 +1166,9 @@
                                             Map<String, Module> nameToModule,
                                             Module m)
     {
-        // The VM doesn't know about open modules so need to export all packages
-        if (descriptor.isOpen()) {
+        // The VM doesn't special case open or automatic modules so need to
+        // export all packages
+        if (descriptor.isOpen() || descriptor.isAutomatic()) {
             assert descriptor.opens().isEmpty();
             for (String source : descriptor.packages()) {
                 addExportsToAll0(m, source);
@@ -1375,35 +1373,44 @@
 
 
     /**
-     * Returns an input stream for reading a resource in this module. The
-     * {@code name} parameter is a {@code '/'}-separated path name that
-     * identifies the resource.
+     * Returns an input stream for reading a resource in this module.
+     * The {@code name} parameter is a {@code '/'}-separated path name that
+     * identifies the resource. As with {@link Class#getResourceAsStream
+     * Class.getResourceAsStream}, this method delegates to the module's class
+     * loader {@link ClassLoader#findResource(String,String)
+     * findResource(String,String)} method, invoking it with the module name
+     * (or {@code null} when the module is unnamed) and the name of the
+     * resource. If the resource name has a leading slash then it is dropped
+     * before delegation.
      *
-     * <p> A resource in a named modules may be <em>encapsulated</em> so that
+     * <p> A resource in a named module may be <em>encapsulated</em> so that
      * it cannot be located by code in other modules. Whether a resource can be
-     * located or not is determined as follows:
+     * located or not is determined as follows: </p>
      *
      * <ul>
-     *     <li> The <em>package name</em> of the resource is derived from the
-     *     subsequence of characters that precedes the last {@code '/'} and then
-     *     replacing each {@code '/'} character in the subsequence with
-     *     {@code '.'}. For example, the package name derived for a resource
-     *     named "{@code a/b/c/foo.properties}" is "{@code a.b.c}". </li>
+     *     <li> If the resource name ends with  "{@code .class}" then it is not
+     *     encapsulated. </li>
      *
-     *     <li> If the package name is a package in the module then the package
-     *     must be {@link #isOpen open} the module of the caller of this method.
-     *     If the package is not in the module then the resource is not
-     *     encapsulated. Resources in the unnamed package or "{@code META-INF}",
-     *     for example, are never encapsulated because they can never be
-     *     packages in a named module. </li>
+     *     <li> A <em>package name</em> is derived from the resource name. If
+     *     the package name is a {@link #getPackages() package} in the module
+     *     then the resource can only be located by the caller of this method
+     *     when the package is {@link #isOpen(String,Module) open} to at least
+     *     the caller's module. If the resource is not in a package in the module
+     *     then the resource is not encapsulated. </li>
+     * </ul>
      *
-     *     <li> As a special case, resources ending with "{@code .class}" are
-     *     never encapsulated. </li>
-     * </ul>
+     * <p> In the above, the <em>package name</em> for a resource is derived
+     * from the subsequence of characters that precedes the last {@code '/'} in
+     * the name and then replacing each {@code '/'} character in the subsequence
+     * with {@code '.'}. A leading slash is ignored when deriving the package
+     * name. As an example, the package name derived for a resource named
+     * "{@code a/b/c/foo.properties}" is "{@code a.b.c}". A resource name
+     * with the name "{@code META-INF/MANIFEST.MF}" is never encapsulated
+     * because "{@code META-INF}" is not a legal package name. </p>
      *
      * <p> This method returns {@code null} if the resource is not in this
      * module, the resource is encapsulated and cannot be located by the caller,
-     * or access to the resource is denied by the security manager.
+     * or access to the resource is denied by the security manager. </p>
      *
      * @param  name
      *         The resource name
@@ -1413,11 +1420,13 @@
      * @throws IOException
      *         If an I/O error occurs
      *
-     * @see java.lang.module.ModuleReader#open(String)
+     * @see Class#getResourceAsStream(String)
      */
     @CallerSensitive
     public InputStream getResourceAsStream(String name) throws IOException {
-        Objects.requireNonNull(name);
+        if (name.startsWith("/")) {
+            name = name.substring(1);
+        }
 
         if (isNamed() && !ResourceHelper.isSimpleResource(name)) {
             Module caller = Reflection.getCallerClass().getModule();
--- a/jdk/src/java.base/share/classes/java/lang/reflect/Proxy.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/reflect/Proxy.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,7 @@
 
 package java.lang.reflect;
 
+import java.lang.module.ModuleDescriptor;
 import java.security.AccessController;
 import java.security.PrivilegedAction;
 import java.util.Arrays;
@@ -52,6 +53,9 @@
 import sun.security.action.GetPropertyAction;
 import sun.security.util.SecurityConstants;
 
+import static java.lang.module.ModuleDescriptor.Modifier.SYNTHETIC;
+
+
 /**
  *
  * {@code Proxy} provides static methods for creating objects that act like instances
@@ -164,7 +168,8 @@
  * methods is specified as follows:
  *
  * <ol>
- * <li>If all the proxy interfaces are in <em>exported</em> packages:
+ * <li>If all the proxy interfaces are in <em>exported</em> or <em>open</em>
+ *     packages:
  * <ol type="a">
  * <li>if all the proxy interfaces are <em>public</em>, then the proxy class is
  *     <em>public</em> in a package exported by the
@@ -178,10 +183,11 @@
  *     <a href="#restrictions">not possible</a>.</li>
  * </ol>
  * </li>
- * <li>If at least one proxy interface is a <em>non-exported</em> package:
+ * <li>If at least one proxy interface is in a package that is
+ *     <em>non-exported</em> and <em>non-open</em>:
  * <ol type="a">
  * <li>if all the proxy interfaces are <em>public</em>, then the proxy class is
- *     <em>public</em> in a <em>non-exported</em> package of
+ *     <em>public</em> in a <em>non-exported</em>, <em>non-open</em> package of
  *     <a href="#dynamicmodule"><em>dynamic module</em>.</a>
  *     The names of the package and the module are unspecified.</li>
  *
@@ -195,21 +201,22 @@
  * </ol>
  *
  * <p>
- * Note that if proxy interfaces with a mix of accessibilities --
- * exported public, exported non-public, non-exported public, non-exported non-public --
- * are proxied by the same instance, then the proxy class's accessibility is
+ * Note that if proxy interfaces with a mix of accessibilities -- for example,
+ * an exported public interface and a non-exported non-public interface -- are
+ * proxied by the same instance, then the proxy class's accessibility is
  * governed by the least accessible proxy interface.
  * <p>
  * Note that it is possible for arbitrary code to obtain access to a proxy class
- * in an exported package with {@link AccessibleObject#setAccessible setAccessible},
- * whereas a proxy class in a non-exported package is never accessible to
+ * in an open package with {@link AccessibleObject#setAccessible setAccessible},
+ * whereas a proxy class in a non-open package is never accessible to
  * code outside the module of the proxy class.
  *
  * <p>
- * Throughout this specification, a "non-exported package" refers to a package that
- * is not exported to all modules. Specifically, it refers to a package that
- * either is not exported at all by its containing module or is exported in a
- * qualified fashion by its containing module.
+ * Throughout this specification, a "non-exported package" refers to a package
+ * that is not exported to all modules, and a "non-open package" refers to
+ * a package that is not open to all modules.  Specifically, these terms refer to
+ * a package that either is not exported/open by its containing module or is
+ * exported/open in a qualified fashion by its containing module.
  *
  * <h3><a name="dynamicmodule">Dynamic Modules</a></h3>
  * <p>
@@ -272,6 +279,8 @@
  * @author      Peter Jones
  * @see         InvocationHandler
  * @since       1.3
+ * @revised 9
+ * @spec JPMS
  */
 public class Proxy implements java.io.Serializable {
     private static final long serialVersionUID = -2222568056686623797L;
@@ -358,6 +367,8 @@
      *      to create a proxy instance instead.
      *
      * @see <a href="#membership">Package and Module Membership of Proxy Class</a>
+     * @revised 9
+     * @spec JPMS
      */
     @Deprecated
     @CallerSensitive
@@ -855,7 +866,11 @@
                 // create a dynamic module and setup module access
                 String mn = "jdk.proxy" + counter.incrementAndGet();
                 String pn = PROXY_PACKAGE_PREFIX + "." + mn;
-                Module m = Modules.defineModule(ld, mn, Collections.singleton(pn));
+                ModuleDescriptor descriptor =
+                    ModuleDescriptor.newModule(mn, Set.of(SYNTHETIC))
+                                    .packages(Set.of(pn))
+                                    .build();
+                Module m = Modules.defineModule(ld, descriptor, null);
                 Modules.addReads(m, Proxy.class.getModule());
                 // java.base to create proxy instance
                 Modules.addExports(m, pn, Object.class.getModule());
@@ -955,6 +970,8 @@
      *          {@code null}
      *
      * @see <a href="#membership">Package and Module Membership of Proxy Class</a>
+     * @revised 9
+     * @spec JPMS
      */
     @CallerSensitive
     public static Object newProxyInstance(ClassLoader loader,
@@ -1039,6 +1056,9 @@
      * @return  {@code true} if the class is a proxy class and
      *          {@code false} otherwise
      * @throws  NullPointerException if {@code cl} is {@code null}
+     *
+     * @revised 9
+     * @spec JPMS
      */
     public static boolean isProxyClass(Class<?> cl) {
         return Proxy.class.isAssignableFrom(cl) && ProxyBuilder.isProxyClass(cl);
--- a/jdk/src/java.base/share/classes/java/lang/reflect/package-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/lang/reflect/package-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -45,5 +45,7 @@
  * members declared by a given class.
  *
  * @since 1.1
+ * @revised 9
+ * @spec JPMS
  */
 package java.lang.reflect;
--- a/jdk/src/java.base/share/classes/java/net/URLClassLoader.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/net/URLClassLoader.java	Wed Jul 05 22:52:01 2017 +0200
@@ -228,6 +228,7 @@
      *         allow creation of a class loader.
      *
      * @since 9
+     * @spec JPMS
      */
     public URLClassLoader(String name,
                           URL[] urls,
@@ -262,6 +263,7 @@
      *         creation of a class loader.
      *
      * @since 9
+     * @spec JPMS
      */
     public URLClassLoader(String name, URL[] urls, ClassLoader parent,
                           URLStreamHandlerFactory factory) {
@@ -558,6 +560,9 @@
      * @throws      IllegalArgumentException if the package name is
      *              already defined by this class loader
      * @return      the newly defined {@code Package} object
+     *
+     * @revised 9
+     * @spec JPMS
      */
     protected Package definePackage(String name, Manifest man, URL url) {
         String path = name.replace('.', '/').concat("/");
--- a/jdk/src/java.base/share/classes/java/security/SecureClassLoader.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/security/SecureClassLoader.java	Wed Jul 05 22:52:01 2017 +0200
@@ -125,6 +125,7 @@
      *         doesn't allow creation of a class loader.
      *
      * @since 9
+     * @spec JPMS
      */
     protected SecureClassLoader(String name, ClassLoader parent) {
         super(name, parent);
--- a/jdk/src/java.base/share/classes/java/security/Security.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/security/Security.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,11 +25,12 @@
 
 package java.security;
 
-import java.lang.reflect.*;
 import java.util.*;
 import java.util.concurrent.ConcurrentHashMap;
 import java.io.*;
 import java.net.URL;
+
+import jdk.internal.misc.SharedSecrets;
 import sun.security.util.Debug;
 import sun.security.util.PropertyExpander;
 
@@ -800,9 +801,6 @@
      * "package.definition", we need to signal to the SecurityManager
      * class that the value has just changed, and that it should
      * invalidate it's local cache values.
-     *
-     * Rather than create a new API entry for this function,
-     * we use reflection to set a private variable.
      */
     private static void invalidateSMCache(String key) {
 
@@ -810,42 +808,8 @@
         final boolean pd = key.equals("package.definition");
 
         if (pa || pd) {
-            AccessController.doPrivileged(new PrivilegedAction<>() {
-                public Void run() {
-                    try {
-                        /* Get the class via the bootstrap class loader. */
-                        Class<?> cl = Class.forName(
-                            "java.lang.SecurityManager", false, null);
-                        Field f = null;
-                        boolean accessible = false;
-
-                        if (pa) {
-                            f = cl.getDeclaredField("packageAccessValid");
-                            accessible = f.isAccessible();
-                            f.setAccessible(true);
-                        } else {
-                            f = cl.getDeclaredField("packageDefinitionValid");
-                            accessible = f.isAccessible();
-                            f.setAccessible(true);
-                        }
-                        f.setBoolean(f, false);
-                        f.setAccessible(accessible);
-                    }
-                    catch (Exception e1) {
-                        /* If we couldn't get the class, it hasn't
-                         * been loaded yet.  If there is no such
-                         * field, we shouldn't try to set it.  There
-                         * shouldn't be a security execption, as we
-                         * are loaded by boot class loader, and we
-                         * are inside a doPrivileged() here.
-                         *
-                         * NOOP: don't do anything...
-                         */
-                    }
-                    return null;
-                }  /* run */
-            });  /* PrivilegedAction */
-        }  /* if */
+            SharedSecrets.getJavaLangAccess().invalidatePackageAccessCache();
+        }
     }
 
     private static void check(String directive) {
--- a/jdk/src/java.base/share/classes/java/util/ResourceBundle.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/util/ResourceBundle.java	Wed Jul 05 22:52:01 2017 +0200
@@ -350,6 +350,8 @@
  * @see MissingResourceException
  * @see ResourceBundleProvider
  * @since 1.1
+ * @revised 9
+ * @spec JPMS
  */
 public abstract class ResourceBundle {
 
@@ -870,6 +872,8 @@
      * @throws UnsupportedOperationException
      *         if this method is called in a named module
      * @since 1.6
+     * @revised 9
+     * @spec JPMS
      */
     @CallerSensitive
     public static final ResourceBundle getBundle(String baseName,
@@ -938,6 +942,7 @@
      *         specified module
      * @return a resource bundle for the given base name and the default locale
      * @since 9
+     * @spec JPMS
      * @see ResourceBundleProvider
      */
     @CallerSensitive
@@ -991,6 +996,7 @@
      *         be found in the specified {@code module}
      * @return a resource bundle for the given base name and locale in the module
      * @since 9
+     * @spec JPMS
      */
     @CallerSensitive
     public static ResourceBundle getBundle(String baseName, Locale targetLocale, Module module) {
@@ -1036,6 +1042,8 @@
      * @throws UnsupportedOperationException
      *         if this method is called in a named module
      * @since 1.6
+     * @revised 9
+     * @spec JPMS
      */
     @CallerSensitive
     public static final ResourceBundle getBundle(String baseName, Locale targetLocale,
@@ -1243,6 +1251,8 @@
      * @exception MissingResourceException
      *        if no resource bundle for the specified base name can be found
      * @since 1.2
+     * @revised 9
+     * @spec JPMS
      */
     @CallerSensitive
     public static ResourceBundle getBundle(String baseName, Locale locale,
@@ -1465,6 +1475,8 @@
      * @throws UnsupportedOperationException
      *         if this method is called in a named module
      * @since 1.6
+     * @revised 9
+     * @spec JPMS
      */
     @CallerSensitive
     public static ResourceBundle getBundle(String baseName, Locale targetLocale,
@@ -2194,6 +2206,8 @@
      * by the caller's module.
      *
      * @since 1.6
+     * @revised 9
+     * @spec JPMS
      * @see ResourceBundle.Control#getTimeToLive(String,Locale)
      */
     @CallerSensitive
@@ -2475,6 +2489,8 @@
      * of {@link ResourceBundleControlProvider} are ignored in named modules.
      *
      * @since 1.6
+     * @revised 9
+     * @spec JPMS
      * @see java.util.spi.ResourceBundleProvider
      */
     public static class Control {
@@ -3103,6 +3119,8 @@
          *        if an error occurred when reading resources using
          *        any I/O operations
          * @see java.util.spi.ResourceBundleProvider#getBundle(String, Locale)
+         * @revised 9
+         * @spec JPMS
          */
         public ResourceBundle newBundle(String baseName, Locale locale, String format,
                                         ClassLoader loader, boolean reload)
--- a/jdk/src/java.base/share/classes/java/util/ServiceLoader.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/util/ServiceLoader.java	Wed Jul 05 22:52:01 2017 +0200
@@ -119,7 +119,7 @@
  * and deployed as an explicit module must have an appropriate <i>uses</i>
  * clause in its <i>module descriptor</i> to declare that the module uses
  * implementations of the service. A corresponding requirement is that a
- * provider deployed as a named module must have an appropriate
+ * provider deployed as an explicit module must have an appropriate
  * <i>provides</i> clause in its module descriptor to declare that the module
  * provides an implementation of the service. The <i>uses</i> and
  * <i>provides</i> allow consumers of a service to be <i>linked</i> to modules
@@ -203,8 +203,11 @@
  *     ordering of modules in a layer, is not defined. </li>
  *
  *     <li> If a named module declares more than one provider then the providers
- *     are located in the order that they appear in the {@code provides} table of
- *     the {@code Module} class file attribute ({@code module-info.class}). </li>
+ *     are located in the iteration order of the {@link
+ *     java.lang.module.ModuleDescriptor.Provides#providers() providers} list.
+ *     Providers added dynamically by instrumentation agents ({@link
+ *     java.lang.instrument.Instrumentation#redefineModule redefineModule})
+ *     are always located after providers declared by the module. </li>
  *
  *     <li> When locating providers in unnamed modules then the ordering is
  *     based on the order that the class loader's {@link
@@ -335,6 +338,8 @@
  *
  * @author Mark Reinhold
  * @since 1.6
+ * @revised 9
+ * @spec JPMS
  */
 
 public final class ServiceLoader<S>
@@ -386,6 +391,7 @@
      *
      * @param  <S> The service type
      * @since 9
+     * @spec JPMS
      */
     public static interface Provider<S> extends Supplier<S> {
         /**
@@ -927,26 +933,28 @@
             } else {
                 catalog = ServicesCatalog.getServicesCatalogOrNull(loader);
             }
-            Stream<ServiceProvider> stream1;
+            List<ServiceProvider> providers;
             if (catalog == null) {
-                stream1 = Stream.empty();
+                providers = List.of();
             } else {
-                stream1 = catalog.findServices(serviceName).stream();
+                providers = catalog.findServices(serviceName);
             }
 
             // modules in custom layers that define modules to the class loader
-            Stream<ServiceProvider> stream2;
             if (loader == null) {
-                stream2 = Stream.empty();
+                return providers.iterator();
             } else {
+                List<ServiceProvider> allProviders = new ArrayList<>(providers);
                 Layer bootLayer = Layer.boot();
-                stream2 = JLRM_ACCESS.layers(loader)
-                        .filter(l -> (l != bootLayer))
-                        .map(l -> providers(l))
-                        .flatMap(List::stream);
+                Iterator<Layer> iterator = JLRM_ACCESS.layers(loader).iterator();
+                while (iterator.hasNext()) {
+                    Layer layer = iterator.next();
+                    if (layer != bootLayer) {
+                        allProviders.addAll(providers(layer));
+                    }
+                }
+                return allProviders.iterator();
             }
-
-            return Stream.concat(stream1, stream2).iterator();
         }
 
         @Override
@@ -1214,6 +1222,9 @@
      *
      * @return  An iterator that lazily loads providers for this loader's
      *          service
+     *
+     * @revised 9
+     * @spec JPMS
      */
     public Iterator<S> iterator() {
 
@@ -1279,8 +1290,10 @@
      * provider to be loaded. </p>
      *
      * <p> If this loader's provider caches are cleared by invoking the {@link
-     * #reload() reload} method then existing streams for this service
-     * loader should be discarded. </p>
+     * #reload() reload} method then existing streams for this service loader
+     * should be discarded. The returned stream's source {@code Spliterator} is
+     * <em>fail-fast</em> and will throw {@link ConcurrentModificationException}
+     * if the provider cache has been cleared. </p>
      *
      * <p> The following examples demonstrate usage. The first example
      * creates a stream of providers, the second example is the same except
@@ -1300,6 +1313,7 @@
      * @return  A stream that lazily loads providers for this loader's service
      *
      * @since 9
+     * @spec JPMS
      */
     public Stream<Provider<S>> stream() {
         // use cached providers as the source when all providers loaded
@@ -1414,6 +1428,9 @@
      *         if the service type is not accessible to the caller or the
      *         caller is in an explicit module and its module descriptor does
      *         not declare that it uses {@code service}
+     *
+     * @revised 9
+     * @spec JPMS
      */
     @CallerSensitive
     public static <S> ServiceLoader<S> load(Class<S> service,
@@ -1457,6 +1474,9 @@
      *         if the service type is not accessible to the caller or the
      *         caller is in an explicit module and its module descriptor does
      *         not declare that it uses {@code service}
+     *
+     * @revised 9
+     * @spec JPMS
      */
     @CallerSensitive
     public static <S> ServiceLoader<S> load(Class<S> service) {
@@ -1490,6 +1510,9 @@
      *         if the service type is not accessible to the caller or the
      *         caller is in an explicit module and its module descriptor does
      *         not declare that it uses {@code service}
+     *
+     * @revised 9
+     * @spec JPMS
      */
     @CallerSensitive
     public static <S> ServiceLoader<S> loadInstalled(Class<S> service) {
@@ -1522,6 +1545,7 @@
      *         not declare that it uses {@code service}
      *
      * @since 9
+     * @spec JPMS
      */
     @CallerSensitive
     public static <S> ServiceLoader<S> load(Layer layer, Class<S> service) {
@@ -1551,6 +1575,7 @@
      *         or error is thrown when locating or instantiating the provider.
      *
      * @since 9
+     * @spec JPMS
      */
     public Optional<S> findFirst() {
         Iterator<S> iterator = iterator();
--- a/jdk/src/java.base/share/classes/java/util/spi/AbstractResourceBundleProvider.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/util/spi/AbstractResourceBundleProvider.java	Wed Jul 05 22:52:01 2017 +0200
@@ -81,6 +81,7 @@
  *     ResourceBundleProvider Service Providers</a>
  *
  * @since 9
+ * @spec JPMS
  */
 public abstract class AbstractResourceBundleProvider implements ResourceBundleProvider {
     private static final JavaUtilResourceBundleAccess RB_ACCESS =
--- a/jdk/src/java.base/share/classes/java/util/spi/ResourceBundleControlProvider.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/util/spi/ResourceBundleControlProvider.java	Wed Jul 05 22:52:01 2017 +0200
@@ -44,6 +44,8 @@
  *
  * @author Masayoshi Okutsu
  * @since 1.8
+ * @revised 9
+ * @spec JPMS
  * @see ResourceBundle#getBundle(String, java.util.Locale, ClassLoader, ResourceBundle.Control)
  *      ResourceBundle.getBundle
  * @see java.util.ServiceLoader#load(Class)
--- a/jdk/src/java.base/share/classes/java/util/spi/ResourceBundleProvider.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/java/util/spi/ResourceBundleProvider.java	Wed Jul 05 22:52:01 2017 +0200
@@ -57,6 +57,7 @@
  * @see <a href="../ResourceBundle.html#RBP_support">
  *     ResourceBundleProvider Service Providers</a>
  * @since 9
+ * @spec JPMS
  */
 public interface ResourceBundleProvider {
     /**
--- a/jdk/src/java.base/share/classes/jdk/internal/jmod/JmodFile.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/jdk/internal/jmod/JmodFile.java	Wed Jul 05 22:52:01 2017 +0200
@@ -78,7 +78,7 @@
         HEADER_FILES("include"),
         LEGAL_NOTICES("legal"),
         MAN_PAGES("man"),
-        NATIVE_LIBS("native"),
+        NATIVE_LIBS("lib"),
         NATIVE_CMDS("bin");
 
         private final String jmodDir;
@@ -186,7 +186,7 @@
     public Entry getEntry(Section section, String name) {
         String entry = section.jmodDir() + "/" + name;
         ZipEntry ze = zipfile.getEntry(entry);
-        return (ze != null) ? new Entry(ze) : null;
+        return (ze == null || ze.isDirectory()) ? null : new Entry(ze);
     }
 
     /**
@@ -201,7 +201,7 @@
     {
         String entry = section.jmodDir() + "/" + name;
         ZipEntry e = zipfile.getEntry(entry);
-        if (e == null) {
+        if (e == null || e.isDirectory()) {
             throw new IOException(name + " not found: " + file);
         }
         return zipfile.getInputStream(e);
--- a/jdk/src/java.base/share/classes/jdk/internal/loader/BuiltinClassLoader.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/jdk/internal/loader/BuiltinClassLoader.java	Wed Jul 05 22:52:01 2017 +0200
@@ -57,8 +57,9 @@
 import java.util.jar.Manifest;
 import java.util.stream.Stream;
 
+import jdk.internal.misc.VM;
 import jdk.internal.module.ModulePatcher.PatchedModuleReader;
-import jdk.internal.misc.VM;
+import jdk.internal.module.SystemModules;
 
 
 /**
@@ -135,7 +136,7 @@
 
     // maps package name to loaded module for modules in the boot layer
     private static final Map<String, LoadedModule> packageToModule
-        = new ConcurrentHashMap<>(1024);
+        = new ConcurrentHashMap<>(SystemModules.PACKAGES_IN_BOOT_LAYER);
 
     // maps a module name to a module reference
     private final Map<String, ModuleReference> nameToModule;
@@ -922,13 +923,13 @@
      * Returns the ModuleReader for the given module.
      */
     private ModuleReader moduleReaderFor(ModuleReference mref) {
-        return moduleToReader.computeIfAbsent(mref, m -> createModuleReader(mref));
+        return moduleToReader.computeIfAbsent(mref, BuiltinClassLoader::createModuleReader);
     }
 
     /**
      * Creates a ModuleReader for the given module.
      */
-    private ModuleReader createModuleReader(ModuleReference mref) {
+    private static ModuleReader createModuleReader(ModuleReference mref) {
         try {
             return mref.open();
         } catch (IOException e) {
--- a/jdk/src/java.base/share/classes/jdk/internal/loader/ResourceHelper.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/jdk/internal/loader/ResourceHelper.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -24,6 +24,10 @@
  */
 package jdk.internal.loader;
 
+import java.io.File;
+import java.nio.file.Path;
+import java.nio.file.Paths;
+
 import jdk.internal.module.Checks;
 
 /**
@@ -34,7 +38,8 @@
     private ResourceHelper() { }
 
     /**
-     * Returns the <em>package name</em> for a resource.
+     * Returns the <em>package name</em> for a resource or the empty package if
+     * the resource name does not contain a slash.
      */
     public static String getPackageName(String name) {
         int index = name.lastIndexOf('/');
@@ -46,19 +51,75 @@
     }
 
     /**
-     * Returns true if the resource is a <em>simple resource</em> that can
-     * never be encapsulated. Resources ending in "{@code .class}" or where
-     * the package name is not a Java identifier are resources that can
-     * never be encapsulated.
+     * Returns true if the resource is a <em>simple resource</em>. Simple
+     * resources can never be encapsulated. Resources ending in "{@code .class}"
+     * or where the package name is not a legal package name can not be
+     * encapsulated.
      */
     public static boolean isSimpleResource(String name) {
         int len = name.length();
         if (len > 6 && name.endsWith(".class")) {
             return true;
         }
-        if (!Checks.isJavaIdentifier(getPackageName(name))) {
+        if (!Checks.isPackageName(getPackageName(name))) {
             return true;
         }
         return false;
     }
+
+    /**
+     * Converts a resource name to a file path. Returns {@code null} if the
+     * resource name cannot be converted into a file path. Resource names
+     * with empty elements, or elements that are "." or ".." are rejected,
+     * as is a resource name that translates to a file path with a root
+     * component.
+     */
+    public static Path toFilePath(String name) {
+        // scan the resource name to eagerly reject obviously invalid names
+        int next;
+        int off = 0;
+        while ((next = name.indexOf('/', off)) != -1) {
+            int len = next - off;
+            if (!mayTranslate(name, off, len)) {
+                return null;
+            }
+            off = next + 1;
+        }
+        int rem = name.length() - off;
+        if (!mayTranslate(name, off, rem)) {
+            return null;
+        }
+
+        // convert to file path
+        Path path;
+        if (File.separatorChar == '/') {
+            path = Paths.get(name);
+        } else {
+            // not allowed to embed file separators
+            if (name.contains(File.separator))
+                return null;
+            path = Paths.get(name.replace('/', File.separatorChar));
+        }
+
+        // file path not allowed to have root component
+        return (path.getRoot() == null) ? path : null;
+    }
+
+    /**
+     * Returns {@code true} if the element in a resource name is a candidate
+     * to translate to the element of a file path.
+     */
+    private static boolean mayTranslate(String name, int off, int len) {
+        if (len <= 2) {
+            if (len == 0)
+                return false;
+            boolean starsWithDot = (name.charAt(off) == '.');
+            if (len == 1 && starsWithDot)
+                return false;
+            if (len == 2 && starsWithDot && (name.charAt(off+1) == '.'))
+                return false;
+        }
+        return true;
+    }
+
 }
--- a/jdk/src/java.base/share/classes/jdk/internal/misc/JavaLangAccess.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/jdk/internal/misc/JavaLangAccess.java	Wed Jul 05 22:52:01 2017 +0200
@@ -174,4 +174,9 @@
      * Invokes Long.fastUUID
      */
     String fastUUID(long lsb, long msb);
+
+    /**
+     * Invalidate package access cache
+     */
+    void invalidatePackageAccessCache();
 }
--- a/jdk/src/java.base/share/classes/jdk/internal/misc/JavaLangModuleAccess.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/jdk/internal/misc/JavaLangModuleAccess.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2017, 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
@@ -59,20 +59,21 @@
      */
     ModuleDescriptor.Builder newModuleBuilder(String mn,
                                               boolean strict,
-                                              boolean open,
-                                              boolean synthetic);
+                                              Set<ModuleDescriptor.Modifier> ms);
+
+    /**
+     * Returns a snapshot of the packages in the module.
+     */
+    Set<String> packages(ModuleDescriptor.Builder builder);
 
     /**
-     * Returns the set of packages that are exported (unconditionally or
-     * unconditionally).
+     * Adds a dependence on a module with the given (possibly un-parsable)
+     * version string.
      */
-    Set<String> exportedPackages(ModuleDescriptor.Builder builder);
-
-    /**
-     * Returns the set of packages that are opened (unconditionally or
-     * unconditionally).
-     */
-    Set<String> openPackages(ModuleDescriptor.Builder builder);
+    void requires(ModuleDescriptor.Builder builder,
+                  Set<Requires.Modifier> ms,
+                  String mn,
+                  String compiledVersion);
 
     /**
      * Returns a {@code ModuleDescriptor.Requires} of the given modifiers
@@ -114,23 +115,11 @@
     Provides newProvides(String service, List<String> providers);
 
     /**
-     * Returns a {@code ModuleDescriptor.Version} of the given version.
-     */
-    Version newVersion(String v);
-
-    /**
-     * Clones the given module descriptor with an augmented set of packages
-     */
-    ModuleDescriptor newModuleDescriptor(ModuleDescriptor md, Set<String> pkgs);
-
-    /**
      * Returns a new {@code ModuleDescriptor} instance.
      */
     ModuleDescriptor newModuleDescriptor(String name,
                                          Version version,
-                                         boolean open,
-                                         boolean automatic,
-                                         boolean synthetic,
+                                         Set<ModuleDescriptor.Modifier> ms,
                                          Set<Requires> requires,
                                          Set<Exports> exports,
                                          Set<Opens> opens,
@@ -148,9 +137,9 @@
      * and the empty configuration as the parent. The post resolution
      * checks are optionally run.
      */
-    Configuration resolveRequiresAndUses(ModuleFinder finder,
-                                         Collection<String> roots,
-                                         boolean check,
-                                         PrintStream traceOutput);
+    Configuration resolveAndBind(ModuleFinder finder,
+                                 Collection<String> roots,
+                                 boolean check,
+                                 PrintStream traceOutput);
 
 }
--- a/jdk/src/java.base/share/classes/jdk/internal/module/Builder.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/jdk/internal/module/Builder.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2017, 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
@@ -38,7 +38,7 @@
 import jdk.internal.misc.SharedSecrets;
 
 /**
- * This builder is optimized for reconstituting ModuleDescriptor
+ * This builder is optimized for reconstituting the {@code ModuleDescriptor}s
  * for system modules.  The validation should be done at jlink time.
  *
  * 1. skip name validation
@@ -136,9 +136,7 @@
     }
 
     final String name;
-    boolean open;
-    boolean automatic;
-    boolean synthetic;
+    boolean open, synthetic, mandated;
     Set<Requires> requires;
     Set<Exports> exports;
     Set<Opens> opens;
@@ -165,13 +163,13 @@
         return this;
     }
 
-    Builder automatic(boolean value) {
-        this.automatic = value;
+    Builder synthetic(boolean value) {
+        this.synthetic = value;
         return this;
     }
 
-    Builder synthetic(boolean value) {
-        this.synthetic = value;
+    Builder mandated(boolean value) {
+        this.mandated = value;
         return this;
     }
 
@@ -228,13 +226,10 @@
      *
      * @throws IllegalArgumentException if {@code v} is null or cannot be
      *         parsed as a version string
-     * @throws IllegalStateException if the module version is already set
      *
      * @see Version#parse(String)
      */
     public Builder version(String v) {
-        if (version != null)
-            throw new IllegalStateException("module version already set");
         Version ver = cachedVersion;
         if (ver != null && v.equals(ver.toString())) {
             version = ver;
@@ -246,63 +241,63 @@
 
     /**
      * Sets the module main class.
-     *
-     * @throws IllegalStateException if already set
      */
     public Builder mainClass(String mc) {
-        if (mainClass != null)
-            throw new IllegalStateException("main class already set");
         mainClass = mc;
         return this;
     }
 
     /**
      * Sets the OS name.
-     *
-     * @throws IllegalStateException if already set
      */
     public Builder osName(String name) {
-        if (osName != null)
-            throw new IllegalStateException("OS name already set");
         this.osName = name;
         return this;
     }
 
     /**
      * Sets the OS arch.
-     *
-     * @throws IllegalStateException if already set
      */
     public Builder osArch(String arch) {
-        if (osArch != null)
-            throw new IllegalStateException("OS arch already set");
         this.osArch = arch;
         return this;
     }
 
     /**
      * Sets the OS version.
-     *
-     * @throws IllegalStateException if already set
      */
     public Builder osVersion(String version) {
-        if (osVersion != null)
-            throw new IllegalStateException("OS version already set");
         this.osVersion = version;
         return this;
     }
 
     /**
+     * Returns an immutable set of the module modifiers derived from the flags.
+     */
+    private Set<ModuleDescriptor.Modifier> modifiers() {
+        int n = 0;
+        if (open) n++;
+        if (synthetic) n++;
+        if (mandated) n++;
+        if (n == 0) {
+            return Collections.emptySet();
+        } else {
+            ModuleDescriptor.Modifier[] mods = new ModuleDescriptor.Modifier[n];
+            if (open) mods[--n] = ModuleDescriptor.Modifier.OPEN;
+            if (synthetic) mods[--n] = ModuleDescriptor.Modifier.SYNTHETIC;
+            if (mandated) mods[--n] = ModuleDescriptor.Modifier.MANDATED;
+            return Set.of(mods);
+        }
+    }
+
+    /**
      * Builds a {@code ModuleDescriptor} from the components.
      */
     public ModuleDescriptor build(int hashCode) {
         assert name != null;
-
         return JLMA.newModuleDescriptor(name,
                                         version,
-                                        open,
-                                        automatic,
-                                        synthetic,
+                                        modifiers(),
                                         requires,
                                         exports,
                                         opens,
--- a/jdk/src/java.base/share/classes/jdk/internal/module/Checks.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/jdk/internal/module/Checks.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2009, 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2009, 2017, 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
@@ -26,7 +26,7 @@
 package jdk.internal.module;
 
 /**
- * Utility class for checking module name and binary names.
+ * Utility class for checking module, package, and class names.
  */
 
 public final class Checks {
@@ -58,8 +58,6 @@
             throw new IllegalArgumentException(name + ": Invalid module name"
                     + ": '" + id + "' is not a Java identifier");
         }
-        //if (!Character.isJavaIdentifierStart(last))
-        //    throw new IllegalArgumentException(name + ": Module name ends in digit");
         return name;
     }
 
@@ -77,8 +75,6 @@
         int last = isJavaIdentifier(name, off, name.length() - off);
         if (last == -1)
             return false;
-        //if (!Character.isJavaIdentifierStart(last))
-        //    return false;
         return true;
     }
 
@@ -89,40 +85,62 @@
      *         package name
      */
     public static String requirePackageName(String name) {
-        return requireBinaryName("package name", name);
+        return requireTypeName("package name", name);
     }
 
     /**
-     * Checks a name to ensure that it's a legal type name.
+     * Returns {@code true} if the given name is a legal package name.
+     */
+    public static boolean isPackageName(String name) {
+        return isTypeName(name);
+    }
+
+    /**
+     * Checks a name to ensure that it's a legal qualified class name
      *
      * @throws IllegalArgumentException if name is null or not a legal
-     *         type name
+     *         qualified class name
      */
     public static String requireServiceTypeName(String name) {
-        return requireBinaryName("service type name", name);
+        return requireQualifiedClassName("service type name", name);
     }
 
     /**
-     * Checks a name to ensure that it's a legal type name.
+     * Checks a name to ensure that it's a legal qualified class name.
      *
      * @throws IllegalArgumentException if name is null or not a legal
-     *         type name
+     *         qualified class name
      */
     public static String requireServiceProviderName(String name) {
-        return requireBinaryName("service provider name", name);
+        return requireQualifiedClassName("service provider name", name);
     }
 
     /**
-     * Returns {@code true} if the given name is a legal binary name.
+     * Checks a name to ensure that it's a legal qualified class name in
+     * a named package.
+     *
+     * @throws IllegalArgumentException if name is null or not a legal
+     *         qualified class name in a named package
      */
-    public static boolean isJavaIdentifier(String name) {
-        return isBinaryName(name);
+    public static String requireQualifiedClassName(String what, String name) {
+        requireTypeName(what, name);
+        if (name.indexOf('.') == -1)
+            throw new IllegalArgumentException(name + ": is not a qualified name of"
+                                               + " a Java class in a named package");
+        return name;
     }
 
     /**
-     * Returns {@code true} if the given name is a legal binary name.
+     * Returns {@code true} if the given name is a legal class name.
      */
-    public static boolean isBinaryName(String name) {
+    public static boolean isClassName(String name) {
+        return isTypeName(name);
+    }
+
+    /**
+     * Returns {@code true} if the given name is a legal type name.
+     */
+    private static boolean isTypeName(String name) {
         int next;
         int off = 0;
         while ((next = name.indexOf('.', off)) != -1) {
@@ -135,12 +153,12 @@
     }
 
     /**
-     * Checks if the given name is a legal binary name.
+     * Checks if the given name is a legal type name.
      *
      * @throws IllegalArgumentException if name is null or not a legal
-     *         binary name
+     *         type name
      */
-    public static String requireBinaryName(String what, String name) {
+    private static String requireTypeName(String what, String name) {
         if (name == null)
             throw new IllegalArgumentException("Null " + what);
         int next;
--- a/jdk/src/java.base/share/classes/jdk/internal/module/ClassFileAttributes.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/jdk/internal/module/ClassFileAttributes.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2017, 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
@@ -26,6 +26,7 @@
 package jdk.internal.module;
 
 import java.lang.module.ModuleDescriptor;
+import java.lang.module.ModuleDescriptor.Builder;
 import java.lang.module.ModuleDescriptor.Requires;
 import java.lang.module.ModuleDescriptor.Exports;
 import java.lang.module.ModuleDescriptor.Opens;
@@ -98,14 +99,17 @@
 
             // module_flags
             int module_flags = cr.readUnsignedShort(off);
-            boolean open = ((module_flags & ACC_OPEN) != 0);
-            boolean synthetic = ((module_flags & ACC_SYNTHETIC) != 0);
             off += 2;
 
-            ModuleDescriptor.Builder builder = JLMA.newModuleBuilder(mn,
-                                                                     false,
-                                                                     open,
-                                                                     synthetic);
+            Set<ModuleDescriptor.Modifier> modifiers = new HashSet<>();
+            if ((module_flags & ACC_OPEN) != 0)
+                modifiers.add(ModuleDescriptor.Modifier.OPEN);
+            if ((module_flags & ACC_SYNTHETIC) != 0)
+                modifiers.add(ModuleDescriptor.Modifier.SYNTHETIC);
+            if ((module_flags & ACC_MANDATED) != 0)
+                modifiers.add(ModuleDescriptor.Modifier.MANDATED);
+
+            Builder builder = JLMA.newModuleBuilder(mn, false, modifiers);
 
             // module_version
             String module_version = cr.readUTF8(off, buf);
@@ -142,19 +146,13 @@
                         mods.add(Requires.Modifier.MANDATED);
                 }
 
-
                 // requires_version
-                Version compiledVersion = null;
                 String requires_version = cr.readUTF8(off, buf);
                 off += 2;
-                if (requires_version != null) {
-                    compiledVersion = Version.parse(requires_version);
-                }
-
-                if (compiledVersion == null) {
+                if (requires_version == null) {
                     builder.requires(mods, dn);
                 } else {
-                    builder.requires(mods, dn, compiledVersion);
+                    JLMA.requires(builder, mods, dn, requires_version);
                 }
             }
 
@@ -283,11 +281,14 @@
             attr.putShort(module_name_index);
 
             // module_flags
+            Set<ModuleDescriptor.Modifier> modifiers = descriptor.modifiers();
             int module_flags = 0;
-            if (descriptor.isOpen())
+            if (modifiers.contains(ModuleDescriptor.Modifier.OPEN))
                 module_flags |= ACC_OPEN;
-            if (descriptor.isSynthetic())
+            if (modifiers.contains(ModuleDescriptor.Modifier.SYNTHETIC))
                 module_flags |= ACC_SYNTHETIC;
+            if (modifiers.contains(ModuleDescriptor.Modifier.MANDATED))
+                module_flags |= ACC_MANDATED;
             attr.putShort(module_flags);
 
             // module_version
--- a/jdk/src/java.base/share/classes/jdk/internal/module/ClassFileConstants.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/jdk/internal/module/ClassFileConstants.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2017, 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
@@ -46,8 +46,8 @@
     // access, requires, exports, and opens flags
     public static final int ACC_MODULE        = 0x8000;
     public static final int ACC_OPEN          = 0x0020;
-    public static final int ACC_TRANSITIVE    = 0x0010;
-    public static final int ACC_STATIC_PHASE  = 0x0020;
+    public static final int ACC_TRANSITIVE    = 0x0020;
+    public static final int ACC_STATIC_PHASE  = 0x0040;
     public static final int ACC_SYNTHETIC     = 0x1000;
     public static final int ACC_MANDATED      = 0x8000;
 
--- a/jdk/src/java.base/share/classes/jdk/internal/module/ModuleBootstrap.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/jdk/internal/module/ModuleBootstrap.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2014, 2017, 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
@@ -46,6 +46,7 @@
 import java.util.Optional;
 import java.util.Set;
 import java.util.function.Function;
+import java.util.stream.Stream;
 
 import jdk.internal.loader.BootLoader;
 import jdk.internal.loader.BuiltinClassLoader;
@@ -114,7 +115,12 @@
         long t0 = System.nanoTime();
 
         // system modules (may be patched)
-        ModuleFinder systemModules = ModuleFinder.ofSystem();
+        ModuleFinder systemModules;
+        if (SystemModules.MODULE_NAMES.length > 0) {
+            systemModules = SystemModuleFinder.getInstance();
+        } else {
+            systemModules = ModuleFinder.ofSystem();
+        }
 
         PerfCounters.systemModulesTime.addElapsedTimeFrom(t0);
 
@@ -275,10 +281,10 @@
 
         // run the resolver to create the configuration
         Configuration cf = SharedSecrets.getJavaLangModuleAccess()
-                .resolveRequiresAndUses(finder,
-                                        roots,
-                                        needPostResolutionChecks,
-                                        traceOutput);
+                .resolveAndBind(finder,
+                                roots,
+                                needPostResolutionChecks,
+                                traceOutput);
 
         // time to create configuration
         PerfCounters.resolveTime.addElapsedTimeFrom(t3);
@@ -318,20 +324,20 @@
         // if needed check that there are no split packages in the set of
         // resolved modules for the boot layer
         if (SystemModules.hasSplitPackages() || needPostResolutionChecks) {
-                Map<String, String> packageToModule = new HashMap<>();
-                for (ResolvedModule resolvedModule : cf.modules()) {
-                    ModuleDescriptor descriptor =
-                        resolvedModule.reference().descriptor();
-                    String name = descriptor.name();
-                    for (String p : descriptor.packages()) {
-                        String other = packageToModule.putIfAbsent(p, name);
-                        if (other != null) {
-                            fail("Package " + p + " in both module "
-                                 + name + " and module " + other);
-                        }
+            Map<String, String> packageToModule = new HashMap<>();
+            for (ResolvedModule resolvedModule : cf.modules()) {
+                ModuleDescriptor descriptor =
+                    resolvedModule.reference().descriptor();
+                String name = descriptor.name();
+                for (String p : descriptor.packages()) {
+                    String other = packageToModule.putIfAbsent(p, name);
+                    if (other != null) {
+                        fail("Package " + p + " in both module "
+                             + name + " and module " + other);
                     }
                 }
             }
+        }
 
         long t4 = System.nanoTime();
 
@@ -380,10 +386,9 @@
                                             Set<String> otherMods)
     {
         // resolve all root modules
-        Configuration cf = Configuration.empty()
-                .resolveRequires(finder,
-                                 ModuleFinder.of(),
-                                 roots);
+        Configuration cf = Configuration.empty().resolve(finder,
+                                                         ModuleFinder.of(),
+                                                         roots);
 
         // module name -> reference
         Map<String, ModuleReference> map = new HashMap<>();
@@ -416,7 +421,7 @@
 
     /**
      * Creates a finder from the module path that is the value of the given
-     * system property.
+     * system property and optionally patched by --patch-module
      */
     private static ModuleFinder createModulePathFinder(String prop) {
         String s = System.getProperty(prop);
@@ -429,7 +434,7 @@
             for (String dir: dirs) {
                 paths[i++] = Paths.get(dir);
             }
-            return ModuleFinder.of(paths);
+            return ModulePath.of(patcher, paths);
         }
     }
 
@@ -528,6 +533,7 @@
         if (!extraOpens.isEmpty()) {
             addExtraExportsOrOpens(bootLayer, extraOpens, true);
         }
+
     }
 
     private static void addExtraExportsOrOpens(Layer bootLayer,
--- a/jdk/src/java.base/share/classes/jdk/internal/module/ModuleInfo.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/jdk/internal/module/ModuleInfo.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2014, 2017, 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
@@ -37,7 +37,6 @@
 import java.lang.module.ModuleDescriptor.Requires;
 import java.lang.module.ModuleDescriptor.Exports;
 import java.lang.module.ModuleDescriptor.Opens;
-import java.lang.module.ModuleDescriptor.Version;
 import java.nio.ByteBuffer;
 import java.nio.BufferUnderflowException;
 import java.util.ArrayList;
@@ -51,7 +50,6 @@
 
 import jdk.internal.misc.JavaLangModuleAccess;
 import jdk.internal.misc.SharedSecrets;
-import jdk.internal.module.ModuleResolution;
 
 import static jdk.internal.module.ClassFileConstants.*;
 
@@ -221,7 +219,7 @@
         Set<String> attributes = new HashSet<>();
 
         Builder builder = null;
-        Set<String> packages = null;
+        Set<String> allPackages = null;
         String mainClass = null;
         String[] osValues = null;
         ModuleHashes hashes = null;
@@ -245,7 +243,7 @@
                     break;
 
                 case MODULE_PACKAGES :
-                    packages = readModulePackagesAttribute(in, cpool);
+                    allPackages = readModulePackagesAttribute(in, cpool);
                     break;
 
                 case MODULE_MAIN_CLASS :
@@ -284,51 +282,44 @@
             throw invalidModuleDescriptor(MODULE + " attribute not found");
         }
 
+        // ModuleMainClass and ModuleTarget attributes
+        if (mainClass != null) {
+            builder.mainClass(mainClass);
+        }
+        if (osValues != null) {
+            if (osValues[0] != null) builder.osName(osValues[0]);
+            if (osValues[1] != null) builder.osArch(osValues[1]);
+            if (osValues[2] != null) builder.osVersion(osValues[2]);
+        }
+
         // If the ModulePackages attribute is not present then the packageFinder
         // is used to find the set of packages
         boolean usedPackageFinder = false;
-        if (packages == null && packageFinder != null) {
+        if (allPackages == null && packageFinder != null) {
             try {
-                packages = new HashSet<>(packageFinder.get());
+                allPackages = packageFinder.get();
             } catch (UncheckedIOException x) {
                 throw x.getCause();
             }
             usedPackageFinder = true;
         }
-        if (packages != null) {
-            Set<String> exportedPackages = JLMA.exportedPackages(builder);
-            Set<String> openPackages = JLMA.openPackages(builder);
-            if (packages.containsAll(exportedPackages)
-                    && packages.containsAll(openPackages)) {
-                packages.removeAll(exportedPackages);
-                packages.removeAll(openPackages);
-            } else {
-                // the set of packages is not complete
-                Set<String> exportedAndOpenPackages = new HashSet<>();
-                exportedAndOpenPackages.addAll(exportedPackages);
-                exportedAndOpenPackages.addAll(openPackages);
-                for (String pn : exportedAndOpenPackages) {
-                    if (!packages.contains(pn)) {
-                        String tail;
-                        if (usedPackageFinder) {
-                            tail = " not found by package finder";
-                        } else {
-                            tail = " missing from ModulePackages attribute";
-                        }
-                        throw invalidModuleDescriptor("Package " + pn + tail);
-                    }
+        if (allPackages != null) {
+            Set<String> knownPackages = JLMA.packages(builder);
+            if (!allPackages.containsAll(knownPackages)) {
+                Set<String> missingPackages = new HashSet<>(knownPackages);
+                missingPackages.removeAll(allPackages);
+                assert !missingPackages.isEmpty();
+                String missingPackage = missingPackages.iterator().next();
+                String tail;
+                if (usedPackageFinder) {
+                    tail = " not found in module";
+                } else {
+                    tail = " missing from ModulePackages class file attribute";
                 }
-                assert false; // should not get here
-            }
-            builder.contains(packages);
-        }
+                throw invalidModuleDescriptor("Package " + missingPackage + tail);
 
-        if (mainClass != null)
-            builder.mainClass(mainClass);
-        if (osValues != null) {
-            if (osValues[0] != null) builder.osName(osValues[0]);
-            if (osValues[1] != null) builder.osArch(osValues[1]);
-            if (osValues[2] != null) builder.osVersion(osValues[2]);
+            }
+            builder.packages(allPackages);
         }
 
         ModuleDescriptor descriptor = builder.build();
@@ -347,10 +338,17 @@
         String mn = cpool.getModuleName(module_name_index);
 
         int module_flags = in.readUnsignedShort();
+
+        Set<ModuleDescriptor.Modifier> modifiers = new HashSet<>();
         boolean open = ((module_flags & ACC_OPEN) != 0);
-        boolean synthetic = ((module_flags & ACC_SYNTHETIC) != 0);
+        if (open)
+            modifiers.add(ModuleDescriptor.Modifier.OPEN);
+        if ((module_flags & ACC_SYNTHETIC) != 0)
+            modifiers.add(ModuleDescriptor.Modifier.SYNTHETIC);
+        if ((module_flags & ACC_MANDATED) != 0)
+            modifiers.add(ModuleDescriptor.Modifier.MANDATED);
 
-        Builder builder = JLMA.newModuleBuilder(mn, false, open, synthetic);
+        Builder builder = JLMA.newModuleBuilder(mn, false, modifiers);
 
         int module_version_index = in.readUnsignedShort();
         if (module_version_index != 0) {
@@ -381,16 +379,11 @@
             }
 
             int requires_version_index = in.readUnsignedShort();
-            Version compiledVersion = null;
-            if (requires_version_index != 0) {
-                String vs = cpool.getUtf8(requires_version_index);
-                compiledVersion = Version.parse(vs);
-            }
-
-            if (compiledVersion == null) {
+            if (requires_version_index == 0) {
                 builder.requires(mods, dn);
             } else {
-                builder.requires(mods, dn, compiledVersion);
+                String vs = cpool.getUtf8(requires_version_index);
+                JLMA.requires(builder, mods, dn, vs);
             }
 
             if (dn.equals("java.base"))
@@ -629,10 +622,7 @@
 
     /**
      * Return true if the given attribute name is the name of a pre-defined
-     * attribute that is not allowed in the class file.
-     *
-     * Except for Module, InnerClasses, SourceFile, SourceDebugExtension, and
-     * Deprecated, none of the pre-defined attributes in JVMS 4.7 may appear.
+     * attribute in JVMS 4.7 that is not allowed in a module-info class.
      */
     private static boolean isAttributeDisallowed(String name) {
         Set<String> notAllowed = predefinedNotAllowed;
@@ -640,6 +630,7 @@
             notAllowed = Set.of(
                     "ConstantValue",
                     "Code",
+                    "Deprecated",
                     "StackMapTable",
                     "Exceptions",
                     "EnclosingMethod",
--- a/jdk/src/java.base/share/classes/jdk/internal/module/ModuleInfoExtender.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/jdk/internal/module/ModuleInfoExtender.java	Wed Jul 05 22:52:01 2017 +0200
@@ -56,7 +56,7 @@
     // the packages in the ModulePackages attribute
     private Set<String> packages;
 
-    // the value of the module_version in Module attribute
+    // the value for the module version in the Module attribute
     private Version version;
 
     // the value of the ModuleMainClass attribute
@@ -78,7 +78,11 @@
     }
 
     /**
-     * Sets the set of packages for the ModulePackages attribute
+     * Sets the packages for the ModulePackages attribute
+     *
+     * @apiNote This method does not check that the package names are legal
+     * package names or that the set of packages is a super set of the
+     * packages in the module.
      */
     public ModuleInfoExtender packages(Set<String> packages) {
         this.packages = Collections.unmodifiableSet(packages);
@@ -86,7 +90,7 @@
     }
 
     /**
-     * Sets the value of the module_version in Module attribute.
+     * Sets the value for the module version in the Module attribute
      */
     public ModuleInfoExtender version(Version version) {
         this.version = version;
@@ -95,6 +99,9 @@
 
     /**
      * Sets the value of the ModuleMainClass attribute.
+     *
+     * @apiNote This method does not check that the main class is a legal
+     * class name in a named package.
      */
     public ModuleInfoExtender mainClass(String mainClass) {
         this.mainClass = mainClass;
@@ -133,7 +140,7 @@
 
     /**
      * A ClassVisitor that supports adding class file attributes. If an
-     * attribute already exists then the first occurence of the attribute
+     * attribute already exists then the first occurrence of the attribute
      * is replaced.
      */
     private static class AttributeAddingClassVisitor extends ClassVisitor {
--- a/jdk/src/java.base/share/classes/jdk/internal/module/ModuleLoaderMap.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/jdk/internal/module/ModuleLoaderMap.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2017, 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
@@ -41,13 +41,6 @@
  * are generated at build time.
  */
 final class ModuleLoaderMap {
-    /*
-     * The list of boot modules and platform modules are generated at build time.
-     */
-    private static final String[] BOOT_MODULES
-        = new String[] { "@@BOOT_MODULE_NAMES@@" };
-    private static final String[] PLATFORM_MODULES
-        = new String[] { "@@PLATFORM_MODULE_NAMES@@" };
 
     /**
      * Returns the function to map modules in the given configuration to the
@@ -55,6 +48,10 @@
      */
     static Function<String, ClassLoader> mappingFunction(Configuration cf) {
 
+        // The list of boot modules and platform modules are generated at build time.
+        final String[] BOOT_MODULES = new String[] { "@@BOOT_MODULE_NAMES@@" };
+        final String[] PLATFORM_MODULES = new String[] { "@@PLATFORM_MODULE_NAMES@@" };
+
         Set<String> bootModules = new HashSet<>(BOOT_MODULES.length);
         for (String mn : BOOT_MODULES) {
             bootModules.add(mn);
--- a/jdk/src/java.base/share/classes/jdk/internal/module/ModulePatcher.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/jdk/internal/module/ModulePatcher.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2017, 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
@@ -31,6 +31,7 @@
 import java.io.InputStream;
 import java.io.UncheckedIOException;
 import java.lang.module.ModuleDescriptor;
+import java.lang.module.ModuleDescriptor.Builder;
 import java.lang.module.ModuleReader;
 import java.lang.module.ModuleReference;
 import java.net.MalformedURLException;
@@ -54,6 +55,7 @@
 import java.util.stream.Stream;
 
 import jdk.internal.loader.Resource;
+import jdk.internal.loader.ResourceHelper;
 import jdk.internal.misc.JavaLangModuleAccess;
 import jdk.internal.misc.SharedSecrets;
 import sun.net.www.ParseUtil;
@@ -108,8 +110,11 @@
         if (paths == null)
             return mref;
 
-        // scan the JAR file or directory tree to get the set of packages
+        // Scan the JAR file or directory tree to get the set of packages.
+        // For automatic modules then packages that do not contain class files
+        // must be ignored.
         Set<String> packages = new HashSet<>();
+        boolean isAutomatic = descriptor.isAutomatic();
         try {
             for (Path file : paths) {
                 if (Files.isRegularFile(file)) {
@@ -118,8 +123,10 @@
                     // is not supported by the boot class loader
                     try (JarFile jf = new JarFile(file.toFile())) {
                         jf.stream()
+                          .filter(e -> !e.isDirectory()
+                                  && (!isAutomatic || e.getName().endsWith(".class")))
                           .map(e -> toPackageName(file, e))
-                          .filter(Checks::isJavaIdentifier)
+                          .filter(Checks::isPackageName)
                           .forEach(packages::add);
                     }
 
@@ -129,8 +136,10 @@
                     Path top = file;
                     Files.find(top, Integer.MAX_VALUE,
                                ((path, attrs) -> attrs.isRegularFile()))
+                            .filter(path -> !isAutomatic
+                                    || path.toString().endsWith(".class"))
                             .map(path -> toPackageName(top, path))
-                            .filter(Checks::isJavaIdentifier)
+                            .filter(Checks::isPackageName)
                             .forEach(packages::add);
 
                 }
@@ -141,10 +150,30 @@
         }
 
         // if there are new packages then we need a new ModuleDescriptor
-        Set<String> original = descriptor.packages();
-        packages.addAll(original);
-        if (packages.size() > original.size()) {
-            descriptor = JLMA.newModuleDescriptor(descriptor, packages);
+        packages.removeAll(descriptor.packages());
+        if (!packages.isEmpty()) {
+            Builder builder = JLMA.newModuleBuilder(descriptor.name(),
+                                                    /*strict*/ false,
+                                                    descriptor.modifiers());
+            if (!descriptor.isAutomatic()) {
+                descriptor.requires().forEach(builder::requires);
+                descriptor.exports().forEach(builder::exports);
+                descriptor.opens().forEach(builder::opens);
+                descriptor.uses().forEach(builder::uses);
+            }
+            descriptor.provides().forEach(builder::provides);
+
+            descriptor.version().ifPresent(builder::version);
+            descriptor.mainClass().ifPresent(builder::mainClass);
+            descriptor.osName().ifPresent(builder::osName);
+            descriptor.osArch().ifPresent(builder::osArch);
+            descriptor.osVersion().ifPresent(builder::osVersion);
+
+            // original + new packages
+            builder.packages(descriptor.packages());
+            builder.packages(packages);
+
+            descriptor = builder.build();
         }
 
         // return a module reference to the patched module
@@ -471,23 +500,14 @@
 
         @Override
         public Resource find(String name) throws IOException {
-            Path file = Paths.get(name.replace('/', File.separatorChar));
-            if (file.getRoot() == null) {
-                file = dir.resolve(file);
-            } else {
-                // drop the root component so that the resource is
-                // located relative to the module directory
-                int n = file.getNameCount();
-                if (n == 0)
-                    return null;
-                file = dir.resolve(file.subpath(0, n));
+            Path path = ResourceHelper.toFilePath(name);
+            if (path != null) {
+                Path file = dir.resolve(path);
+                if (Files.isRegularFile(file)) {
+                    return newResource(name, dir, file);
+                }
             }
-
-            if (Files.isRegularFile(file)) {
-                return newResource(name, dir, file);
-            } else {
-                return null;
-            }
+            return null;
         }
 
         private Resource newResource(String name, Path top, Path file) {
--- a/jdk/src/java.base/share/classes/jdk/internal/module/ModulePath.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/jdk/internal/module/ModulePath.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2014, 2017, 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
@@ -35,7 +35,6 @@
 import java.lang.module.FindException;
 import java.lang.module.InvalidModuleDescriptorException;
 import java.lang.module.ModuleDescriptor;
-import java.lang.module.ModuleDescriptor.Requires;
 import java.lang.module.ModuleFinder;
 import java.lang.module.ModuleReference;
 import java.net.URI;
@@ -70,12 +69,11 @@
 
 /**
  * A {@code ModuleFinder} that locates modules on the file system by searching
- * a sequence of directories or packaged modules.
- *
- * The {@code ModuleFinder} can be created to work in either the run-time
- * or link-time phases. In both cases it locates modular JAR and exploded
- * modules. When created for link-time then it additionally locates
- * modules in JMOD files.
+ * a sequence of directories or packaged modules. The ModuleFinder can be
+ * created to work in either the run-time or link-time phases. In both cases it
+ * locates modular JAR and exploded modules. When created for link-time then it
+ * additionally locates modules in JMOD files. The ModuleFinder can also
+ * optionally patch any modules that it locates with a ModulePatcher.
  */
 
 public class ModulePath implements ModuleFinder {
@@ -87,6 +85,9 @@
     // true for the link phase (supports modules packaged in JMOD format)
     private final boolean isLinkPhase;
 
+    // for patching modules, can be null
+    private final ModulePatcher patcher;
+
     // the entries on this module path
     private final Path[] entries;
     private int next;
@@ -94,19 +95,51 @@
     // map of module name to module reference map for modules already located
     private final Map<String, ModuleReference> cachedModules = new HashMap<>();
 
-    public ModulePath(Runtime.Version version, boolean isLinkPhase, Path... entries) {
+
+    private ModulePath(Runtime.Version version,
+                       boolean isLinkPhase,
+                       ModulePatcher patcher,
+                       Path... entries) {
         this.releaseVersion = version;
         this.isLinkPhase = isLinkPhase;
+        this.patcher = patcher;
         this.entries = entries.clone();
         for (Path entry : this.entries) {
             Objects.requireNonNull(entry);
         }
     }
 
-    public ModulePath(Path... entries) {
-        this(JarFile.runtimeVersion(), false, entries);
+    /**
+     * Returns a ModuleFinder that that locates modules on the file system by
+     * searching a sequence of directories and/or packaged modules. The modules
+     * may be patched by the given ModulePatcher.
+     */
+    public static ModuleFinder of(ModulePatcher patcher, Path... entries) {
+        return new ModulePath(JarFile.runtimeVersion(), false, patcher, entries);
     }
 
+    /**
+     * Returns a ModuleFinder that that locates modules on the file system by
+     * searching a sequence of directories and/or packaged modules.
+     */
+    public static ModuleFinder of(Path... entries) {
+        return of((ModulePatcher)null, entries);
+    }
+
+    /**
+     * Returns a ModuleFinder that that locates modules on the file system by
+     * searching a sequence of directories and/or packaged modules.
+     *
+     * @param version The release version to use for multi-release JAR files
+     * @param isLinkPhase {@code true} if the link phase to locate JMOD files
+     */
+    public static ModuleFinder of(Runtime.Version version,
+                                  boolean isLinkPhase,
+                                  Path... entries) {
+        return new ModulePath(version, isLinkPhase, null, entries);
+    }
+
+
     @Override
     public Optional<ModuleReference> find(String name) {
         Objects.requireNonNull(name);
@@ -195,8 +228,7 @@
             if (attrs.isDirectory()) {
                 Path mi = entry.resolve(MODULE_INFO);
                 if (!Files.exists(mi)) {
-                    // does not exist or unable to determine so assume a
-                    // directory of modules
+                    // assume a directory of modules
                     return scanDirectory(entry);
                 }
             }
@@ -206,10 +238,16 @@
             if (mref != null) {
                 String name = mref.descriptor().name();
                 return Collections.singletonMap(name, mref);
+            }
+
+            // not recognized
+            String msg;
+            if (!isLinkPhase && entry.toString().endsWith(".jmod")) {
+                msg = "JMOD format not supported at execution time";
             } else {
-                // skipped
-                return Collections.emptyMap();
+                msg = "Module format not recognized";
             }
+            throw new FindException(msg + ": " + entry);
 
         } catch (IOException ioe) {
             throw new FindException(ioe);
@@ -266,14 +304,11 @@
 
 
     /**
-     * Locates a packaged or exploded module, returning a {@code ModuleReference}
-     * to the module. Returns {@code null} if the entry is skipped because it is
-     * to a directory that does not contain a module-info.class or it's a hidden
-     * file.
+     * Reads a packaged or exploded module, returning a {@code ModuleReference}
+     * to the module. Returns {@code null} if the entry is not recognized.
      *
      * @throws IOException if an I/O error occurs
-     * @throws FindException if the file is not recognized as a module or an
-     *         error occurs parsing its module descriptor
+     * @throws FindException if an error occurs parsing its module descriptor
      */
     private ModuleReference readModule(Path entry, BasicFileAttributes attrs)
         throws IOException
@@ -282,24 +317,16 @@
 
             if (attrs.isDirectory()) {
                 return readExplodedModule(entry); // may return null
-            }
-
-            String fn = entry.getFileName().toString();
-            if (attrs.isRegularFile()) {
-                if (fn.endsWith(".jar")) {
-                    return readJar(entry);
-                } else if (fn.endsWith(".jmod")) {
-                    if (isLinkPhase)
+            } else {
+                String fn = entry.getFileName().toString();
+                if (attrs.isRegularFile()) {
+                    if (fn.endsWith(".jar")) {
+                        return readJar(entry);
+                    } else if (isLinkPhase && fn.endsWith(".jmod")) {
                         return readJMod(entry);
-                    throw new FindException("JMOD files not supported: " + entry);
+                    }
                 }
-            }
-
-            // skip hidden files
-            if (fn.startsWith(".") || Files.isHidden(entry)) {
                 return null;
-            } else {
-                throw new FindException("Unrecognized module: " + entry);
             }
 
         } catch (InvalidModuleDescriptorException e) {
@@ -327,7 +354,7 @@
         }
     }
 
-    // -- jmod files --
+    // -- JMOD files --
 
     private Set<String> jmodPackages(JmodFile jf) {
         return jf.stream()
@@ -339,7 +366,7 @@
     }
 
     /**
-     * Returns a {@code ModuleReference} to a module in jmod file on the
+     * Returns a {@code ModuleReference} to a module in JMOD file on the
      * file system.
      *
      * @throws IOException
@@ -362,7 +389,7 @@
 
     /**
      * Returns the service type corresponding to the name of a services
-     * configuration file if it is a valid Java identifier.
+     * configuration file if it is a legal type name.
      *
      * For example, if called with "META-INF/services/p.S" then this method
      * returns a container with the value "p.S".
@@ -374,7 +401,7 @@
             String prefix = cf.substring(0, index);
             if (prefix.equals(SERVICES_PREFIX)) {
                 String sn = cf.substring(index);
-                if (Checks.isJavaIdentifier(sn))
+                if (Checks.isClassName(sn))
                     return Optional.of(sn);
             }
         }
@@ -403,11 +430,10 @@
      *
      * 1. The module name (and optionally the version) is derived from the file
      *    name of the JAR file
-     * 2. All packages are exported and open
-     * 3. It has no non-exported/non-open packages
-     * 4. The contents of any META-INF/services configuration files are mapped
+     * 2. All packages are derived from the .class files in the JAR file
+     * 3. The contents of any META-INF/services configuration files are mapped
      *    to "provides" declarations
-     * 5. The Main-Class attribute in the main attributes of the JAR manifest
+     * 4. The Main-Class attribute in the main attributes of the JAR manifest
      *    is mapped to the module descriptor mainClass
      */
     private ModuleDescriptor deriveModuleDescriptor(JarFile jf)
@@ -443,9 +469,7 @@
         mn = cleanModuleName(mn);
 
         // Builder throws IAE if module name is empty or invalid
-        ModuleDescriptor.Builder builder
-            = ModuleDescriptor.automaticModule(mn)
-                .requires(Set.of(Requires.Modifier.MANDATED), "java.base");
+        ModuleDescriptor.Builder builder = ModuleDescriptor.newAutomaticModule(mn);
         if (vs != null)
             builder.version(vs);
 
@@ -453,17 +477,22 @@
         Map<Boolean, Set<String>> map = VersionedStream.stream(jf)
                 .filter(e -> !e.isDirectory())
                 .map(JarEntry::getName)
+                .filter(e -> (e.endsWith(".class") ^ e.startsWith(SERVICES_PREFIX)))
                 .collect(Collectors.partitioningBy(e -> e.startsWith(SERVICES_PREFIX),
                                                    Collectors.toSet()));
 
-        Set<String> resources = map.get(Boolean.FALSE);
+        Set<String> classFiles = map.get(Boolean.FALSE);
         Set<String> configFiles = map.get(Boolean.TRUE);
-        // all packages are exported and open
-        resources.stream()
+
+        // the packages containing class files
+        Set<String> packages = classFiles.stream()
                 .map(this::toPackageName)
                 .flatMap(Optional::stream)
                 .distinct()
-                .forEach(pn -> builder.exports(pn).opens(pn));
+                .collect(Collectors.toSet());
+
+        // all packages are exported and open
+        builder.packages(packages);
 
         // map names of service configuration files to service names
         Set<String> serviceNames = configFiles.stream()
@@ -481,6 +510,11 @@
                 String cn;
                 while ((cn = nextLine(reader)) != null) {
                     if (cn.length() > 0) {
+                        String pn = packageName(cn);
+                        if (!packages.contains(pn)) {
+                            String msg = "Provider class " + cn + " not in module";
+                            throw new IOException(msg);
+                        }
                         providerClasses.add(cn);
                     }
                 }
@@ -494,8 +528,15 @@
         if (man != null) {
             Attributes attrs = man.getMainAttributes();
             String mainClass = attrs.getValue(Attributes.Name.MAIN_CLASS);
-            if (mainClass != null)
-                builder.mainClass(mainClass.replace("/", "."));
+            if (mainClass != null) {
+                mainClass = mainClass.replace("/", ".");
+                String pn = packageName(mainClass);
+                if (!packages.contains(pn)) {
+                    String msg = "Main-Class " + mainClass + " not in module";
+                    throw new IOException(msg);
+                }
+                builder.mainClass(mainClass);
+            }
         }
 
         return builder.build();
@@ -569,10 +610,10 @@
                 try {
                     ModuleDescriptor md = deriveModuleDescriptor(jf);
                     attrs = new ModuleInfo.Attributes(md, null, null);
-                } catch (IllegalArgumentException iae) {
+                } catch (IllegalArgumentException e) {
                     throw new FindException(
                         "Unable to derive module descriptor for: "
-                        + jf.getName(), iae);
+                        + jf.getName(), e);
                 }
 
             } else {
@@ -580,7 +621,7 @@
                                         () -> jarPackages(jf));
             }
 
-            return ModuleReferences.newJarModule(attrs, file);
+            return ModuleReferences.newJarModule(attrs, patcher, file);
         }
     }
 
@@ -617,7 +658,15 @@
             // for now
             return null;
         }
-        return ModuleReferences.newExplodedModule(attrs, dir);
+        return ModuleReferences.newExplodedModule(attrs, patcher, dir);
+    }
+
+    /**
+     * Maps a type name to its package name.
+     */
+    private static String packageName(String cn) {
+        int index = cn.lastIndexOf('.');
+        return (index == -1) ? "" : cn.substring(0, index);
     }
 
     /**
@@ -629,19 +678,18 @@
      */
     private Optional<String> toPackageName(String name) {
         assert !name.endsWith("/");
-
         int index = name.lastIndexOf("/");
         if (index == -1) {
             if (name.endsWith(".class") && !name.equals(MODULE_INFO)) {
                 throw new IllegalArgumentException(name
-                        + " found in top-level directory:"
+                        + " found in top-level directory"
                         + " (unnamed package not allowed in module)");
             }
             return Optional.empty();
         }
 
         String pn = name.substring(0, index).replace('/', '.');
-        if (Checks.isJavaIdentifier(pn)) {
+        if (Checks.isPackageName(pn)) {
             return Optional.of(pn);
         } else {
             // not a valid package name
@@ -654,7 +702,7 @@
      * name.
      *
      * @throws IllegalArgumentException if the name is a class file in
-     *         the top-level directory (and it's not module-info.class)
+     *          the top-level directory (and it's not module-info.class)
      */
     private Optional<String> toPackageName(Path file) {
         assert file.getRoot() == null;
@@ -664,14 +712,14 @@
             String name = file.toString();
             if (name.endsWith(".class") && !name.equals(MODULE_INFO)) {
                 throw new IllegalArgumentException(name
-                        + " found in in top-level directory"
+                        + " found in top-level directory"
                         + " (unnamed package not allowed in module)");
             }
             return Optional.empty();
         }
 
         String pn = parent.toString().replace(File.separatorChar, '.');
-        if (Checks.isJavaIdentifier(pn)) {
+        if (Checks.isPackageName(pn)) {
             return Optional.of(pn);
         } else {
             // not a valid package name
--- a/jdk/src/java.base/share/classes/jdk/internal/module/ModuleReferenceImpl.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/jdk/internal/module/ModuleReferenceImpl.java	Wed Jul 05 22:52:01 2017 +0200
@@ -163,7 +163,14 @@
 
     @Override
     public String toString() {
-        return super.toString();
+        StringBuilder sb = new StringBuilder();
+        sb.append("[module ");
+        sb.append(descriptor().name());
+        sb.append(", location=");
+        sb.append(location().orElseThrow(() -> new InternalError()));
+        if (isPatched()) sb.append(" (patched)");
+        sb.append("]");
+        return sb.toString();
     }
 
 }
--- a/jdk/src/java.base/share/classes/jdk/internal/module/ModuleReferences.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/jdk/internal/module/ModuleReferences.java	Wed Jul 05 22:52:01 2017 +0200
@@ -36,7 +36,6 @@
 import java.nio.ByteBuffer;
 import java.nio.file.Files;
 import java.nio.file.Path;
-import java.nio.file.Paths;
 import java.util.List;
 import java.util.Objects;
 import java.util.Optional;
@@ -51,7 +50,7 @@
 import java.util.zip.ZipFile;
 
 import jdk.internal.jmod.JmodFile;
-import jdk.internal.misc.JavaLangAccess;
+import jdk.internal.loader.ResourceHelper;
 import jdk.internal.misc.SharedSecrets;
 import jdk.internal.module.ModuleHashes.HashSupplier;
 import jdk.internal.util.jar.VersionedStream;
@@ -65,20 +64,16 @@
  */
 
 class ModuleReferences {
-
-    private static final JavaLangAccess JLA = SharedSecrets.getJavaLangAccess();
-
     private ModuleReferences() { }
 
     /**
-     * Creates a ModuleReference to a module or to patched module when
-     * creating modules for the boot Layer and --patch-module is specified.
+     * Creates a ModuleReference to a possibly-patched module
      */
     private static ModuleReference newModule(ModuleInfo.Attributes attrs,
                                              URI uri,
                                              Supplier<ModuleReader> supplier,
+                                             ModulePatcher patcher,
                                              HashSupplier hasher) {
-
         ModuleReference mref = new ModuleReferenceImpl(attrs.descriptor(),
                                                        uri,
                                                        supplier,
@@ -86,38 +81,42 @@
                                                        attrs.recordedHashes(),
                                                        hasher,
                                                        attrs.moduleResolution());
-        if (JLA.getBootLayer() == null)
-            mref = ModuleBootstrap.patcher().patchIfNeeded(mref);
+        if (patcher != null)
+            mref = patcher.patchIfNeeded(mref);
 
         return mref;
     }
 
     /**
-     * Creates a ModuleReference to a module packaged as a modular JAR.
+     * Creates a ModuleReference to a possibly-patched module in a modular JAR.
      */
-    static ModuleReference newJarModule(ModuleInfo.Attributes attrs, Path file) {
+    static ModuleReference newJarModule(ModuleInfo.Attributes attrs,
+                                        ModulePatcher patcher,
+                                        Path file) {
         URI uri = file.toUri();
         Supplier<ModuleReader> supplier = () -> new JarModuleReader(file, uri);
         HashSupplier hasher = (a) -> ModuleHashes.computeHash(file, a);
-        return newModule(attrs, uri, supplier, hasher);
+        return newModule(attrs, uri, supplier, patcher, hasher);
     }
 
     /**
-     * Creates a ModuleReference to a module packaged as a JMOD.
+     * Creates a ModuleReference to a module in a JMOD file.
      */
     static ModuleReference newJModModule(ModuleInfo.Attributes attrs, Path file) {
         URI uri = file.toUri();
         Supplier<ModuleReader> supplier = () -> new JModModuleReader(file, uri);
         HashSupplier hasher = (a) -> ModuleHashes.computeHash(file, a);
-        return newModule(attrs, uri, supplier, hasher);
+        return newModule(attrs, uri, supplier, null, hasher);
     }
 
     /**
-     * Creates a ModuleReference to an exploded module.
+     * Creates a ModuleReference to a possibly-patched exploded module.
      */
-    static ModuleReference newExplodedModule(ModuleInfo.Attributes attrs, Path dir) {
+    static ModuleReference newExplodedModule(ModuleInfo.Attributes attrs,
+                                             ModulePatcher patcher,
+                                             Path dir) {
         Supplier<ModuleReader> supplier = () -> new ExplodedModuleReader(dir);
-        return newModule(attrs, dir.toUri(), supplier, null);
+        return newModule(attrs, dir.toUri(), supplier, patcher, null);
     }
 
 
@@ -243,7 +242,8 @@
         }
 
         private JarEntry getEntry(String name) {
-            return jf.getJarEntry(Objects.requireNonNull(name));
+            JarEntry entry = jf.getJarEntry(Objects.requireNonNull(name));
+            return (entry == null || entry.isDirectory()) ? null : entry;
         }
 
         @Override
@@ -370,32 +370,33 @@
         }
 
         /**
-         * Returns a Path to access to the given resource.
-         */
-        private Path toPath(String name) {
-            Path path = Paths.get(name.replace('/', File.separatorChar));
-            if (path.getRoot() == null) {
-                return dir.resolve(path);
-            } else {
-                // drop the root component so that the resource is
-                // located relative to the module directory
-                int n = path.getNameCount();
-                return (n > 0) ? dir.resolve(path.subpath(0, n)) : null;
-            }
-        }
-
-        /**
          * Throws IOException if the module reader is closed;
          */
         private void ensureOpen() throws IOException {
             if (closed) throw new IOException("ModuleReader is closed");
         }
 
+        /**
+         * Returns a Path to access the given resource. Returns null if the
+         * resource name does not convert to a file path that locates a regular
+         * file in the module.
+         */
+        private Path toFilePath(String name) {
+            Path path = ResourceHelper.toFilePath(name);
+            if (path != null) {
+                Path file = dir.resolve(path);
+                if (Files.isRegularFile(file)) {
+                    return file;
+                }
+            }
+            return null;
+        }
+
         @Override
         public Optional<URI> find(String name) throws IOException {
             ensureOpen();
-            Path path = toPath(name);
-            if (path != null && Files.isRegularFile(path)) {
+            Path path = toFilePath(name);
+            if (path != null) {
                 try {
                     return Optional.of(path.toUri());
                 } catch (IOError e) {
@@ -409,8 +410,8 @@
         @Override
         public Optional<InputStream> open(String name) throws IOException {
             ensureOpen();
-            Path path = toPath(name);
-            if (path != null && Files.isRegularFile(path)) {
+            Path path = toFilePath(name);
+            if (path != null) {
                 return Optional.of(Files.newInputStream(path));
             } else {
                 return Optional.empty();
@@ -420,8 +421,8 @@
         @Override
         public Optional<ByteBuffer> read(String name) throws IOException {
             ensureOpen();
-            Path path = toPath(name);
-            if (path != null && Files.isRegularFile(path)) {
+            Path path = toFilePath(name);
+            if (path != null) {
                 return Optional.of(ByteBuffer.wrap(Files.readAllBytes(path)));
             } else {
                 return Optional.empty();
--- a/jdk/src/java.base/share/classes/jdk/internal/module/Modules.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/jdk/internal/module/Modules.java	Wed Jul 05 22:52:01 2017 +0200
@@ -82,8 +82,8 @@
                                       String name,
                                       Set<String> packages)
     {
-        ModuleDescriptor descriptor = ModuleDescriptor.module(name)
-                .contains(packages)
+        ModuleDescriptor descriptor = ModuleDescriptor.newModule(name)
+                .packages(packages)
                 .build();
 
         return JLRMA.defineModule(loader, descriptor, null);
@@ -185,7 +185,8 @@
     /**
      * Adds a package to a module's content.
      *
-     * This method is a no-op if the module already contains the package.
+     * This method is a no-op if the module already contains the package or the
+     * module is an unnamed module.
      */
     public static void addPackage(Module m, String pn) {
         JLRMA.addPackage(m, pn);
--- a/jdk/src/java.base/share/classes/jdk/internal/module/SystemModuleFinder.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/jdk/internal/module/SystemModuleFinder.java	Wed Jul 05 22:52:01 2017 +0200
@@ -80,8 +80,6 @@
         = PerfCounter.newPerfCounter("jdk.module.finder.jimage.packages");
     private static final PerfCounter exportsCount
         = PerfCounter.newPerfCounter("jdk.module.finder.jimage.exports");
-    // ImageReader used to access all modules in the image
-    private static final ImageReader imageReader;
 
     // singleton finder to find modules in the run-time images
     private static final SystemModuleFinder INSTANCE;
@@ -96,13 +94,28 @@
      */
     static {
         long t0 = System.nanoTime();
-        imageReader = ImageReaderFactory.getImageReader();
 
         INSTANCE = new SystemModuleFinder();
 
         initTime.addElapsedTimeFrom(t0);
     }
 
+    /**
+     * Holder class for the ImageReader
+     */
+    private static class SystemImage {
+        static final ImageReader READER;
+        static {
+            long t0 = System.nanoTime();
+            READER = ImageReaderFactory.getImageReader();
+            initTime.addElapsedTimeFrom(t0);
+        }
+
+        static ImageReader reader() {
+            return READER;
+        }
+    }
+
     private static boolean isFastPathSupported() {
        return SystemModules.MODULE_NAMES.length > 0;
     }
@@ -114,7 +127,7 @@
 
         // this happens when java.base is patched with java.base
         // from an exploded image
-        return imageReader.getModuleNames();
+        return SystemImage.reader().getModuleNames();
     }
 
     // the set of modules in the run-time image
@@ -151,6 +164,7 @@
             descriptors = new ModuleDescriptor[n];
             recordedHashes = new ModuleHashes[n];
             moduleResolutions = new ModuleResolution[n];
+            ImageReader imageReader = SystemImage.reader();
             for (int i = 0; i < names.length; i++) {
                 String mn = names[i];
                 ImageLocation loc = imageReader.findLocation(mn, "module-info.class");
@@ -291,6 +305,7 @@
             Objects.requireNonNull(name);
             if (closed)
                 throw new IOException("ModuleReader is closed");
+            ImageReader imageReader = SystemImage.reader();
             if (imageReader != null) {
                 return imageReader.findLocation(module, name);
             } else {
@@ -330,7 +345,7 @@
         public Optional<ByteBuffer> read(String name) throws IOException {
             ImageLocation location = findImageLocation(name);
             if (location != null) {
-                return Optional.of(imageReader.getResourceBuffer(location));
+                return Optional.of(SystemImage.reader().getResourceBuffer(location));
             } else {
                 return Optional.empty();
             }
@@ -372,7 +387,7 @@
             stack = new ArrayDeque<>();
 
             // push the root node to the stack to get started
-            ImageReader.Node dir = imageReader.findNode(moduleRoot);
+            ImageReader.Node dir = SystemImage.reader().findNode(moduleRoot);
             if (dir == null || !dir.isDirectory())
                 throw new IOException(moduleRoot + " not a directory");
             stack.push(dir);
@@ -390,7 +405,7 @@
                     String name = node.getName();
                     if (node.isDirectory()) {
                         // build node
-                        ImageReader.Node dir = imageReader.findNode(name);
+                        ImageReader.Node dir = SystemImage.reader().findNode(name);
                         assert dir.isDirectory();
                         stack.push(dir);
                     } else {
--- a/jdk/src/java.base/share/classes/jdk/internal/reflect/Reflection.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/jdk/internal/reflect/Reflection.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2001, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2001, 2017, 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
@@ -211,15 +211,7 @@
         if (currentModule == memberModule)
            return true;  // same module (named or unnamed)
 
-        // memberClass may be primitive or array class
-        Class<?> c = memberClass;
-        while (c.isArray()) {
-            c = c.getComponentType();
-        }
-        if (c.isPrimitive())
-            return true;
-
-        String pkg = c.getPackageName();
+        String pkg = memberClass.getPackageName();
         boolean allowed = memberModule.isExported(pkg, currentModule);
         if (allowed && memberModule.isNamed() && printStackTraceWhenAccessSucceeds()) {
             if (!SharedSecrets.getJavaLangReflectModuleAccess()
@@ -237,10 +229,6 @@
     private static boolean isSameClassPackage(Class<?> c1, Class<?> c2) {
         if (c1.getClassLoader() != c2.getClassLoader())
             return false;
-        while (c1.isArray())
-            c1 = c1.getComponentType();
-        while (c2.isArray())
-            c2 = c2.getComponentType();
         return Objects.equals(c1.getPackageName(), c2.getPackageName());
     }
 
@@ -378,12 +366,6 @@
         }
     }
 
-    public static void enableStackTraces() {
-        printStackWhenAccessFails = true;
-        printStackWhenAccessSucceeds = true;
-        printStackPropertiesSet = true;
-    }
-
     public static boolean printStackTraceWhenAccessFails() {
         ensurePrintStackPropertiesSet();
         return printStackWhenAccessFails;
@@ -413,11 +395,7 @@
         if (m2.isNamed())
             memberSuffix = " (in " + m2 + ")";
 
-        Class<?> c = memberClass;
-        while (c.isArray()) {
-            c = c.getComponentType();
-        }
-        String memberPackageName = c.getPackageName();
+        String memberPackageName = memberClass.getPackageName();
 
         String msg = currentClass + currentSuffix + " cannot access ";
         if (m2.isExported(memberPackageName, m1)) {
--- a/jdk/src/java.base/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Defines the foundational APIs of the Java SE Platform.
+ *
+ * @since 9
  */
 module java.base {
 
--- a/jdk/src/java.base/share/classes/sun/invoke/util/VerifyAccess.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/sun/invoke/util/VerifyAccess.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2008, 2017, 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
@@ -39,6 +39,7 @@
 
     private VerifyAccess() { }  // cannot instantiate
 
+    private static final int UNCONDITIONAL_ALLOWED = java.lang.invoke.MethodHandles.Lookup.UNCONDITIONAL;
     private static final int MODULE_ALLOWED = java.lang.invoke.MethodHandles.Lookup.MODULE;
     private static final int PACKAGE_ONLY = 0;
     private static final int PACKAGE_ALLOWED = java.lang.invoke.MethodHandles.Lookup.PACKAGE;
@@ -92,7 +93,7 @@
                                              int      allowedModes) {
         if (allowedModes == 0)  return false;
         assert((allowedModes & PUBLIC) != 0 &&
-               (allowedModes & ~(ALL_ACCESS_MODES|PACKAGE_ALLOWED|MODULE_ALLOWED)) == 0);
+               (allowedModes & ~(ALL_ACCESS_MODES|PACKAGE_ALLOWED|MODULE_ALLOWED|UNCONDITIONAL_ALLOWED)) == 0);
         // The symbolic reference class (refc) must always be fully verified.
         if (!isClassAccessible(refc, lookupClass, allowedModes)) {
             return false;
@@ -173,7 +174,7 @@
                                             int allowedModes) {
         if (allowedModes == 0)  return false;
         assert((allowedModes & PUBLIC) != 0 &&
-               (allowedModes & ~(ALL_ACCESS_MODES|PACKAGE_ALLOWED|MODULE_ALLOWED)) == 0);
+               (allowedModes & ~(ALL_ACCESS_MODES|PACKAGE_ALLOWED|MODULE_ALLOWED|UNCONDITIONAL_ALLOWED)) == 0);
         int mods = getClassModifiers(refc);
         if (isPublic(mods)) {
 
@@ -191,22 +192,17 @@
                 (lookupModule == refModule))
                 return true;
 
-            // check readability
-            if (lookupModule.canRead(refModule)) {
+            // check readability when UNCONDITIONAL not allowed
+            if (((allowedModes & UNCONDITIONAL_ALLOWED) != 0)
+                || lookupModule.canRead(refModule)) {
 
                 // check that refc is in an exported package
-                Class<?> c = refc;
-                while (c.isArray()) {
-                    c = c.getComponentType();
-                }
-                if (c.isPrimitive())
-                    return true;
                 if ((allowedModes & MODULE_ALLOWED) != 0) {
-                    if (refModule.isExported(c.getPackageName(), lookupModule))
+                    if (refModule.isExported(refc.getPackageName(), lookupModule))
                         return true;
                 } else {
                     // exported unconditionally
-                    if (refModule.isExported(c.getPackageName()))
+                    if (refModule.isExported(refc.getPackageName()))
                         return true;
                 }
 
--- a/jdk/src/java.base/share/classes/sun/launcher/LauncherHelper.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/sun/launcher/LauncherHelper.java	Wed Jul 05 22:52:01 2017 +0200
@@ -591,8 +591,8 @@
                 c = Class.forName(m, cn);
             }
         } catch (LinkageError le) {
-            abort(null, "java.launcher.module.error3",
-                    mainClass, m.getName(), le.getLocalizedMessage());
+            abort(null, "java.launcher.module.error3", mainClass, m.getName(),
+                    le.getClass().getName() + ": " + le.getLocalizedMessage());
         }
         if (c == null) {
             abort(null, "java.launcher.module.error2", mainClass, mainModule);
@@ -645,7 +645,8 @@
                 }
             }
         } catch (LinkageError le) {
-            abort(le, "java.launcher.cls.error6", cn, le.getLocalizedMessage());
+            abort(le, "java.launcher.cls.error6", cn,
+                    le.getClass().getName() + ": " + le.getLocalizedMessage());
         }
         return mainClass;
     }
@@ -966,6 +967,10 @@
                     ostream.print("open ");
                 if (md.isAutomatic())
                     ostream.print("automatic ");
+                if (md.modifiers().contains(ModuleDescriptor.Modifier.SYNTHETIC))
+                    ostream.print("synthetic ");
+                if (md.modifiers().contains(ModuleDescriptor.Modifier.MANDATED))
+                    ostream.print("mandated ");
                 ostream.println("module " + midAndLocation(md, mref.location()));
 
                 // unqualified exports (sorted by package)
--- a/jdk/src/java.base/share/classes/sun/net/www/protocol/jrt/JavaRuntimeURLConnection.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/sun/net/www/protocol/jrt/JavaRuntimeURLConnection.java	Wed Jul 05 22:52:01 2017 +0200
@@ -32,7 +32,9 @@
 import java.io.InputStream;
 import java.net.MalformedURLException;
 import java.net.URL;
+import java.security.AccessController;
 import java.security.Permission;
+import java.security.PrivilegedAction;
 
 import jdk.internal.jimage.ImageLocation;
 import jdk.internal.jimage.ImageReader;
@@ -51,7 +53,11 @@
 public class JavaRuntimeURLConnection extends URLConnection {
 
     // ImageReader to access resources in jimage
-    private static final ImageReader reader = ImageReaderFactory.getImageReader();
+    private static final ImageReader reader;
+    static {
+        PrivilegedAction<ImageReader> pa = ImageReaderFactory::getImageReader;
+        reader = AccessController.doPrivileged(pa);
+    }
 
     // the module and resource name in the URL
     private final String module;
--- a/jdk/src/java.base/share/classes/sun/security/pkcs/SignerInfo.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/sun/security/pkcs/SignerInfo.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1996, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1996, 2017, 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
@@ -37,6 +37,7 @@
 import java.security.Signature;
 import java.security.SignatureException;
 import java.security.Timestamp;
+import java.security.cert.CertPathValidatorException;
 import java.security.cert.CertificateException;
 import java.security.cert.CertificateFactory;
 import java.security.cert.CertPath;
@@ -48,6 +49,7 @@
 import java.util.Set;
 
 import sun.security.timestamp.TimestampToken;
+import sun.security.util.ConstraintsParameters;
 import sun.security.util.Debug;
 import sun.security.util.DerEncoder;
 import sun.security.util.DerInputStream;
@@ -321,6 +323,8 @@
                 data = content.getContentBytes();
             }
 
+            ConstraintsParameters cparams =
+                    new ConstraintsParameters(timestamp);
             String digestAlgname = getDigestAlgorithmId().getName();
 
             byte[] dataSigned;
@@ -347,11 +351,11 @@
                 if (messageDigest == null) // fail if there is no message digest
                     return null;
 
-                // check that algorithm is not restricted
-                if (!JAR_DISABLED_CHECK.permits(DIGEST_PRIMITIVE_SET,
-                        digestAlgname, null)) {
-                    throw new SignatureException("Digest check failed. " +
-                            "Disabled algorithm used: " + digestAlgname);
+                // check that digest algorithm is not restricted
+                try {
+                    JAR_DISABLED_CHECK.permits(digestAlgname, cparams);
+                } catch (CertPathValidatorException e) {
+                    throw new SignatureException(e.getMessage(), e);
                 }
 
                 MessageDigest md = MessageDigest.getInstance(digestAlgname);
@@ -385,17 +389,18 @@
             String algname = AlgorithmId.makeSigAlg(
                     digestAlgname, encryptionAlgname);
 
-            // check that algorithm is not restricted
-            if (!JAR_DISABLED_CHECK.permits(SIG_PRIMITIVE_SET, algname, null)) {
-                throw new SignatureException("Signature check failed. " +
-                        "Disabled algorithm used: " + algname);
+            // check that jar signature algorithm is not restricted
+            try {
+                JAR_DISABLED_CHECK.permits(algname, cparams);
+            } catch (CertPathValidatorException e) {
+                throw new SignatureException(e.getMessage(), e);
             }
 
             X509Certificate cert = getCertificate(block);
-            PublicKey key = cert.getPublicKey();
             if (cert == null) {
                 return null;
             }
+            PublicKey key = cert.getPublicKey();
 
             // check if the public key is restricted
             if (!JAR_DISABLED_CHECK.permits(SIG_PRIMITIVE_SET, key)) {
--- a/jdk/src/java.base/share/classes/sun/security/provider/certpath/AlgorithmChecker.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/sun/security/provider/certpath/AlgorithmChecker.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2009, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2009, 2017, 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
@@ -28,6 +28,7 @@
 import java.security.AlgorithmConstraints;
 import java.security.CryptoPrimitive;
 import java.security.Timestamp;
+import java.security.cert.CertPathValidator;
 import java.util.Collection;
 import java.util.Collections;
 import java.util.Date;
@@ -53,9 +54,10 @@
 import java.security.spec.DSAPublicKeySpec;
 
 import sun.security.util.AnchorCertificates;
-import sun.security.util.CertConstraintParameters;
+import sun.security.util.ConstraintsParameters;
 import sun.security.util.Debug;
 import sun.security.util.DisabledAlgorithmConstraints;
+import sun.security.validator.Validator;
 import sun.security.x509.X509CertImpl;
 import sun.security.x509.X509CRLImpl;
 import sun.security.x509.AlgorithmId;
@@ -79,6 +81,7 @@
     private final Date pkixdate;
     private PublicKey prevPubKey;
     private final Timestamp jarTimestamp;
+    private final String variant;
 
     private static final Set<CryptoPrimitive> SIGNATURE_PRIMITIVE_SET =
         Collections.unmodifiableSet(EnumSet.of(CryptoPrimitive.SIGNATURE));
@@ -109,64 +112,36 @@
      *
      * @param anchor the trust anchor selected to validate the target
      *     certificate
-     */
-    public AlgorithmChecker(TrustAnchor anchor) {
-        this(anchor, certPathDefaultConstraints, null);
-    }
-
-    /**
-     * Create a new {@code AlgorithmChecker} with the
-     * given {@code TrustAnchor} and {@code AlgorithmConstraints}.
-     *
-     * @param anchor the trust anchor selected to validate the target
-     *     certificate
-     * @param constraints the algorithm constraints (or null)
-     *
-     * @throws IllegalArgumentException if the {@code anchor} is null
+     * @param variant is the Validator variants of the operation. A null value
+     *                passed will set it to Validator.GENERIC.
      */
-    public AlgorithmChecker(TrustAnchor anchor,
-            AlgorithmConstraints constraints) {
-        this(anchor, constraints, null);
-    }
-
-    /**
-     * Create a new {@code AlgorithmChecker} with the
-     * given {@code AlgorithmConstraints}.
-     * <p>
-     * Note that this constructor will be used to check a certification
-     * path where the trust anchor is unknown, or a certificate list which may
-     * contain the trust anchor. This constructor is used by SunJSSE.
-     *
-     * @param constraints the algorithm constraints (or null)
-     */
-    public AlgorithmChecker(AlgorithmConstraints constraints) {
-        this.prevPubKey = null;
-        this.trustedPubKey = null;
-        this.constraints = constraints;
-        this.pkixdate = null;
-        this.jarTimestamp = null;
+    public AlgorithmChecker(TrustAnchor anchor, String variant) {
+        this(anchor, certPathDefaultConstraints, null, variant);
     }
 
     /**
      * Create a new {@code AlgorithmChecker} with the given
-     * {@code Timestamp}.
+     * {@code AlgorithmConstraints}, {@code Timestamp}, and/or {@code Variant}.
      * <p>
-     * Note that this constructor will be used to check a certification
-     * path for signed JAR files that are timestamped.
+     * Note that this constructor can initialize a variation of situations where
+     * the AlgorithmConstraints, Timestamp, or Variant maybe known.
      *
+     * @param constraints the algorithm constraints (or null)
      * @param jarTimestamp Timestamp passed for JAR timestamp constraint
      *                     checking. Set to null if not applicable.
+     * @param variant is the Validator variants of the operation. A null value
+     *                passed will set it to Validator.GENERIC.
      */
-    public AlgorithmChecker(Timestamp jarTimestamp) {
+    public AlgorithmChecker(AlgorithmConstraints constraints,
+            Timestamp jarTimestamp, String variant) {
         this.prevPubKey = null;
         this.trustedPubKey = null;
-        this.constraints = certPathDefaultConstraints;
-        if (jarTimestamp == null) {
-            throw new IllegalArgumentException(
-                    "Timestamp cannot be null");
-        }
-        this.pkixdate = jarTimestamp.getTimestamp();
+        this.constraints = (constraints == null ? certPathDefaultConstraints :
+                constraints);
+        this.pkixdate = (jarTimestamp != null ? jarTimestamp.getTimestamp() :
+                null);
         this.jarTimestamp = jarTimestamp;
+        this.variant = (variant == null ? Validator.VAR_GENERIC : variant);
     }
 
     /**
@@ -178,12 +153,13 @@
      * @param constraints the algorithm constraints (or null)
      * @param pkixdate Date the constraints are checked against. The value is
      *             either the PKIXParameter date or null for the current date.
+     * @param variant is the Validator variants of the operation. A null value
+     *                passed will set it to Validator.GENERIC.
      *
      * @throws IllegalArgumentException if the {@code anchor} is null
      */
     public AlgorithmChecker(TrustAnchor anchor,
-            AlgorithmConstraints constraints,
-            Date pkixdate) {
+            AlgorithmConstraints constraints, Date pkixdate, String variant) {
 
         if (anchor != null) {
             if (anchor.getTrustedCert() != null) {
@@ -207,6 +183,7 @@
         this.constraints = constraints;
         this.pkixdate = pkixdate;
         this.jarTimestamp = null;
+        this.variant = (variant == null ? Validator.VAR_GENERIC : variant);
     }
 
     /**
@@ -217,11 +194,13 @@
      *     certificate
      * @param pkixdate Date the constraints are checked against. The value is
      *             either the PKIXParameter date or null for the current date.
+     * @param variant is the Validator variants of the operation. A null value
+     *                passed will set it to Validator.GENERIC.
      *
      * @throws IllegalArgumentException if the {@code anchor} is null
      */
-    public AlgorithmChecker(TrustAnchor anchor, Date pkixdate) {
-        this(anchor, certPathDefaultConstraints, pkixdate);
+    public AlgorithmChecker(TrustAnchor anchor, Date pkixdate, String variant) {
+        this(anchor, certPathDefaultConstraints, pkixdate, variant);
     }
 
     // Check this 'cert' for restrictions in the AnchorCertificates
@@ -286,6 +265,28 @@
                 null, null, -1, PKIXReason.INVALID_KEY_USAGE);
         }
 
+        X509CertImpl x509Cert;
+        AlgorithmId algorithmId;
+        try {
+            x509Cert = X509CertImpl.toImpl((X509Certificate)cert);
+            algorithmId = (AlgorithmId)x509Cert.get(X509CertImpl.SIG_ALG);
+        } catch (CertificateException ce) {
+            throw new CertPathValidatorException(ce);
+        }
+
+        AlgorithmParameters currSigAlgParams = algorithmId.getParameters();
+        PublicKey currPubKey = cert.getPublicKey();
+        String currSigAlg = x509Cert.getSigAlgName();
+
+        // Check the signature algorithm and parameters against constraints.
+        if (!constraints.permits(SIGNATURE_PRIMITIVE_SET, currSigAlg,
+                currSigAlgParams)) {
+            throw new CertPathValidatorException(
+                    "Algorithm constraints check failed on signature " +
+                            "algorithm: " + currSigAlg, null, null, -1,
+                    BasicReason.ALGORITHM_CONSTRAINED);
+        }
+
         // Assume all key usage bits are set if key usage is not present
         Set<CryptoPrimitive> primitives = KU_PRIMITIVE_SET;
 
@@ -322,101 +323,74 @@
             }
         }
 
-        PublicKey currPubKey = cert.getPublicKey();
-
-        if (constraints instanceof DisabledAlgorithmConstraints) {
-            // Check against DisabledAlgorithmConstraints certpath constraints.
-            // permits() will throw exception on failure.
-            ((DisabledAlgorithmConstraints)constraints).permits(primitives,
-                new CertConstraintParameters((X509Certificate)cert,
-                        trustedMatch, pkixdate, jarTimestamp));
-            // If there is no previous key, set one and exit
-            if (prevPubKey == null) {
-                prevPubKey = currPubKey;
-                return;
-            }
-        }
+        ConstraintsParameters cp =
+                new ConstraintsParameters((X509Certificate)cert,
+                        trustedMatch, pkixdate, jarTimestamp, variant);
 
-        X509CertImpl x509Cert;
-        AlgorithmId algorithmId;
-        try {
-            x509Cert = X509CertImpl.toImpl((X509Certificate)cert);
-            algorithmId = (AlgorithmId)x509Cert.get(X509CertImpl.SIG_ALG);
-        } catch (CertificateException ce) {
-            throw new CertPathValidatorException(ce);
-        }
-
-        AlgorithmParameters currSigAlgParams = algorithmId.getParameters();
-        String currSigAlg = x509Cert.getSigAlgName();
+        // Check against local constraints if it is DisabledAlgorithmConstraints
+        if (constraints instanceof DisabledAlgorithmConstraints) {
+            ((DisabledAlgorithmConstraints)constraints).permits(currSigAlg, cp);
+            // DisabledAlgorithmsConstraints does not check primitives, so key
+            // additional key check.
 
-        // If 'constraints' is not of DisabledAlgorithmConstraints, check all
-        // everything individually
-        if (!(constraints instanceof DisabledAlgorithmConstraints)) {
-            // Check the current signature algorithm
-            if (!constraints.permits(
-                    SIGNATURE_PRIMITIVE_SET,
-                    currSigAlg, currSigAlgParams)) {
-                throw new CertPathValidatorException(
-                        "Algorithm constraints check failed on signature " +
-                                "algorithm: " + currSigAlg, null, null, -1,
-                        BasicReason.ALGORITHM_CONSTRAINED);
-            }
-
+        } else {
+            // Perform the default constraints checking anyway.
+            certPathDefaultConstraints.permits(currSigAlg, cp);
+            // Call locally set constraints to check key with primitives.
             if (!constraints.permits(primitives, currPubKey)) {
                 throw new CertPathValidatorException(
-                        "Algorithm constraints check failed on keysize: " +
-                                sun.security.util.KeyUtil.getKeySize(currPubKey),
+                        "Algorithm constraints check failed on key " +
+                                currPubKey.getAlgorithm() + " with size of " +
+                                sun.security.util.KeyUtil.getKeySize(currPubKey) +
+                                "bits",
                         null, null, -1, BasicReason.ALGORITHM_CONSTRAINED);
             }
         }
 
+        // If there is no previous key, set one and exit
+        if (prevPubKey == null) {
+            prevPubKey = currPubKey;
+            return;
+        }
+
         // Check with previous cert for signature algorithm and public key
-        if (prevPubKey != null) {
-            if (!constraints.permits(
-                    SIGNATURE_PRIMITIVE_SET,
-                    currSigAlg, prevPubKey, currSigAlgParams)) {
-                throw new CertPathValidatorException(
+        if (!constraints.permits(
+                SIGNATURE_PRIMITIVE_SET,
+                currSigAlg, prevPubKey, currSigAlgParams)) {
+            throw new CertPathValidatorException(
                     "Algorithm constraints check failed on " +
                             "signature algorithm: " + currSigAlg,
                     null, null, -1, BasicReason.ALGORITHM_CONSTRAINED);
+        }
+
+        // Inherit key parameters from previous key
+        if (PKIX.isDSAPublicKeyWithoutParams(currPubKey)) {
+            // Inherit DSA parameters from previous key
+            if (!(prevPubKey instanceof DSAPublicKey)) {
+                throw new CertPathValidatorException("Input key is not " +
+                        "of a appropriate type for inheriting parameters");
             }
 
-            // Inherit key parameters from previous key
-            if (PKIX.isDSAPublicKeyWithoutParams(currPubKey)) {
-                // Inherit DSA parameters from previous key
-                if (!(prevPubKey instanceof DSAPublicKey)) {
-                    throw new CertPathValidatorException("Input key is not " +
-                        "of a appropriate type for inheriting parameters");
-                }
-
-                DSAParams params = ((DSAPublicKey)prevPubKey).getParams();
-                if (params == null) {
-                    throw new CertPathValidatorException(
+            DSAParams params = ((DSAPublicKey)prevPubKey).getParams();
+            if (params == null) {
+                throw new CertPathValidatorException(
                         "Key parameters missing from public key.");
-                }
+            }
 
-                try {
-                    BigInteger y = ((DSAPublicKey)currPubKey).getY();
-                    KeyFactory kf = KeyFactory.getInstance("DSA");
-                    DSAPublicKeySpec ks = new DSAPublicKeySpec(y,
-                                                       params.getP(),
-                                                       params.getQ(),
-                                                       params.getG());
-                    currPubKey = kf.generatePublic(ks);
-                } catch (GeneralSecurityException e) {
-                    throw new CertPathValidatorException("Unable to generate " +
+            try {
+                BigInteger y = ((DSAPublicKey)currPubKey).getY();
+                KeyFactory kf = KeyFactory.getInstance("DSA");
+                DSAPublicKeySpec ks = new DSAPublicKeySpec(y, params.getP(),
+                        params.getQ(), params.getG());
+                currPubKey = kf.generatePublic(ks);
+            } catch (GeneralSecurityException e) {
+                throw new CertPathValidatorException("Unable to generate " +
                         "key with inherited parameters: " + e.getMessage(), e);
-                }
             }
         }
 
         // reset the previous public key
         prevPubKey = currPubKey;
-
-        // check the extended key usage, ignore the check now
-        // List<String> extendedKeyUsages = x509Cert.getExtendedKeyUsage();
-
-        // DO NOT remove any unresolved critical extensions
     }
 
     /**
@@ -456,8 +430,10 @@
      *
      * @param key the public key to verify the CRL signature
      * @param crl the target CRL
+     * @param variant is the Validator variants of the operation. A null value
+     *                passed will set it to Validator.GENERIC.
      */
-    static void check(PublicKey key, X509CRL crl)
+    static void check(PublicKey key, X509CRL crl, String variant)
                         throws CertPathValidatorException {
 
         X509CRLImpl x509CRLImpl = null;
@@ -468,7 +444,7 @@
         }
 
         AlgorithmId algorithmId = x509CRLImpl.getSigAlgId();
-        check(key, algorithmId);
+        check(key, algorithmId, variant);
     }
 
     /**
@@ -476,20 +452,16 @@
      *
      * @param key the public key to verify the CRL signature
      * @param algorithmId signature algorithm Algorithm ID
+     * @param variant is the Validator variants of the operation. A null value
+     *                passed will set it to Validator.GENERIC.
      */
-    static void check(PublicKey key, AlgorithmId algorithmId)
+    static void check(PublicKey key, AlgorithmId algorithmId, String variant)
                         throws CertPathValidatorException {
         String sigAlgName = algorithmId.getName();
         AlgorithmParameters sigAlgParams = algorithmId.getParameters();
 
-        if (!certPathDefaultConstraints.permits(
-                SIGNATURE_PRIMITIVE_SET, sigAlgName, key, sigAlgParams)) {
-            throw new CertPathValidatorException(
-                "Algorithm constraints check failed on signature algorithm: " +
-                sigAlgName + " is disabled",
-                null, null, -1, BasicReason.ALGORITHM_CONSTRAINED);
-        }
+        certPathDefaultConstraints.permits(new ConstraintsParameters(
+                sigAlgName, sigAlgParams, key, variant));
     }
-
 }
 
--- a/jdk/src/java.base/share/classes/sun/security/provider/certpath/DistributionPointFetcher.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/sun/security/provider/certpath/DistributionPointFetcher.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2002, 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2002, 2017, 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
@@ -33,6 +33,7 @@
 import java.util.*;
 
 import sun.security.util.Debug;
+import sun.security.validator.Validator;
 import static sun.security.x509.PKIXExtensions.*;
 import sun.security.x509.*;
 
@@ -66,6 +67,20 @@
      * an X509CRLSelector with certificateChecking set.
      */
     public static Collection<X509CRL> getCRLs(X509CRLSelector selector,
+            boolean signFlag, PublicKey prevKey, String provider,
+            List<CertStore> certStores, boolean[] reasonsMask,
+            Set<TrustAnchor> trustAnchors, Date validity, String variant)
+            throws CertStoreException
+    {
+        return getCRLs(selector, signFlag, prevKey, null, provider, certStores,
+                reasonsMask, trustAnchors, validity, variant);
+    }
+    /**
+     * Return the X509CRLs matching this selector. The selector must be
+     * an X509CRLSelector with certificateChecking set.
+     */
+    // Called by com.sun.deploy.security.RevocationChecker
+    public static Collection<X509CRL> getCRLs(X509CRLSelector selector,
                                               boolean signFlag,
                                               PublicKey prevKey,
                                               String provider,
@@ -76,7 +91,7 @@
         throws CertStoreException
     {
         return getCRLs(selector, signFlag, prevKey, null, provider, certStores,
-                       reasonsMask, trustAnchors, validity);
+                reasonsMask, trustAnchors, validity, Validator.VAR_GENERIC);
     }
 
     /**
@@ -91,7 +106,8 @@
                                               List<CertStore> certStores,
                                               boolean[] reasonsMask,
                                               Set<TrustAnchor> trustAnchors,
-                                              Date validity)
+                                              Date validity,
+                                              String variant)
         throws CertStoreException
     {
         X509Certificate cert = selector.getCertificateChecking();
@@ -120,7 +136,7 @@
                 DistributionPoint point = t.next();
                 Collection<X509CRL> crls = getCRLs(selector, certImpl,
                     point, reasonsMask, signFlag, prevKey, prevCert, provider,
-                    certStores, trustAnchors, validity);
+                    certStores, trustAnchors, validity, variant);
                 results.addAll(crls);
             }
             if (debug != null) {
@@ -145,7 +161,7 @@
         X509CertImpl certImpl, DistributionPoint point, boolean[] reasonsMask,
         boolean signFlag, PublicKey prevKey, X509Certificate prevCert,
         String provider, List<CertStore> certStores,
-        Set<TrustAnchor> trustAnchors, Date validity)
+        Set<TrustAnchor> trustAnchors, Date validity, String variant)
             throws CertStoreException {
 
         // check for full name
@@ -208,7 +224,7 @@
                 selector.setIssuerNames(null);
                 if (selector.match(crl) && verifyCRL(certImpl, point, crl,
                         reasonsMask, signFlag, prevKey, prevCert, provider,
-                        trustAnchors, certStores, validity)) {
+                        trustAnchors, certStores, validity, variant)) {
                     crls.add(crl);
                 }
             } catch (IOException | CRLException e) {
@@ -316,7 +332,7 @@
         X509CRL crl, boolean[] reasonsMask, boolean signFlag,
         PublicKey prevKey, X509Certificate prevCert, String provider,
         Set<TrustAnchor> trustAnchors, List<CertStore> certStores,
-        Date validity) throws CRLException, IOException {
+        Date validity, String variant) throws CRLException, IOException {
 
         if (debug != null) {
             debug.println("DistributionPointFetcher.verifyCRL: " +
@@ -663,7 +679,7 @@
 
         // check the crl signature algorithm
         try {
-            AlgorithmChecker.check(prevKey, crl);
+            AlgorithmChecker.check(prevKey, crl, variant);
         } catch (CertPathValidatorException cpve) {
             if (debug != null) {
                 debug.println("CRL signature algorithm check failed: " + cpve);
--- a/jdk/src/java.base/share/classes/sun/security/provider/certpath/OCSP.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/sun/security/provider/certpath/OCSP.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2009, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2009, 2017, 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
@@ -45,6 +45,7 @@
 
 import sun.security.action.GetIntegerAction;
 import sun.security.util.Debug;
+import sun.security.validator.Validator;
 import sun.security.x509.AccessDescription;
 import sun.security.x509.AuthorityInfoAccessExtension;
 import sun.security.x509.GeneralName;
@@ -94,42 +95,6 @@
 
     private OCSP() {}
 
-    /**
-     * Obtains the revocation status of a certificate using OCSP using the most
-     * common defaults. The OCSP responder URI is retrieved from the
-     * certificate's AIA extension. The OCSP responder certificate is assumed
-     * to be the issuer's certificate (or issued by the issuer CA).
-     *
-     * @param cert the certificate to be checked
-     * @param issuerCert the issuer certificate
-     * @return the RevocationStatus
-     * @throws IOException if there is an exception connecting to or
-     *    communicating with the OCSP responder
-     * @throws CertPathValidatorException if an exception occurs while
-     *    encoding the OCSP Request or validating the OCSP Response
-     */
-    public static RevocationStatus check(X509Certificate cert,
-                                         X509Certificate issuerCert)
-        throws IOException, CertPathValidatorException {
-        CertId certId = null;
-        URI responderURI = null;
-        try {
-            X509CertImpl certImpl = X509CertImpl.toImpl(cert);
-            responderURI = getResponderURI(certImpl);
-            if (responderURI == null) {
-                throw new CertPathValidatorException
-                    ("No OCSP Responder URI in certificate");
-            }
-            certId = new CertId(issuerCert, certImpl.getSerialNumberObject());
-        } catch (CertificateException | IOException e) {
-            throw new CertPathValidatorException
-                ("Exception while encoding OCSPRequest", e);
-        }
-        OCSPResponse ocspResponse = check(Collections.singletonList(certId),
-            responderURI, new OCSPResponse.IssuerInfo(issuerCert), null, null,
-            Collections.<Extension>emptyList());
-        return (RevocationStatus)ocspResponse.getSingleResponse(certId);
-    }
 
     /**
      * Obtains the revocation status of a certificate using OCSP.
@@ -146,6 +111,8 @@
      * @throws CertPathValidatorException if an exception occurs while
      *    encoding the OCSP Request or validating the OCSP Response
      */
+
+    // Called by com.sun.deploy.security.TrustDecider
     public static RevocationStatus check(X509Certificate cert,
                                          X509Certificate issuerCert,
                                          URI responderURI,
@@ -154,27 +121,27 @@
         throws IOException, CertPathValidatorException
     {
         return check(cert, issuerCert, responderURI, responderCert, date,
-                     Collections.<Extension>emptyList());
+                     Collections.<Extension>emptyList(), Validator.VAR_GENERIC);
     }
 
-    // Called by com.sun.deploy.security.TrustDecider
+
     public static RevocationStatus check(X509Certificate cert,
-                                         X509Certificate issuerCert,
-                                         URI responderURI,
-                                         X509Certificate responderCert,
-                                         Date date, List<Extension> extensions)
+            X509Certificate issuerCert, URI responderURI,
+            X509Certificate responderCert, Date date, List<Extension> extensions,
+            String variant)
         throws IOException, CertPathValidatorException
     {
-        return check(cert, responderURI, null, issuerCert, responderCert, date, extensions);
+        return check(cert, responderURI, null, issuerCert, responderCert, date,
+                extensions, variant);
     }
 
     public static RevocationStatus check(X509Certificate cert,
             URI responderURI, TrustAnchor anchor, X509Certificate issuerCert,
             X509Certificate responderCert, Date date,
-            List<Extension> extensions)
+            List<Extension> extensions, String variant)
             throws IOException, CertPathValidatorException
     {
-        CertId certId = null;
+        CertId certId;
         try {
             X509CertImpl certImpl = X509CertImpl.toImpl(cert);
             certId = new CertId(issuerCert, certImpl.getSerialNumberObject());
@@ -184,7 +151,7 @@
         }
         OCSPResponse ocspResponse = check(Collections.singletonList(certId),
                 responderURI, new OCSPResponse.IssuerInfo(anchor, issuerCert),
-                responderCert, date, extensions);
+                responderCert, date, extensions, variant);
         return (RevocationStatus) ocspResponse.getSingleResponse(certId);
     }
 
@@ -206,10 +173,10 @@
      * @throws CertPathValidatorException if an exception occurs while
      *    encoding the OCSP Request or validating the OCSP Response
      */
-        static OCSPResponse check(List<CertId> certIds, URI responderURI,
+    static OCSPResponse check(List<CertId> certIds, URI responderURI,
                               OCSPResponse.IssuerInfo issuerInfo,
                               X509Certificate responderCert, Date date,
-                              List<Extension> extensions)
+                              List<Extension> extensions, String variant)
         throws IOException, CertPathValidatorException
     {
         byte[] nonce = null;
@@ -226,7 +193,7 @@
 
             // verify the response
             ocspResponse.verify(certIds, issuerInfo, responderCert, date,
-                    nonce);
+                    nonce, variant);
         } catch (IOException ioe) {
             throw new CertPathValidatorException(
                 "Unable to determine revocation status due to network error",
--- a/jdk/src/java.base/share/classes/sun/security/provider/certpath/OCSPResponse.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/sun/security/provider/certpath/OCSPResponse.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 2017, 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
@@ -41,7 +41,6 @@
 import java.util.HashMap;
 import java.util.List;
 import java.util.Map;
-import java.util.Objects;
 import java.util.Set;
 import javax.security.auth.x500.X500Principal;
 
@@ -375,7 +374,8 @@
     }
 
     void verify(List<CertId> certIds, IssuerInfo issuerInfo,
-            X509Certificate responderCert, Date date, byte[] nonce)
+            X509Certificate responderCert, Date date, byte[] nonce,
+            String variant)
         throws CertPathValidatorException
     {
         switch (responseStatus) {
@@ -508,7 +508,8 @@
                 // Check algorithm constraints specified in security property
                 // "jdk.certpath.disabledAlgorithms".
                 AlgorithmChecker algChecker =
-                        new AlgorithmChecker(issuerInfo.getAnchor(), date);
+                        new AlgorithmChecker(issuerInfo.getAnchor(), date,
+                                variant);
                 algChecker.init(false);
                 algChecker.check(signerCert, Collections.<String>emptySet());
 
@@ -568,7 +569,7 @@
         if (signerCert != null) {
             // Check algorithm constraints specified in security property
             // "jdk.certpath.disabledAlgorithms".
-            AlgorithmChecker.check(signerCert.getPublicKey(), sigAlgId);
+            AlgorithmChecker.check(signerCert.getPublicKey(), sigAlgId, variant);
 
             if (!verifySignature(signerCert)) {
                 throw new CertPathValidatorException(
--- a/jdk/src/java.base/share/classes/sun/security/provider/certpath/PKIX.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/sun/security/provider/certpath/PKIX.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012, 2017, 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
@@ -87,6 +87,7 @@
         private Set<TrustAnchor> anchors;
         private List<X509Certificate> certs;
         private Timestamp timestamp;
+        private String variant;
 
         ValidatorParams(CertPath cp, PKIXParameters params)
             throws InvalidAlgorithmParameterException
@@ -102,8 +103,9 @@
         ValidatorParams(PKIXParameters params)
             throws InvalidAlgorithmParameterException
         {
-            if (params instanceof PKIXTimestampParameters) {
-                timestamp = ((PKIXTimestampParameters) params).getTimestamp();
+            if (params instanceof PKIXExtendedParameters) {
+                timestamp = ((PKIXExtendedParameters) params).getTimestamp();
+                variant = ((PKIXExtendedParameters) params).getVariant();
             }
 
             this.anchors = params.getTrustAnchors();
@@ -199,6 +201,10 @@
         Timestamp timestamp() {
             return timestamp;
         }
+
+        String variant() {
+            return variant;
+        }
     }
 
     static class BuilderParams extends ValidatorParams {
--- a/jdk/src/java.base/share/classes/sun/security/provider/certpath/PKIXCertPathValidator.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/sun/security/provider/certpath/PKIXCertPathValidator.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 2017, 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
@@ -173,9 +173,10 @@
         // add standard checkers that we will be using
         certPathCheckers.add(untrustedChecker);
         if (params.timestamp() == null) {
-            certPathCheckers.add(new AlgorithmChecker(anchor, params.date()));
+            certPathCheckers.add(new AlgorithmChecker(anchor, params.date(), null));
         } else {
-            certPathCheckers.add(new AlgorithmChecker(params.timestamp()));
+            certPathCheckers.add(new AlgorithmChecker(null,
+                    params.timestamp(), params.variant()));
         }
         certPathCheckers.add(new KeyChecker(certPathLen,
                                             params.targetCertConstraints()));
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/sun/security/provider/certpath/PKIXExtendedParameters.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,226 @@
+/*
+ * Copyright (c) 2016, 2017, 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.security.provider.certpath;
+
+import java.security.InvalidAlgorithmParameterException;
+import java.security.Timestamp;
+import java.security.cert.CertSelector;
+import java.security.cert.CertStore;
+import java.security.cert.PKIXBuilderParameters;
+import java.security.cert.PKIXCertPathChecker;
+import java.security.cert.TrustAnchor;
+import java.util.Date;
+import java.util.List;
+import java.util.Set;
+
+/**
+ * This class is a wrapper for PKIXBuilderParameters so that a Timestamp object
+ * and a string for the variant type, can be passed when doing certpath
+ * checking.
+ */
+
+public class PKIXExtendedParameters extends PKIXBuilderParameters {
+
+    private final PKIXBuilderParameters p;
+    private Timestamp jarTimestamp;
+    private final String variant;
+
+    public PKIXExtendedParameters(PKIXBuilderParameters params,
+            Timestamp timestamp, String variant)
+            throws InvalidAlgorithmParameterException {
+        super(params.getTrustAnchors(), null);
+        p = params;
+        jarTimestamp = timestamp;
+        this.variant = variant;
+    }
+
+    public Timestamp getTimestamp() {
+        return jarTimestamp;
+    }
+    public void setTimestamp(Timestamp t) {
+        jarTimestamp = t;
+    }
+
+    public String getVariant() {
+        return variant;
+    }
+
+    @Override
+    public void setDate(Date d) {
+        p.setDate(d);
+    }
+
+    @Override
+    public void addCertPathChecker(PKIXCertPathChecker c) {
+        p.addCertPathChecker(c);
+    }
+
+    @Override
+    public void setMaxPathLength(int maxPathLength) {
+        p.setMaxPathLength(maxPathLength);
+    }
+
+    @Override
+    public int getMaxPathLength() {
+        return p.getMaxPathLength();
+    }
+
+    @Override
+    public String toString() {
+        return p.toString();
+    }
+
+    @Override
+    public Set<TrustAnchor> getTrustAnchors() {
+        return p.getTrustAnchors();
+    }
+
+    @Override
+    public void setTrustAnchors(Set<TrustAnchor> trustAnchors)
+            throws InvalidAlgorithmParameterException {
+        // To avoid problems with PKIXBuilderParameter's constructors
+        if (p == null) {
+            return;
+        }
+        p.setTrustAnchors(trustAnchors);
+    }
+
+    @Override
+    public Set<String> getInitialPolicies() {
+        return p.getInitialPolicies();
+    }
+
+    @Override
+    public void setInitialPolicies(Set<String> initialPolicies) {
+        p.setInitialPolicies(initialPolicies);
+    }
+
+    @Override
+    public void setCertStores(List<CertStore> stores) {
+        p.setCertStores(stores);
+    }
+
+    @Override
+    public void addCertStore(CertStore store) {
+        p.addCertStore(store);
+    }
+
+    @Override
+    public List<CertStore> getCertStores() {
+        return p.getCertStores();
+    }
+
+    @Override
+    public void setRevocationEnabled(boolean val) {
+        p.setRevocationEnabled(val);
+    }
+
+    @Override
+    public boolean isRevocationEnabled() {
+        return p.isRevocationEnabled();
+    }
+
+    @Override
+    public void setExplicitPolicyRequired(boolean val) {
+        p.setExplicitPolicyRequired(val);
+    }
+
+    @Override
+    public boolean isExplicitPolicyRequired() {
+        return p.isExplicitPolicyRequired();
+    }
+
+    @Override
+    public void setPolicyMappingInhibited(boolean val) {
+        p.setPolicyMappingInhibited(val);
+    }
+
+    @Override
+    public boolean isPolicyMappingInhibited() {
+        return p.isPolicyMappingInhibited();
+    }
+
+    @Override
+    public void setAnyPolicyInhibited(boolean val) {
+        p.setAnyPolicyInhibited(val);
+    }
+
+    @Override
+    public boolean isAnyPolicyInhibited() {
+        return p.isAnyPolicyInhibited();
+    }
+
+    @Override
+    public void setPolicyQualifiersRejected(boolean qualifiersRejected) {
+        p.setPolicyQualifiersRejected(qualifiersRejected);
+    }
+
+    @Override
+    public boolean getPolicyQualifiersRejected() {
+        return p.getPolicyQualifiersRejected();
+    }
+
+    @Override
+    public Date getDate() {
+        return p.getDate();
+    }
+
+    @Override
+    public void setCertPathCheckers(List<PKIXCertPathChecker> checkers) {
+        p.setCertPathCheckers(checkers);
+    }
+
+    @Override
+    public List<PKIXCertPathChecker> getCertPathCheckers() {
+        return p.getCertPathCheckers();
+    }
+
+    @Override
+    public String getSigProvider() {
+        return p.getSigProvider();
+    }
+
+    @Override
+    public void setSigProvider(String sigProvider) {
+        p.setSigProvider(sigProvider);
+    }
+
+    @Override
+    public CertSelector getTargetCertConstraints() {
+        return p.getTargetCertConstraints();
+    }
+
+    @Override
+    public void setTargetCertConstraints(CertSelector selector) {
+        // To avoid problems with PKIXBuilderParameter's constructors
+        if (p == null) {
+            return;
+        }
+        p.setTargetCertConstraints(selector);
+    }
+
+}
--- a/jdk/src/java.base/share/classes/sun/security/provider/certpath/PKIXTimestampParameters.java	Mon Feb 13 11:57:56 2017 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,218 +0,0 @@
-/*
- * Copyright (c) 2016, 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.security.provider.certpath;
-
-import java.security.InvalidAlgorithmParameterException;
-import java.security.Timestamp;
-import java.security.cert.CertSelector;
-import java.security.cert.CertStore;
-import java.security.cert.PKIXBuilderParameters;
-import java.security.cert.PKIXCertPathChecker;
-import java.security.cert.TrustAnchor;
-import java.util.Date;
-import java.util.List;
-import java.util.Set;
-
-/**
- * This class is a wrapper for PKIXBuilderParameters so that a Timestamp object
- * can be passed alone when PKIXCertPath is checking signed jar files.
- */
-
-public class PKIXTimestampParameters extends PKIXBuilderParameters {
-
-    private final PKIXBuilderParameters p;
-    private Timestamp jarTimestamp;
-
-    public PKIXTimestampParameters(PKIXBuilderParameters params,
-            Timestamp timestamp) throws InvalidAlgorithmParameterException {
-        super(params.getTrustAnchors(), null);
-        p = params;
-        jarTimestamp = timestamp;
-    }
-
-    public Timestamp getTimestamp() {
-        return jarTimestamp;
-    }
-    public void setTimestamp(Timestamp t) {
-        jarTimestamp = t;
-    }
-
-    @Override
-    public void setDate(Date d) {
-        p.setDate(d);
-    }
-
-    @Override
-    public void addCertPathChecker(PKIXCertPathChecker c) {
-        p.addCertPathChecker(c);
-    }
-
-    @Override
-    public void setMaxPathLength(int maxPathLength) {
-        p.setMaxPathLength(maxPathLength);
-    }
-
-    @Override
-    public int getMaxPathLength() {
-        return p.getMaxPathLength();
-    }
-
-    @Override
-    public String toString() {
-        return p.toString();
-    }
-
-    @Override
-    public Set<TrustAnchor> getTrustAnchors() {
-        return p.getTrustAnchors();
-    }
-
-    @Override
-    public void setTrustAnchors(Set<TrustAnchor> trustAnchors)
-            throws InvalidAlgorithmParameterException {
-        // To avoid problems with PKIXBuilderParameter's constructors
-        if (p == null) {
-            return;
-        }
-        p.setTrustAnchors(trustAnchors);
-    }
-
-    @Override
-    public Set<String> getInitialPolicies() {
-        return p.getInitialPolicies();
-    }
-
-    @Override
-    public void setInitialPolicies(Set<String> initialPolicies) {
-        p.setInitialPolicies(initialPolicies);
-    }
-
-    @Override
-    public void setCertStores(List<CertStore> stores) {
-        p.setCertStores(stores);
-    }
-
-    @Override
-    public void addCertStore(CertStore store) {
-        p.addCertStore(store);
-    }
-
-    @Override
-    public List<CertStore> getCertStores() {
-        return p.getCertStores();
-    }
-
-    @Override
-    public void setRevocationEnabled(boolean val) {
-        p.setRevocationEnabled(val);
-    }
-
-    @Override
-    public boolean isRevocationEnabled() {
-        return p.isRevocationEnabled();
-    }
-
-    @Override
-    public void setExplicitPolicyRequired(boolean val) {
-        p.setExplicitPolicyRequired(val);
-    }
-
-    @Override
-    public boolean isExplicitPolicyRequired() {
-        return p.isExplicitPolicyRequired();
-    }
-
-    @Override
-    public void setPolicyMappingInhibited(boolean val) {
-        p.setPolicyMappingInhibited(val);
-    }
-
-    @Override
-    public boolean isPolicyMappingInhibited() {
-        return p.isPolicyMappingInhibited();
-    }
-
-    @Override
-    public void setAnyPolicyInhibited(boolean val) {
-        p.setAnyPolicyInhibited(val);
-    }
-
-    @Override
-    public boolean isAnyPolicyInhibited() {
-        return p.isAnyPolicyInhibited();
-    }
-
-    @Override
-    public void setPolicyQualifiersRejected(boolean qualifiersRejected) {
-        p.setPolicyQualifiersRejected(qualifiersRejected);
-    }
-
-    @Override
-    public boolean getPolicyQualifiersRejected() {
-        return p.getPolicyQualifiersRejected();
-    }
-
-    @Override
-    public Date getDate() {
-        return p.getDate();
-    }
-
-    @Override
-    public void setCertPathCheckers(List<PKIXCertPathChecker> checkers) {
-        p.setCertPathCheckers(checkers);
-    }
-
-    @Override
-    public List<PKIXCertPathChecker> getCertPathCheckers() {
-        return p.getCertPathCheckers();
-    }
-
-    @Override
-    public String getSigProvider() {
-        return p.getSigProvider();
-    }
-
-    @Override
-    public void setSigProvider(String sigProvider) {
-        p.setSigProvider(sigProvider);
-    }
-
-    @Override
-    public CertSelector getTargetCertConstraints() {
-        return p.getTargetCertConstraints();
-    }
-
-    @Override
-    public void setTargetCertConstraints(CertSelector selector) {
-        // To avoid problems with PKIXBuilderParameter's constructors
-        if (p == null) {
-            return;
-        }
-        p.setTargetCertConstraints(selector);
-    }
-
-}
--- a/jdk/src/java.base/share/classes/sun/security/provider/certpath/RevocationChecker.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/sun/security/provider/certpath/RevocationChecker.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012, 2017, 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
@@ -579,7 +579,7 @@
                     approvedCRLs.addAll(DistributionPointFetcher.getCRLs(
                                         sel, signFlag, prevKey, prevCert,
                                         params.sigProvider(), certStores,
-                                        reasonsMask, anchors, null));
+                                        reasonsMask, anchors, null, params.variant()));
                 }
             } catch (CertStoreException e) {
                 if (e instanceof CertStoreTypeException) {
@@ -727,7 +727,7 @@
                     }
                 }
                 response.verify(Collections.singletonList(certId), issuerInfo,
-                        responderCert, params.date(), nonce);
+                        responderCert, params.date(), nonce, params.variant());
 
             } else {
                 URI responderURI = (this.responderURI != null)
@@ -741,7 +741,7 @@
 
                 response = OCSP.check(Collections.singletonList(certId),
                         responderURI, issuerInfo, responderCert, null,
-                        ocspExtensions);
+                        ocspExtensions, params.variant());
             }
         } catch (IOException e) {
             throw new CertPathValidatorException(
@@ -853,7 +853,7 @@
                     if (DistributionPointFetcher.verifyCRL(
                             certImpl, point, crl, reasonsMask, signFlag,
                             prevKey, null, params.sigProvider(), anchors,
-                            certStores, params.date()))
+                            certStores, params.date(), params.variant()))
                     {
                         results.add(crl);
                     }
--- a/jdk/src/java.base/share/classes/sun/security/provider/certpath/SunCertPathBuilder.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/sun/security/provider/certpath/SunCertPathBuilder.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 2017, 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
@@ -344,7 +344,7 @@
 
                 // add the algorithm checker
                 checkers.add(new AlgorithmChecker(builder.trustAnchor,
-                        buildParams.date()));
+                        buildParams.date(), null));
 
                 BasicChecker basicChecker = null;
                 if (nextState.keyParamsNeeded()) {
--- a/jdk/src/java.base/share/classes/sun/security/ssl/EllipticCurvesExtension.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/sun/security/ssl/EllipticCurvesExtension.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2006, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2006, 2017, 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
@@ -43,6 +43,9 @@
 
 final class EllipticCurvesExtension extends HelloExtension {
 
+    /* Class and subclass dynamic debugging support */
+    private static final Debug debug = Debug.getInstance("ssl");
+
     private static final int ARBITRARY_PRIME = 0xff01;
     private static final int ARBITRARY_CHAR2 = 0xff02;
 
@@ -159,6 +162,11 @@
                     }   // ignore unknown curves
                 }
             }
+            if (idList.isEmpty() && JsseJce.isEcAvailable()) {
+                throw new IllegalArgumentException(
+                    "System property jdk.tls.namedGroups(" + property + ") " +
+                    "contains no supported elliptic curves");
+            }
         } else {        // default curves
             int[] ids;
             if (requireFips) {
@@ -183,16 +191,17 @@
             }
         }
 
-        if (idList.isEmpty()) {
-            throw new IllegalArgumentException(
-                "System property jdk.tls.namedGroups(" + property + ") " +
-                "contains no supported elliptic curves");
-        } else {
-            supportedCurveIds = new int[idList.size()];
-            int i = 0;
-            for (Integer id : idList) {
-                supportedCurveIds[i++] = id;
-            }
+        if (debug != null && idList.isEmpty()) {
+            Debug.log(
+                "Initialized [jdk.tls.namedGroups|default] list contains " +
+                "no available elliptic curves. " +
+                (property != null ? "(" + property + ")" : "[Default]"));
+        }
+
+        supportedCurveIds = new int[idList.size()];
+        int i = 0;
+        for (Integer id : idList) {
+            supportedCurveIds[i++] = id;
         }
     }
 
--- a/jdk/src/java.base/share/classes/sun/security/ssl/SSLContextImpl.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/sun/security/ssl/SSLContextImpl.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1999, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1999, 2017, 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
@@ -37,6 +37,7 @@
 
 import sun.security.provider.certpath.AlgorithmChecker;
 import sun.security.action.GetPropertyAction;
+import sun.security.validator.Validator;
 
 public abstract class SSLContextImpl extends SSLContextSpi {
 
@@ -1436,7 +1437,7 @@
                 constraints = new SSLAlgorithmConstraints(sslSocket, true);
             }
 
-            checkAlgorithmConstraints(chain, constraints);
+            checkAlgorithmConstraints(chain, constraints, isClient);
         }
     }
 
@@ -1478,12 +1479,12 @@
                 constraints = new SSLAlgorithmConstraints(engine, true);
             }
 
-            checkAlgorithmConstraints(chain, constraints);
+            checkAlgorithmConstraints(chain, constraints, isClient);
         }
     }
 
     private void checkAlgorithmConstraints(X509Certificate[] chain,
-            AlgorithmConstraints constraints) throws CertificateException {
+            AlgorithmConstraints constraints, boolean isClient) throws CertificateException {
 
         try {
             // Does the certificate chain end with a trusted certificate?
@@ -1501,7 +1502,9 @@
 
             // A forward checker, need to check from trust to target
             if (checkedLength >= 0) {
-                AlgorithmChecker checker = new AlgorithmChecker(constraints);
+                AlgorithmChecker checker =
+                        new AlgorithmChecker(constraints, null,
+                                (isClient ? Validator.VAR_TLS_CLIENT : Validator.VAR_TLS_SERVER));
                 checker.init(false);
                 for (int i = checkedLength; i >= 0; i--) {
                     Certificate cert = chain[i];
--- a/jdk/src/java.base/share/classes/sun/security/ssl/X509KeyManagerImpl.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/sun/security/ssl/X509KeyManagerImpl.java	Wed Jul 05 22:52:01 2017 +0200
@@ -39,6 +39,7 @@
 import javax.net.ssl.*;
 
 import sun.security.provider.certpath.AlgorithmChecker;
+import sun.security.validator.Validator;
 
 /**
  * The new X509 key manager implementation. The main differences to the
@@ -661,6 +662,15 @@
 
             return CheckResult.OK;
         }
+
+        public String getValidator() {
+            if (this == CLIENT) {
+                return Validator.VAR_TLS_CLIENT;
+            } else if (this == SERVER) {
+                return Validator.VAR_TLS_SERVER;
+            }
+            return Validator.VAR_GENERIC;
+        }
     }
 
     // enum for the result of the extension check
@@ -774,7 +784,8 @@
 
             // check the algorithm constraints
             if (constraints != null &&
-                    !conformsToAlgorithmConstraints(constraints, chain)) {
+                    !conformsToAlgorithmConstraints(constraints, chain,
+                            checkType.getValidator())) {
 
                 if (useDebug) {
                     debug.println("Ignoring alias " + alias +
@@ -811,9 +822,10 @@
     }
 
     private static boolean conformsToAlgorithmConstraints(
-            AlgorithmConstraints constraints, Certificate[] chain) {
+            AlgorithmConstraints constraints, Certificate[] chain,
+            String variant) {
 
-        AlgorithmChecker checker = new AlgorithmChecker(constraints);
+        AlgorithmChecker checker = new AlgorithmChecker(constraints, null, variant);
         try {
             checker.init(false);
         } catch (CertPathValidatorException cpve) {
--- a/jdk/src/java.base/share/classes/sun/security/util/CertConstraintParameters.java	Mon Feb 13 11:57:56 2017 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,76 +0,0 @@
-/*
- * Copyright (c) 2016, 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.security.util;
-
-import java.security.Timestamp;
-import java.security.cert.X509Certificate;
-import java.util.Date;
-
-/**
- * This class is a wrapper for keeping state and passing objects between PKIX,
- * AlgorithmChecker, and DisabledAlgorithmConstraints.
- */
-public class CertConstraintParameters {
-    // A certificate being passed to check against constraints.
-    private final X509Certificate cert;
-    // This is true if the trust anchor in the certificate chain matches a cert
-    // in AnchorCertificates
-    private final boolean trustedMatch;
-    // PKIXParameter date
-    private final Date pkixDate;
-    // Timestamp of the signed JAR file
-    private final Timestamp jarTimestamp;
-
-    public CertConstraintParameters(X509Certificate c, boolean match,
-            Date pkixdate, Timestamp jarTime) {
-        cert = c;
-        trustedMatch = match;
-        pkixDate = pkixdate;
-        jarTimestamp = jarTime;
-    }
-
-    public CertConstraintParameters(X509Certificate c) {
-        this(c, false, null, null);
-    }
-
-    // Returns if the trust anchor has a match if anchor checking is enabled.
-    public boolean isTrustedMatch() {
-        return trustedMatch;
-    }
-
-    public X509Certificate getCertificate() {
-        return cert;
-    }
-
-    public Date getPKIXParamDate() {
-        return pkixDate;
-    }
-
-    public Timestamp getJARTimestamp() {
-        return jarTimestamp;
-    }
-
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/sun/security/util/ConstraintsParameters.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,135 @@
+/*
+ * Copyright (c) 2016, 2017 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.security.util;
+
+import sun.security.validator.Validator;
+
+import java.security.AlgorithmParameters;
+import java.security.Key;
+import java.security.Timestamp;
+import java.security.cert.X509Certificate;
+import java.util.Date;
+
+/**
+ * This class contains parameters for checking against constraints that extend
+ * past the publicly available parameters in java.security.AlgorithmConstraints.
+
+ * This is currently on passed between  between PKIX, AlgorithmChecker,
+ * and DisabledAlgorithmConstraints.
+ */
+public class ConstraintsParameters {
+    /*
+     * The below 3 values are used the same as the permit() methods
+     * published in java.security.AlgorithmConstraints.
+     */
+    // Algorithm string to be checked against constraints
+    private final String algorithm;
+    // AlgorithmParameters to the algorithm being checked
+    private final AlgorithmParameters algParams;
+    // Public Key being checked against constraints
+    private final Key publicKey;
+
+    /*
+     * New values that are checked against constraints that the current public
+     * API does not support.
+     */
+    // A certificate being passed to check against constraints.
+    private final X509Certificate cert;
+    // This is true if the trust anchor in the certificate chain matches a cert
+    // in AnchorCertificates
+    private final boolean trustedMatch;
+    // PKIXParameter date
+    private final Date pkixDate;
+    // Timestamp of the signed JAR file
+    private final Timestamp jarTimestamp;
+    private final String variant;
+
+    public ConstraintsParameters(X509Certificate c, boolean match,
+            Date pkixdate, Timestamp jarTime, String variant) {
+        cert = c;
+        trustedMatch = match;
+        pkixDate = pkixdate;
+        jarTimestamp = jarTime;
+        this.variant = (variant == null ? Validator.VAR_GENERIC : variant);
+        algorithm = null;
+        algParams = null;
+        publicKey = null;
+    }
+
+    public ConstraintsParameters(String algorithm, AlgorithmParameters params,
+            Key key, String variant) {
+        this.algorithm = algorithm;
+        algParams = params;
+        this.publicKey = key;
+        cert = null;
+        trustedMatch = false;
+        pkixDate = null;
+        jarTimestamp = null;
+        this.variant = (variant == null ? Validator.VAR_GENERIC : variant);
+    }
+
+
+    public ConstraintsParameters(X509Certificate c) {
+        this(c, false, null, null,
+                Validator.VAR_GENERIC);
+    }
+
+    public ConstraintsParameters(Timestamp jarTime) {
+        this(null, false, null, jarTime, Validator.VAR_GENERIC);
+    }
+
+    public String getAlgorithm() {
+        return algorithm;
+    }
+
+    public AlgorithmParameters getAlgParams() {
+        return algParams;
+    }
+
+    public Key getPublicKey() {
+        return publicKey;
+    }
+    // Returns if the trust anchor has a match if anchor checking is enabled.
+    public boolean isTrustedMatch() {
+        return trustedMatch;
+    }
+
+    public X509Certificate getCertificate() {
+        return cert;
+    }
+
+    public Date getPKIXParamDate() {
+        return pkixDate;
+    }
+
+    public Timestamp getJARTimestamp() {
+        return jarTimestamp;
+    }
+
+    public String getVariant() {
+        return variant;
+    }
+}
--- a/jdk/src/java.base/share/classes/sun/security/util/DisabledAlgorithmConstraints.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/sun/security/util/DisabledAlgorithmConstraints.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2010, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2010, 2017, 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
@@ -25,6 +25,8 @@
 
 package sun.security.util;
 
+import sun.security.validator.Validator;
+
 import java.security.CryptoPrimitive;
 import java.security.AlgorithmParameters;
 import java.security.Key;
@@ -32,10 +34,12 @@
 import java.security.cert.CertPathValidatorException.BasicReason;
 import java.security.cert.X509Certificate;
 import java.text.SimpleDateFormat;
+import java.util.ArrayList;
 import java.util.Calendar;
 import java.util.Date;
 import java.util.HashMap;
 import java.util.HashSet;
+import java.util.List;
 import java.util.Locale;
 import java.util.Map;
 import java.util.Set;
@@ -100,12 +104,6 @@
     @Override
     public final boolean permits(Set<CryptoPrimitive> primitives,
             String algorithm, AlgorithmParameters parameters) {
-
-        if (primitives == null || primitives.isEmpty()) {
-            throw new IllegalArgumentException(
-                        "No cryptographic primitive specified");
-        }
-
         return checkAlgorithm(disabledAlgorithms, algorithm, decomposer);
     }
 
@@ -133,6 +131,18 @@
         return checkConstraints(primitives, algorithm, key, parameters);
     }
 
+    public final void permits(ConstraintsParameters cp)
+            throws CertPathValidatorException {
+        permits(cp.getAlgorithm(), cp);
+    }
+
+    public final void permits(String algorithm, Key key,
+            AlgorithmParameters params, String variant)
+            throws CertPathValidatorException {
+        permits(algorithm, new ConstraintsParameters(algorithm, params, key,
+                (variant == null) ? Validator.VAR_GENERIC : variant));
+    }
+
     /*
      * Check if a x509Certificate object is permitted.  Check if all
      * algorithms are allowed, certificate constraints, and the
@@ -140,18 +150,10 @@
      *
      * Uses new style permit() which throws exceptions.
      */
-    public final void permits(Set<CryptoPrimitive> primitives,
-            CertConstraintParameters cp) throws CertPathValidatorException {
-        checkConstraints(primitives, cp);
-    }
 
-    /*
-     * Check if Certificate object is within the constraints.
-     * Uses new style permit() which throws exceptions.
-     */
-    public final void permits(Set<CryptoPrimitive> primitives,
-            X509Certificate cert) throws CertPathValidatorException {
-        checkConstraints(primitives, new CertConstraintParameters(cert));
+    public final void permits(String algorithm, ConstraintsParameters cp)
+            throws CertPathValidatorException {
+        algorithmConstraints.permits(algorithm, cp);
     }
 
     // Check if a string is contained inside the property
@@ -174,7 +176,7 @@
             throw new IllegalArgumentException("The key cannot be null");
         }
 
-        // check the signature algorithm
+        // check the signature algorithm with parameters
         if (algorithm != null && algorithm.length() != 0) {
             if (!permits(primitives, algorithm, parameters)) {
                 return false;
@@ -190,36 +192,6 @@
         return algorithmConstraints.permits(key);
     }
 
-    /*
-     * Check algorithm constraints with Certificate
-     * Uses new style permit() which throws exceptions.
-     */
-    private void checkConstraints(Set<CryptoPrimitive> primitives,
-            CertConstraintParameters cp) throws CertPathValidatorException {
-
-        X509Certificate cert = cp.getCertificate();
-        String algorithm = cert.getSigAlgName();
-
-        // Check signature algorithm is not disabled
-        if (!permits(primitives, algorithm, null)) {
-            throw new CertPathValidatorException(
-                    "Algorithm constraints check failed on disabled "+
-                            "signature algorithm: " + algorithm,
-                    null, null, -1, BasicReason.ALGORITHM_CONSTRAINED);
-        }
-
-        // Check key algorithm is not disabled
-        if (!permits(primitives, cert.getPublicKey().getAlgorithm(), null)) {
-            throw new CertPathValidatorException(
-                    "Algorithm constraints check failed on disabled "+
-                            "public key algorithm: " + algorithm,
-                    null, null, -1, BasicReason.ALGORITHM_CONSTRAINED);
-        }
-
-        // Check the certificate and key constraints
-        algorithmConstraints.permits(cp);
-
-    }
 
     /**
      * Key and Certificate Constraints
@@ -234,13 +206,13 @@
      * 'true' means the operation is allowed.
      * 'false' means it failed the constraints and is disallowed.
      *
-     * When passing CertConstraintParameters through permit(), an exception
+     * When passing ConstraintsParameters through permit(), an exception
      * will be thrown on a failure to better identify why the operation was
      * disallowed.
      */
 
     private static class Constraints {
-        private Map<String, Set<Constraint>> constraintsMap = new HashMap<>();
+        private Map<String, List<Constraint>> constraintsMap = new HashMap<>();
 
         private static class Holder {
             private static final Pattern DENY_AFTER_PATTERN = Pattern.compile(
@@ -260,23 +232,22 @@
 
                 // Check if constraint is a complete disabling of an
                 // algorithm or has conditions.
-                String algorithm;
-                String policy;
                 int space = constraintEntry.indexOf(' ');
-                if (space > 0) {
-                    algorithm = AlgorithmDecomposer.hashName(
-                            constraintEntry.substring(0, space).
-                                    toUpperCase(Locale.ENGLISH));
-                    policy = constraintEntry.substring(space + 1);
-                } else {
-                    algorithm = constraintEntry.toUpperCase(Locale.ENGLISH);
-                    if (!constraintsMap.containsKey(algorithm)) {
-                        constraintsMap.putIfAbsent(algorithm,
-                                new HashSet<>());
-                    }
+                String algorithm = AlgorithmDecomposer.hashName(
+                        ((space > 0 ? constraintEntry.substring(0, space) :
+                                constraintEntry).
+                                toUpperCase(Locale.ENGLISH)));
+                List<Constraint> constraintList =
+                        constraintsMap.getOrDefault(algorithm,
+                                new ArrayList<>(1));
+                constraintsMap.putIfAbsent(algorithm, constraintList);
+                if (space <= 0) {
+                    constraintList.add(new DisabledConstraint(algorithm));
                     continue;
                 }
 
+                String policy = constraintEntry.substring(space + 1);
+
                 // Convert constraint conditions into Constraint classes
                 Constraint c, lastConstraint = null;
                 // Allow only one jdkCA entry per constraint entry
@@ -315,7 +286,7 @@
                         c = new jdkCAConstraint(algorithm);
                         jdkCALimit = true;
 
-                    } else if(entry.startsWith("denyAfter") &&
+                    } else if (entry.startsWith("denyAfter") &&
                             (matcher = Holder.DENY_AFTER_PATTERN.matcher(entry))
                                     .matches()) {
                         if (debug != null) {
@@ -332,6 +303,12 @@
                         c = new DenyAfterConstraint(algorithm, year, month,
                                 day);
                         denyAfterLimit = true;
+                    } else if (entry.startsWith("usage")) {
+                        String s[] = (entry.substring(5)).trim().split(" ");
+                        c = new UsageConstraint(algorithm, s);
+                        if (debug != null) {
+                            debug.println("Constraints usage length is " + s.length);
+                        }
                     } else {
                         throw new IllegalArgumentException("Error in security" +
                                 " property. Constraint unknown: " + entry);
@@ -340,11 +317,7 @@
                     // Link multiple conditions for a single constraint
                     // into a linked list.
                     if (lastConstraint == null) {
-                        if (!constraintsMap.containsKey(algorithm)) {
-                            constraintsMap.putIfAbsent(algorithm,
-                                    new HashSet<>());
-                        }
-                        constraintsMap.get(algorithm).add(c);
+                        constraintList.add(c);
                     } else {
                         lastConstraint.nextConstraint = c;
                     }
@@ -354,17 +327,17 @@
         }
 
         // Get applicable constraints based off the signature algorithm
-        private Set<Constraint> getConstraints(String algorithm) {
+        private List<Constraint> getConstraints(String algorithm) {
             return constraintsMap.get(algorithm);
         }
 
         // Check if KeySizeConstraints permit the specified key
         public boolean permits(Key key) {
-            Set<Constraint> set = getConstraints(key.getAlgorithm());
-            if (set == null) {
+            List<Constraint> list = getConstraints(key.getAlgorithm());
+            if (list == null) {
                 return true;
             }
-            for (Constraint constraint : set) {
+            for (Constraint constraint : list) {
                 if (!constraint.permits(key)) {
                     if (debug != null) {
                         debug.println("keySizeConstraint: failed key " +
@@ -377,31 +350,35 @@
         }
 
         // Check if constraints permit this cert.
-        public void permits(CertConstraintParameters cp)
+        public void permits(String algorithm, ConstraintsParameters cp)
                 throws CertPathValidatorException {
             X509Certificate cert = cp.getCertificate();
 
             if (debug != null) {
-                debug.println("Constraints.permits(): " + cert.getSigAlgName());
+                debug.println("Constraints.permits(): " + algorithm +
+                        " Variant: " + cp.getVariant());
             }
 
             // Get all signature algorithms to check for constraints
-            Set<String> algorithms =
-                    AlgorithmDecomposer.decomposeOneHash(cert.getSigAlgName());
-            if (algorithms == null || algorithms.isEmpty()) {
-                return;
+            Set<String> algorithms = new HashSet<>();
+            if (algorithm != null) {
+                algorithms.addAll(AlgorithmDecomposer.decomposeOneHash(algorithm));
             }
 
-            // Attempt to add the public key algorithm to the set
-            algorithms.add(cert.getPublicKey().getAlgorithm());
-
+            // Attempt to add the public key algorithm if cert provided
+            if (cert != null) {
+                algorithms.add(cert.getPublicKey().getAlgorithm());
+            }
+            if (cp.getPublicKey() != null) {
+                algorithms.add(cp.getPublicKey().getAlgorithm());
+            }
             // Check all applicable constraints
-            for (String algorithm : algorithms) {
-                Set<Constraint> set = getConstraints(algorithm);
-                if (set == null) {
+            for (String alg : algorithms) {
+                List<Constraint> list = getConstraints(alg);
+                if (list == null) {
                     continue;
                 }
-                for (Constraint constraint : set) {
+                for (Constraint constraint : list) {
                     constraint.permits(cp);
                 }
             }
@@ -467,17 +444,17 @@
 
         /**
          * Check if an algorithm constraint is permitted with a given
-         * CertConstraintParameters.
+         * ConstraintsParameters.
          *
          * If the check inside of {@code permits()} fails, it must call
-         * {@code next()} with the same {@code CertConstraintParameters}
+         * {@code next()} with the same {@code ConstraintsParameters}
          * parameter passed if multiple constraints need to be checked.
          *
          * @param cp CertConstraintParameter containing certificate info
          * @throws CertPathValidatorException if constraint disallows.
          *
          */
-        public abstract void permits(CertConstraintParameters cp)
+        public abstract void permits(ConstraintsParameters cp)
                 throws CertPathValidatorException;
 
         /**
@@ -491,12 +468,12 @@
          * were disallowed, the last constraint will throw
          * {@code CertPathValidatorException}.
          *
-         * @param cp CertConstraintParameters
+         * @param cp ConstraintsParameters
          * @return 'true' if constraint allows the operation, 'false' if
          * we are at the end of the constraint list or,
          * {@code nextConstraint} is null.
          */
-        boolean next(CertConstraintParameters cp)
+        boolean next(ConstraintsParameters cp)
                 throws CertPathValidatorException {
             if (nextConstraint != null) {
                 nextConstraint.permits(cp);
@@ -525,6 +502,14 @@
             }
             return false;
         }
+
+        String extendedMsg(ConstraintsParameters cp) {
+            return (cp.getCertificate() == null ? "." :
+                    " used with certificate: " +
+                            cp.getCertificate().getSubjectX500Principal() +
+                    (cp.getVariant() != Validator.VAR_GENERIC ?
+                            ".  Usage was " + cp.getVariant() : "."));
+        }
     }
 
     /*
@@ -537,11 +522,11 @@
         }
 
         /*
-         * Check if CertConstraintParameters has a trusted match, if it does
+         * Check if ConstraintsParameters has a trusted match, if it does
          * call next() for any following constraints. If it does not, exit
          * as this constraint(s) does not restrict the operation.
          */
-        public void permits(CertConstraintParameters cp)
+        public void permits(ConstraintsParameters cp)
                 throws CertPathValidatorException {
             if (debug != null) {
                 debug.println("jdkCAConstraints.permits(): " + algorithm);
@@ -554,8 +539,7 @@
                 }
                 throw new CertPathValidatorException(
                         "Algorithm constraints check failed on certificate " +
-                                "anchor limits. " + algorithm + " used with " +
-                                cp.getCertificate().getSubjectX500Principal(),
+                        "anchor limits. " + algorithm + extendedMsg(cp),
                         null, null, -1, BasicReason.ALGORITHM_CONSTRAINED);
             }
         }
@@ -615,7 +599,7 @@
           * constraints. Throw an exception if this is the last constraint.
           */
          @Override
-         public void permits(CertConstraintParameters cp)
+         public void permits(ConstraintsParameters cp)
                  throws CertPathValidatorException {
              Date currentDate;
              String errmsg;
@@ -628,7 +612,7 @@
                  errmsg = "PKIXParameter date: ";
              } else {
                  currentDate = new Date();
-                 errmsg = "Certificate date: ";
+                 errmsg = "Current date: ";
              }
 
              if (!denyAfterDate.after(currentDate)) {
@@ -637,9 +621,9 @@
                  }
                  throw new CertPathValidatorException(
                          "denyAfter constraint check failed: " + algorithm +
-                                 " used with Constraint date: " +
-                                 dateFormat.format(denyAfterDate) + "; "
-                                 + errmsg + dateFormat.format(currentDate),
+                         " used with Constraint date: " +
+                         dateFormat.format(denyAfterDate) + "; " + errmsg +
+                         dateFormat.format(currentDate) + extendedMsg(cp),
                          null, null, -1, BasicReason.ALGORITHM_CONSTRAINED);
              }
          }
@@ -661,6 +645,48 @@
      }
 
     /*
+     * The usage constraint is for the "usage" keyword.  It checks against the
+     * variant value in ConstraintsParameters.
+     */
+    private static class UsageConstraint extends Constraint {
+        String[] usages;
+
+        UsageConstraint(String algorithm, String[] usages) {
+            this.algorithm = algorithm;
+            this.usages = usages;
+        }
+
+        public void permits(ConstraintsParameters cp)
+                throws CertPathValidatorException {
+            for (String usage : usages) {
+
+                String v = null;
+                if (usage.compareToIgnoreCase("TLSServer") == 0) {
+                    v = Validator.VAR_TLS_SERVER;
+                } else if (usage.compareToIgnoreCase("TLSClient") == 0) {
+                    v = Validator.VAR_TLS_CLIENT;
+                } else if (usage.compareToIgnoreCase("SignedJAR") == 0) {
+                    v = Validator.VAR_PLUGIN_CODE_SIGNING;
+                }
+
+                if (debug != null) {
+                    debug.println("Checking if usage constraint " + v +
+                            " matches " + cp.getVariant());
+                }
+                if (cp.getVariant().compareTo(v) == 0) {
+                    if (next(cp)) {
+                        return;
+                    }
+                    throw new CertPathValidatorException("Usage constraint " +
+                            usage + " check failed: " + algorithm +
+                            extendedMsg(cp),
+                            null, null, -1, BasicReason.ALGORITHM_CONSTRAINED);
+                }
+            }
+        }
+    }
+
+    /*
      * This class contains constraints dealing with the key size
      * support limits per algorithm.   e.g.  "keySize <= 1024"
      */
@@ -713,17 +739,22 @@
          * constraint  Any permitted constraint will exit the linked list
          * to allow the operation.
          */
-        public void permits(CertConstraintParameters cp)
+        public void permits(ConstraintsParameters cp)
                 throws CertPathValidatorException {
-            if (!permitsImpl(cp.getCertificate().getPublicKey())) {
+            Key key = null;
+            if (cp.getPublicKey() != null) {
+                key = cp.getPublicKey();
+            } else if (cp.getCertificate() != null) {
+                key = cp.getCertificate().getPublicKey();
+            }
+            if (key != null && !permitsImpl(key)) {
                 if (nextConstraint != null) {
                     nextConstraint.permits(cp);
                     return;
                 }
                 throw new CertPathValidatorException(
                         "Algorithm constraints check failed on keysize limits. "
-                                + algorithm + " " + size + "bit key used with "
-                                + cp.getCertificate().getSubjectX500Principal(),
+                        + algorithm + " " + size + "bit key" + extendedMsg(cp),
                         null, null, -1, BasicReason.ALGORITHM_CONSTRAINED);
             }
         }
@@ -762,5 +793,26 @@
             return true;
         }
     }
+
+    /*
+     * This constraint is used for the complete disabling of the algorithm.
+     */
+    private static class DisabledConstraint extends Constraint {
+        DisabledConstraint(String algo) {
+            algorithm = algo;
+        }
+
+        public void permits(ConstraintsParameters cp)
+                throws CertPathValidatorException {
+            throw new CertPathValidatorException(
+                    "Algorithm constraints check failed on disabled " +
+                            "algorithm: " + algorithm + extendedMsg(cp),
+                    null, null, -1, BasicReason.ALGORITHM_CONSTRAINED);
+        }
+
+        public boolean permits(Key key) {
+            return false;
+        }
+    }
 }
 
--- a/jdk/src/java.base/share/classes/sun/security/util/SignatureFileVerifier.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/sun/security/util/SignatureFileVerifier.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 2017, 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
@@ -28,25 +28,23 @@
 import java.io.ByteArrayInputStream;
 import java.io.IOException;
 import java.security.CodeSigner;
-import java.security.CryptoPrimitive;
+import java.security.GeneralSecurityException;
 import java.security.MessageDigest;
 import java.security.NoSuchAlgorithmException;
 import java.security.SignatureException;
+import java.security.Timestamp;
 import java.security.cert.CertPath;
 import java.security.cert.X509Certificate;
 import java.security.cert.CertificateException;
 import java.security.cert.CertificateFactory;
 import java.util.ArrayList;
 import java.util.Base64;
-import java.util.Collections;
-import java.util.EnumSet;
 import java.util.HashMap;
 import java.util.Hashtable;
 import java.util.Iterator;
 import java.util.List;
 import java.util.Locale;
 import java.util.Map;
-import java.util.Set;
 import java.util.jar.Attributes;
 import java.util.jar.JarException;
 import java.util.jar.JarFile;
@@ -61,9 +59,6 @@
     /* Are we debugging ? */
     private static final Debug debug = Debug.getInstance("jar");
 
-    private static final Set<CryptoPrimitive> DIGEST_PRIMITIVE_SET =
-            Collections.unmodifiableSet(EnumSet.of(CryptoPrimitive.MESSAGE_DIGEST));
-
     private static final DisabledAlgorithmConstraints JAR_DISABLED_CHECK =
             new DisabledAlgorithmConstraints(
                     DisabledAlgorithmConstraints.PROPERTY_JAR_DISABLED_ALGS);
@@ -97,6 +92,14 @@
     /* for generating certpath objects */
     private CertificateFactory certificateFactory = null;
 
+    /** Algorithms that have been checked if they are weak. */
+    private Map<String, Boolean> permittedAlgs= new HashMap<>();
+
+    /** TSA timestamp of signed jar.  The newest timestamp is used.  If there
+     *  was no TSA timestamp used when signed, current time is used ("null").
+     */
+    private Timestamp timestamp = null;
+
     /**
      * Create the named SignatureFileVerifier.
      *
@@ -222,15 +225,8 @@
 
     /** get digest from cache */
 
-    private MessageDigest getDigest(String algorithm) throws SignatureException {
-        // check that algorithm is not restricted
-        if (!JAR_DISABLED_CHECK.permits(DIGEST_PRIMITIVE_SET, algorithm, null)) {
-            SignatureException e =
-                    new SignatureException("SignatureFile check failed. " +
-                            "Disabled algorithm used: " + algorithm);
-            throw e;
-        }
-
+    private MessageDigest getDigest(String algorithm)
+            throws SignatureException {
         if (createdDigests == null)
             createdDigests = new HashMap<>();
 
@@ -302,6 +298,27 @@
         if (newSigners == null)
             return;
 
+        /*
+         * Look for the latest timestamp in the signature block.  If an entry
+         * has no timestamp, use current time (aka null).
+         */
+        for (CodeSigner s: newSigners) {
+            if (debug != null) {
+                debug.println("Gathering timestamp for:  " + s.toString());
+            }
+            if (s.getTimestamp() == null) {
+                timestamp = null;
+                break;
+            } else if (timestamp == null) {
+                timestamp = s.getTimestamp();
+            } else {
+                if (timestamp.getTimestamp().before(
+                        s.getTimestamp().getTimestamp())) {
+                    timestamp = s.getTimestamp();
+                }
+            }
+        }
+
         Iterator<Map.Entry<String,Attributes>> entries =
                                 sf.getEntries().entrySet().iterator();
 
@@ -345,6 +362,68 @@
     }
 
     /**
+     * Check if algorithm is permitted using the permittedAlgs Map.
+     * If the algorithm is not in the map, check against disabled algorithms and
+     * store the result. If the algorithm is in the map use that result.
+     * False is returned for weak algorithm, true for good algorithms.
+     */
+    boolean permittedCheck(String key, String algorithm) {
+        Boolean permitted = permittedAlgs.get(algorithm);
+        if (permitted == null) {
+            try {
+                JAR_DISABLED_CHECK.permits(algorithm,
+                        new ConstraintsParameters(timestamp));
+            } catch(GeneralSecurityException e) {
+                permittedAlgs.put(algorithm, Boolean.FALSE);
+                permittedAlgs.put(key.toUpperCase(), Boolean.FALSE);
+                if (debug != null) {
+                    if (e.getMessage() != null) {
+                        debug.println(key + ":  " + e.getMessage());
+                    } else {
+                        debug.println(key + ":  " + algorithm +
+                                " was disabled, no exception msg given.");
+                        e.printStackTrace();
+                    }
+                }
+                return false;
+            }
+
+            permittedAlgs.put(algorithm, Boolean.TRUE);
+            return true;
+        }
+
+        // Algorithm has already been checked, return the value from map.
+        return permitted.booleanValue();
+    }
+
+    /**
+     * With a given header (*-DIGEST*), return a string that lists all the
+     * algorithms associated with the header.
+     * If there are none, return "Unknown Algorithm".
+     */
+    String getWeakAlgorithms(String header) {
+        String w = "";
+        try {
+            for (String key : permittedAlgs.keySet()) {
+                if (key.endsWith(header)) {
+                    w += key.substring(0, key.length() - header.length()) + " ";
+                }
+            }
+        } catch (RuntimeException e) {
+            w = "Unknown Algorithm(s).  Error processing " + header + ".  " +
+                    e.getMessage();
+        }
+
+        // This means we have an error in finding weak algorithms, run in
+        // debug mode to see permittedAlgs map's values.
+        if (w.length() == 0) {
+            return "Unknown Algorithm(s)";
+        }
+
+        return w;
+    }
+
+    /**
      * See if the whole manifest was signed.
      */
     private boolean verifyManifestHash(Manifest sf,
@@ -354,6 +433,7 @@
     {
         Attributes mattr = sf.getMainAttributes();
         boolean manifestSigned = false;
+        boolean weakAlgs = true;
 
         // go through all the attributes and process *-Digest-Manifest entries
         for (Map.Entry<Object,Object> se : mattr.entrySet()) {
@@ -364,6 +444,15 @@
                 // 16 is length of "-Digest-Manifest"
                 String algorithm = key.substring(0, key.length()-16);
 
+                // Check if this algorithm is permitted, skip if false.
+                if (!permittedCheck(key, algorithm)) {
+                    continue;
+                }
+
+                // A non-weak algorithm was used, any weak algorithms found do
+                // not need to be reported.
+                weakAlgs = false;
+
                 manifestDigests.add(key);
                 manifestDigests.add(se.getValue());
                 MessageDigest digest = getDigest(algorithm);
@@ -373,15 +462,14 @@
                         Base64.getMimeDecoder().decode((String)se.getValue());
 
                     if (debug != null) {
-                     debug.println("Signature File: Manifest digest " +
-                                          digest.getAlgorithm());
-                     debug.println( "  sigfile  " + toHex(expectedHash));
-                     debug.println( "  computed " + toHex(computedHash));
-                     debug.println();
+                        debug.println("Signature File: Manifest digest " +
+                                algorithm);
+                        debug.println( "  sigfile  " + toHex(expectedHash));
+                        debug.println( "  computed " + toHex(computedHash));
+                        debug.println();
                     }
 
-                    if (MessageDigest.isEqual(computedHash,
-                                              expectedHash)) {
+                    if (MessageDigest.isEqual(computedHash, expectedHash)) {
                         manifestSigned = true;
                     } else {
                         //XXX: we will continue and verify each section
@@ -389,15 +477,31 @@
                 }
             }
         }
+
+        if (debug != null) {
+            debug.println("PermittedAlgs mapping: ");
+            for (String key : permittedAlgs.keySet()) {
+                debug.println(key + " : " +
+                        permittedAlgs.get(key).toString());
+            }
+        }
+
+        // If there were only weak algorithms used, throw an exception.
+        if (weakAlgs) {
+            String weakAlgorithms = getWeakAlgorithms("-DIGEST-MANIFEST");
+            throw new SignatureException("Manifest hash check failed " +
+                    "(DIGEST-MANIFEST). Disabled algorithm(s) used: " +
+                    weakAlgorithms);
+        }
         return manifestSigned;
     }
 
-    private boolean verifyManifestMainAttrs(Manifest sf,
-                                        ManifestDigester md)
+    private boolean verifyManifestMainAttrs(Manifest sf, ManifestDigester md)
          throws IOException, SignatureException
     {
         Attributes mattr = sf.getMainAttributes();
         boolean attrsVerified = true;
+        boolean weakAlgs = true;
 
         // go through all the attributes and process
         // digest entries for the manifest main attributes
@@ -408,6 +512,15 @@
                 String algorithm =
                         key.substring(0, key.length() - ATTR_DIGEST.length());
 
+                // Check if this algorithm is permitted, skip if false.
+                if (!permittedCheck(key, algorithm)) {
+                    continue;
+                }
+
+                // A non-weak algorithm was used, any weak algorithms found do
+                // not need to be reported.
+                weakAlgs = false;
+
                 MessageDigest digest = getDigest(algorithm);
                 if (digest != null) {
                     ManifestDigester.Entry mde =
@@ -425,8 +538,7 @@
                      debug.println();
                     }
 
-                    if (MessageDigest.isEqual(computedHash,
-                                              expectedHash)) {
+                    if (MessageDigest.isEqual(computedHash, expectedHash)) {
                         // good
                     } else {
                         // we will *not* continue and verify each section
@@ -442,6 +554,23 @@
             }
         }
 
+        if (debug != null) {
+            debug.println("PermittedAlgs mapping: ");
+            for (String key : permittedAlgs.keySet()) {
+                debug.println(key + " : " +
+                        permittedAlgs.get(key).toString());
+            }
+        }
+
+        // If there were only weak algorithms used, throw an exception.
+        if (weakAlgs) {
+            String weakAlgorithms = getWeakAlgorithms("-DIGEST-" +
+                    ManifestDigester.MF_MAIN_ATTRS);
+            throw new SignatureException("Manifest Main Attribute check " +
+                    "failed (DIGEST-" + ManifestDigester.MF_MAIN_ATTRS +
+                    "). " + "Disabled algorithm(s) used: " + weakAlgorithms);
+        }
+
         // this method returns 'true' if either:
         //      . manifest main attributes were not signed, or
         //      . manifest main attributes were signed and verified
@@ -464,6 +593,7 @@
     {
         boolean oneDigestVerified = false;
         ManifestDigester.Entry mde = md.get(name,block.isOldStyle());
+        boolean weakAlgs = true;
 
         if (mde == null) {
             throw new SecurityException(
@@ -471,7 +601,6 @@
         }
 
         if (sfAttr != null) {
-
             //sun.security.util.HexDumpEncoder hex = new sun.security.util.HexDumpEncoder();
             //hex.encodeBuffer(data, System.out);
 
@@ -483,6 +612,15 @@
                     // 7 is length of "-Digest"
                     String algorithm = key.substring(0, key.length()-7);
 
+                    // Check if this algorithm is permitted, skip if false.
+                    if (!permittedCheck(key, algorithm)) {
+                        continue;
+                    }
+
+                    // A non-weak algorithm was used, any weak algorithms found do
+                    // not need to be reported.
+                    weakAlgs = false;
+
                     MessageDigest digest = getDigest(algorithm);
 
                     if (digest != null) {
@@ -532,6 +670,23 @@
                 }
             }
         }
+
+        if (debug != null) {
+            debug.println("PermittedAlgs mapping: ");
+            for (String key : permittedAlgs.keySet()) {
+                debug.println(key + " : " +
+                        permittedAlgs.get(key).toString());
+            }
+        }
+
+        // If there were only weak algorithms used, throw an exception.
+        if (weakAlgs) {
+            String weakAlgorithms = getWeakAlgorithms("DIGEST");
+            throw new SignatureException("Manifest Main Attribute check " +
+                    "failed (DIGEST). " + "Disabled algorithm(s) used: " +
+                    weakAlgorithms);
+        }
+
         return oneDigestVerified;
     }
 
--- a/jdk/src/java.base/share/classes/sun/security/validator/PKIXValidator.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/sun/security/validator/PKIXValidator.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2002, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2002, 2017, 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
@@ -33,7 +33,7 @@
 import javax.security.auth.x500.X500Principal;
 import sun.security.action.GetBooleanAction;
 import sun.security.provider.certpath.AlgorithmChecker;
-import sun.security.provider.certpath.PKIXTimestampParameters;
+import sun.security.provider.certpath.PKIXExtendedParameters;
 
 /**
  * Validator implementation built on the PKIX CertPath API. This
@@ -199,9 +199,9 @@
         PKIXBuilderParameters pkixParameters = null;
         if (parameter instanceof Timestamp && plugin) {
             try {
-                pkixParameters = new PKIXTimestampParameters(
+                pkixParameters = new PKIXExtendedParameters(
                         (PKIXBuilderParameters) parameterTemplate.clone(),
-                        (Timestamp) parameter);
+                        (Timestamp) parameter, variant);
             } catch (InvalidAlgorithmParameterException e) {
                 // ignore exception
             }
@@ -211,7 +211,8 @@
 
         // add new algorithm constraints checker
         if (constraints != null) {
-            pkixParameters.addCertPathChecker(new AlgorithmChecker(constraints));
+            pkixParameters.addCertPathChecker(
+                    new AlgorithmChecker(constraints, null, variant));
         }
 
         // attach it to the PKIXBuilderParameters.
--- a/jdk/src/java.base/share/classes/sun/security/validator/SimpleValidator.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/classes/sun/security/validator/SimpleValidator.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2002, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2002, 2017, 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
@@ -155,12 +155,14 @@
 
         // create default algorithm constraints checker
         TrustAnchor anchor = new TrustAnchor(anchorCert, null);
-        AlgorithmChecker defaultAlgChecker = new AlgorithmChecker(anchor);
+        AlgorithmChecker defaultAlgChecker =
+                new AlgorithmChecker(anchor, variant);
 
         // create application level algorithm constraints checker
         AlgorithmChecker appAlgChecker = null;
         if (constraints != null) {
-            appAlgChecker = new AlgorithmChecker(anchor, constraints);
+            appAlgChecker = new AlgorithmChecker(anchor, constraints, null,
+                    variant);
         }
 
         // verify top down, starting at the certificate issued by
--- a/jdk/src/java.base/share/conf/security/java.security	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/conf/security/java.security	Wed Jul 05 22:52:01 2017 +0200
@@ -116,6 +116,13 @@
 # Example:
 #   jdk.security.provider.preferred=AES/GCM/NoPadding:SunJCE, \
 #         MessageDigest.SHA-256:SUN, Group.HmacSHA2:SunJCE
+#
+#ifdef solaris-sparc
+# Optional Solaris-SPARC configuration for non-FIPS 140 configurations.
+#   jdk.security.provider.preferred=AES:SunJCE, SHA1:SUN, Group.SHA2:SUN, \
+#   HmacSHA1:SunJCE, Group.HmacSHA2:SunJCE
+#
+#endif
 #jdk.security.provider.preferred=
 
 
@@ -240,6 +247,7 @@
 #
 # The default value is an empty string, which is equivalent to
 #   securerandom.drbg.config=Hash_DRBG,SHA-256,128,none
+#
 securerandom.drbg.config=
 
 #
@@ -262,23 +270,27 @@
 
 # The default is to have a single system-wide policy file,
 # and a policy file in the user's home directory.
+#
 policy.url.1=file:${java.home}/conf/security/java.policy
 policy.url.2=file:${user.home}/.java.policy
 
 # whether or not we expand properties in the policy file
 # if this is set to false, properties (${...}) will not be expanded in policy
 # files.
+#
 policy.expandProperties=true
 
 # whether or not we allow an extra policy to be passed on the command line
 # with -Djava.security.policy=somefile. Comment out this line to disable
 # this feature.
+#
 policy.allowSystemProperty=true
 
 # whether or not we look into the IdentityScope for trusted Identities
 # when encountering a 1.1 signed JAR file. If the identity is found
 # and is trusted, we grant it AllPermission. Note: the default policy
 # provider (sun.security.provider.PolicyFile) does not support this property.
+#
 policy.ignoreIdentityScope=false
 
 #
@@ -360,7 +372,6 @@
 # For this reason the default caching policy is to maintain these
 # results for 10 seconds.
 #
-#
 networkaddress.cache.negative.ttl=10
 
 #
@@ -460,8 +471,10 @@
 # Example,
 #   krb5.kdc.bad.policy = tryLast
 #   krb5.kdc.bad.policy = tryLess:2,2000
+#
 krb5.kdc.bad.policy = tryLast
 
+#
 # Algorithm restrictions for certification path (CertPath) processing
 #
 # In some environments, certain algorithms or key lengths may be undesirable
@@ -481,7 +494,8 @@
 #       (see below)
 #
 #   Constraint:
-#       KeySizeConstraint | CAConstraint | DenyAfterConstraint
+#       KeySizeConstraint | CAConstraint | DenyAfterConstraint |
+#       UsageConstraint
 #
 #   KeySizeConstraint:
 #       keySize Operator KeyLength
@@ -498,6 +512,9 @@
 #   DenyAfterConstraint:
 #       denyAfter YYYY-MM-DD
 #
+#   UsageConstraint:
+#       usage [TLSServer] [TLSClient] [SignedJAR]
+#
 # The "AlgorithmName" is the standard algorithm name of the disabled
 # algorithm. See "Java Cryptography Architecture Standard Algorithm Name
 # Documentation" for information about Standard Algorithm Names.  Matching
@@ -547,6 +564,19 @@
 #       Example:  To deny usage of RSA 2048 bit certificates after Feb 3 2020,
 #       use the following:  "RSA keySize == 2048 & denyAfter 2020-02-03"
 #
+#   UsageConstraint:
+#     usage [TLSServer] [TLSClient] [SignedJAR]
+#       This constraint prohibits the specified algorithm for
+#       a specified usage.  This should be used when disabling an algorithm
+#       for all usages is not practical. 'TLSServer' restricts the algorithm
+#       in TLS server certificate chains when server authentication is
+#       performed. 'TLSClient' restricts the algorithm in TLS client
+#       certificate chains when client authentication is performed.
+#       'SignedJAR' constrains use of certificates in signed jar files.
+#       The usage type follows the keyword and more than one usage type can
+#       be specified with a whitespace delimiter.
+#       Example:  "SHA1 usage TLSServer TLSClient"
+#
 # When an algorithm must satisfy more than one constraint, it must be
 # delimited by an ampersand '&'.  For example, to restrict certificates in a
 # chain that terminate at a distribution provided trust anchor and contain
@@ -572,35 +602,6 @@
     RSA keySize < 1024, DSA keySize < 1024, EC keySize < 224
 
 #
-# RMI Registry Serial Filter
-#
-# The filter pattern uses the same format as jdk.serialFilter.
-# This filter can override the builtin filter if additional types need to be
-# allowed or rejected from the RMI Registry.
-#
-# Note: This property is currently used by the JDK Reference implementation.
-# It is not guaranteed to be examined and used by other implementations.
-#
-#sun.rmi.registry.registryFilter=pattern;pattern
-#
-# RMI Distributed Garbage Collector (DGC) Serial Filter
-#
-# The filter pattern uses the same format as jdk.serialFilter.
-# This filter can override the builtin filter if additional types need to be
-# allowed or rejected from the RMI DGC.
-#
-# Note: This property is currently used by the JDK Reference implementation.
-# It is not guaranteed to be examined and used by other implementations.
-#
-# The builtin DGC filter can approximately be represented as the filter pattern:
-#
-#sun.rmi.transport.dgcFilter=\
-#    java.rmi.server.ObjID;\
-#    java.rmi.server.UID;\
-#    java.rmi.dgc.VMID;\
-#    java.rmi.dgc.Lease;\
-#    maxdepth=5;maxarray=10000
-
 # Algorithm restrictions for signed JAR files
 #
 # In some environments, certain algorithms or key lengths may be undesirable
@@ -615,17 +616,20 @@
 #       " DisabledAlgorithm { , DisabledAlgorithm } "
 #
 #   DisabledAlgorithm:
-#       AlgorithmName [Constraint]
+#       AlgorithmName [Constraint] { '&' Constraint }
 #
 #   AlgorithmName:
 #       (see below)
 #
 #   Constraint:
-#       KeySizeConstraint
+#       KeySizeConstraint | DenyAfterConstraint
 #
 #   KeySizeConstraint:
 #       keySize Operator KeyLength
 #
+#   DenyAfterConstraint:
+#       denyAfter YYYY-MM-DD
+#
 #   Operator:
 #       <= | < | == | != | >= | >
 #
@@ -636,9 +640,12 @@
 # implementation. It is not guaranteed to be examined and used by other
 # implementations.
 #
+# See "jdk.certpath.disabledAlgorithms" for syntax descriptions.
+#
 jdk.jar.disabledAlgorithms=MD2, MD5, RSA keySize < 1024, \
       DSA keySize < 1024
 
+#
 # Algorithm restrictions for Secure Socket Layer/Transport Layer Security
 # (SSL/TLS/DTLS) processing
 #
@@ -939,3 +946,32 @@
 #
 #jdk.serialFilter=pattern;pattern
 
+#
+# RMI Registry Serial Filter
+#
+# The filter pattern uses the same format as jdk.serialFilter.
+# This filter can override the builtin filter if additional types need to be
+# allowed or rejected from the RMI Registry.
+#
+# Note: This property is currently used by the JDK Reference implementation.
+# It is not guaranteed to be examined and used by other implementations.
+#
+#sun.rmi.registry.registryFilter=pattern;pattern
+#
+# RMI Distributed Garbage Collector (DGC) Serial Filter
+#
+# The filter pattern uses the same format as jdk.serialFilter.
+# This filter can override the builtin filter if additional types need to be
+# allowed or rejected from the RMI DGC.
+#
+# Note: This property is currently used by the JDK Reference implementation.
+# It is not guaranteed to be examined and used by other implementations.
+#
+# The builtin DGC filter can approximately be represented as the filter pattern:
+#
+#sun.rmi.transport.dgcFilter=\
+#    java.rmi.server.ObjID;\
+#    java.rmi.server.UID;\
+#    java.rmi.dgc.VMID;\
+#    java.rmi.dgc.Lease;\
+#    maxdepth=5;maxarray=10000
--- a/jdk/src/java.base/share/lib/security/default.policy	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/lib/security/default.policy	Wed Jul 05 22:52:01 2017 +0200
@@ -102,6 +102,8 @@
 };
 
 grant codeBase "jrt:/java.xml.ws" {
+    permission java.net.NetPermission
+                   "getProxySelector";
     permission java.lang.RuntimePermission
                    "accessClassInPackage.com.sun.org.apache.xml.internal.resolver";
     permission java.lang.RuntimePermission
@@ -213,3 +215,7 @@
     permission java.lang.RuntimePermission "accessClassInPackage.com.sun.java.swing.plaf.*";
     permission java.lang.RuntimePermission "accessClassInPackage.com.apple.*";
 };
+
+grant codeBase "jrt:/jdk.vm.compiler" {
+    permission java.security.AllPermission;
+};
--- a/jdk/src/java.base/share/native/launcher/main.c	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/native/launcher/main.c	Wed Jul 05 22:52:01 2017 +0200
@@ -130,10 +130,10 @@
 
         // Add first arg, which is the app name
         JLI_List_add(args, JLI_StringDup(argv[0]));
-        // Append JAVA_OPTIONS
-        if (JLI_AddArgsFromEnvVar(args, JAVA_OPTIONS)) {
+        // Append JDK_JAVA_OPTIONS
+        if (JLI_AddArgsFromEnvVar(args, JDK_JAVA_OPTIONS)) {
             // JLI_SetTraceLauncher is not called yet
-            // Show _JAVA_OPTIONS content along with JAVA_OPTIONS to aid diagnosis
+            // Show _JAVA_OPTIONS content along with JDK_JAVA_OPTIONS to aid diagnosis
             if (getenv(JLDEBUG_ENV_ENTRY)) {
                 char *tmp = getenv("_JAVA_OPTIONS");
                 if (NULL != tmp) {
--- a/jdk/src/java.base/share/native/libjli/args.c	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/native/libjli/args.c	Wed Jul 05 22:52:01 2017 +0200
@@ -34,7 +34,7 @@
     #define NO_JNI
   #endif
   #define JLI_ReportMessage(...) printf(__VA_ARGS__)
-  #define JAVA_OPTIONS "JAVA_OPTIONS"
+  #define JDK_JAVA_OPTIONS "JDK_JAVA_OPTIONS"
   int IsWhiteSpaceOption(const char* name) { return 1; }
 #else
   #include "java.h"
@@ -429,10 +429,6 @@
 }
 
 jboolean JLI_AddArgsFromEnvVar(JLI_List args, const char *var_name) {
-
-#ifndef ENABLE_JAVA_OPTIONS
-    return JNI_FALSE;
-#else
     char *env = getenv(var_name);
     char *p, *arg;
     char quote;
@@ -519,7 +515,6 @@
     }
 
     return JNI_TRUE;
-#endif
 }
 
 #ifdef DEBUG_ARGFILE
--- a/jdk/src/java.base/share/native/libjli/java.h	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/share/native/libjli/java.h	Wed Jul 05 22:52:01 2017 +0200
@@ -71,7 +71,7 @@
 
 #define SPLASH_FILE_ENV_ENTRY "_JAVA_SPLASH_FILE"
 #define SPLASH_JAR_ENV_ENTRY "_JAVA_SPLASH_JAR"
-#define JAVA_OPTIONS "JAVA_OPTIONS"
+#define JDK_JAVA_OPTIONS "JDK_JAVA_OPTIONS"
 
 /*
  * Pointers to the needed JNI invocation API, initialized by LoadJavaVM.
--- a/jdk/src/java.base/windows/native/libjli/cmdtoargs.c	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.base/windows/native/libjli/cmdtoargs.c	Wed Jul 05 22:52:01 2017 +0200
@@ -205,9 +205,9 @@
     size_t i, cnt;
 
     JLI_List envArgs = JLI_List_new(1);
-    if (JLI_AddArgsFromEnvVar(envArgs, JAVA_OPTIONS)) {
+    if (JLI_AddArgsFromEnvVar(envArgs, JDK_JAVA_OPTIONS)) {
         // JLI_SetTraceLauncher is not called yet
-        // Show _JAVA_OPTIONS content along with JAVA_OPTIONS to aid diagnosis
+        // Show _JAVA_OPTIONS content along with JDK_JAVA_OPTIONS to aid diagnosis
         if (getenv(JLDEBUG_ENV_ENTRY)) {
             char *tmp = getenv("_JAVA_OPTIONS");
             if (NULL != tmp) {
--- a/jdk/src/java.datatransfer/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.datatransfer/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Defines an API for transferring data between and within applications.
+ *
+ * @since 9
  */
 module java.datatransfer {
     exports java.awt.datatransfer;
--- a/jdk/src/java.desktop/macosx/classes/com/apple/laf/AquaComboBoxPopup.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/macosx/classes/com/apple/laf/AquaComboBoxPopup.java	Wed Jul 05 22:52:01 2017 +0200
@@ -154,9 +154,15 @@
     protected JList<Object> createList() {
         return new JList<Object>(comboBox.getModel()) {
             @Override
+            @SuppressWarnings("deprecation")
             public void processMouseEvent(MouseEvent e) {
                 if (e.isMetaDown()) {
-                    e = new MouseEvent((Component)e.getSource(), e.getID(), e.getWhen(), e.getModifiers() ^ InputEvent.META_MASK, e.getX(), e.getY(), e.getXOnScreen(), e.getYOnScreen(), e.getClickCount(), e.isPopupTrigger(), MouseEvent.NOBUTTON);
+                    e = new MouseEvent((Component) e.getSource(), e.getID(),
+                                       e.getWhen(),
+                                       e.getModifiers() ^ InputEvent.META_MASK,
+                                       e.getX(), e.getY(), e.getXOnScreen(),
+                                       e.getYOnScreen(), e.getClickCount(),
+                                       e.isPopupTrigger(), MouseEvent.NOBUTTON);
                 }
                 super.processMouseEvent(e);
             }
--- a/jdk/src/java.desktop/macosx/classes/com/apple/laf/AquaInternalFrameDockIconUI.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/macosx/classes/com/apple/laf/AquaInternalFrameDockIconUI.java	Wed Jul 05 22:52:01 2017 +0200
@@ -137,6 +137,7 @@
     }
 
     @Override
+    @SuppressWarnings("deprecation")
     public void mouseEntered(final MouseEvent e) {
         if ((e.getModifiers() & InputEvent.BUTTON1_MASK) != 0) return;
         String title = fFrame.getTitle();
@@ -146,6 +147,7 @@
     }
 
     @Override
+    @SuppressWarnings("deprecation")
     public void mouseExited(final MouseEvent e) {
         if (fDockLabel != null && (e.getModifiers() & InputEvent.BUTTON1_MASK) == 0) fDockLabel.hide();
     }
--- a/jdk/src/java.desktop/macosx/classes/com/apple/laf/AquaInternalFrameUI.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/macosx/classes/com/apple/laf/AquaInternalFrameUI.java	Wed Jul 05 22:52:01 2017 +0200
@@ -555,6 +555,7 @@
         }
 
         @Override
+        @SuppressWarnings("deprecation")
         public void mouseDragged(final MouseEvent e) {
 // do not forward drags
 //            if (didForwardEvent(e)) return;
@@ -621,7 +622,7 @@
 
             return didForwardEvent;
         }
-
+        @SuppressWarnings("deprecation")
         boolean didForwardEventInternal(final MouseEvent e) {
             if (fDraggingFrame) return false;
 
@@ -927,11 +928,15 @@
             return (w - x) + (h - y) < 12;
         }
 
+        @SuppressWarnings("deprecation")
         void forwardEventToFrame(final MouseEvent e) {
             final Point pt = new Point();
             final Component c = getComponentToForwardTo(e, pt);
             if (c == null) return;
-            c.dispatchEvent(new MouseEvent(c, e.getID(), e.getWhen(), e.getModifiers(), pt.x, pt.y, e.getClickCount(), e.isPopupTrigger(), e.getButton()));
+            c.dispatchEvent(
+                    new MouseEvent(c, e.getID(), e.getWhen(), e.getModifiers(),
+                                   pt.x, pt.y, e.getClickCount(),
+                                   e.isPopupTrigger(), e.getButton()));
         }
 
         Component getComponentToForwardTo(final MouseEvent e, final Point dst) {
@@ -993,6 +998,7 @@
         public void mouseMoved(final MouseEvent e) { }
 
         @Override
+        @SuppressWarnings("deprecation")
         public void mouseWheelMoved(final MouseWheelEvent e) {
             final Point pt = new Point();
             final Component c = getComponentToForwardTo(e, pt);
--- a/jdk/src/java.desktop/macosx/classes/com/apple/laf/AquaMenuPainter.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/macosx/classes/com/apple/laf/AquaMenuPainter.java	Wed Jul 05 22:52:01 2017 +0200
@@ -74,7 +74,10 @@
         kUCapsLockGlyph = 0x21EA;
 
     static final int ALT_GRAPH_MASK = 1 << 5; // New to Java2
-    static final int sUnsupportedModifiersMask = ~(InputEvent.CTRL_MASK | InputEvent.ALT_MASK | InputEvent.SHIFT_MASK | InputEvent.META_MASK | ALT_GRAPH_MASK);
+    @SuppressWarnings("deprecation")
+    static final int sUnsupportedModifiersMask =
+            ~(InputEvent.CTRL_MASK | InputEvent.ALT_MASK | InputEvent.SHIFT_MASK
+                    | InputEvent.META_MASK | ALT_GRAPH_MASK);
 
     interface Client {
         public void paintBackground(Graphics g, JComponent c, int menuWidth, int menuHeight);
@@ -86,6 +89,7 @@
     }
 
     // Return a string with the proper modifier glyphs
+    @SuppressWarnings("deprecation")
     private static String getKeyModifiersUnicode(final int modifiers, final boolean isLeftToRight) {
         final StringBuilder buf = new StringBuilder(2);
         // Order (from StandardMenuDef.c): control, option(alt), shift, cmd
--- a/jdk/src/java.desktop/macosx/classes/com/apple/laf/AquaTabbedPaneCopyFromBasicUI.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/macosx/classes/com/apple/laf/AquaTabbedPaneCopyFromBasicUI.java	Wed Jul 05 22:52:01 2017 +0200
@@ -515,6 +515,7 @@
     /**
      * Adds the specified mnemonic at the specified index.
      */
+    @SuppressWarnings("deprecation")
     private void addMnemonic(final int index, final int mnemonic) {
         if (mnemonicToIndexMap == null) {
             initMnemonics();
--- a/jdk/src/java.desktop/macosx/classes/sun/lwawt/LWComponentPeer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/macosx/classes/sun/lwawt/LWComponentPeer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1224,6 +1224,7 @@
      * Changes the target of the AWTEvent from awt component to appropriate
      * swing delegate.
      */
+    @SuppressWarnings("deprecation")
     private AWTEvent createDelegateEvent(final AWTEvent e) {
         // TODO modifiers should be changed to getModifiers()|getModifiersEx()?
         AWTEvent delegateEvent = null;
--- a/jdk/src/java.desktop/macosx/classes/sun/lwawt/LWListPeer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/macosx/classes/sun/lwawt/LWListPeer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -302,6 +302,7 @@
             }
 
             @Override
+            @SuppressWarnings("deprecation")
             protected void processMouseEvent(final MouseEvent e) {
                 super.processMouseEvent(e);
                 if (e.getID() == MouseEvent.MOUSE_CLICKED && e.getClickCount() == 2) {
@@ -314,6 +315,7 @@
             }
 
             @Override
+            @SuppressWarnings("deprecation")
             protected void processKeyEvent(final KeyEvent e) {
                 super.processKeyEvent(e);
                 if (e.getID() == KeyEvent.KEY_PRESSED && e.getKeyCode() == KeyEvent.VK_ENTER) {
--- a/jdk/src/java.desktop/macosx/classes/sun/lwawt/macosx/CDragSourceContextPeer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/macosx/classes/sun/lwawt/macosx/CDragSourceContextPeer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -93,6 +93,7 @@
         InputEvent         triggerEvent = trigger.getTriggerEvent();
 
         Point dragOrigin = new Point(trigger.getDragOrigin());
+        @SuppressWarnings("deprecation")
         int extModifiers = (triggerEvent.getModifiers() | triggerEvent.getModifiersEx());
         long timestamp   = triggerEvent.getWhen();
         int clickCount   = ((triggerEvent instanceof MouseEvent) ? (((MouseEvent) triggerEvent).getClickCount()) : 1);
--- a/jdk/src/java.desktop/macosx/classes/sun/lwawt/macosx/CMenuItem.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/macosx/classes/sun/lwawt/macosx/CMenuItem.java	Wed Jul 05 22:52:01 2017 +0200
@@ -63,7 +63,7 @@
         CMenuComponent parent = (CMenuComponent)LWToolkit.targetToPeer(getTarget().getParent());
         return parent.executeGet(ptr->nativeCreate(ptr, isSeparator()));
     }
-
+    @SuppressWarnings("deprecation")
     public void setLabel(String label, char keyChar, int keyCode, int modifiers) {
         int keyMask = modifiers;
         if (keyCode == KeyEvent.VK_UNDEFINED) {
--- a/jdk/src/java.desktop/macosx/classes/sun/lwawt/macosx/CPopupMenu.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/macosx/classes/sun/lwawt/macosx/CPopupMenu.java	Wed Jul 05 22:52:01 2017 +0200
@@ -46,6 +46,7 @@
     private native long nativeShowPopupMenu(long modelPtr, int x, int y);
 
     @Override
+    @SuppressWarnings("deprecation")
     public void show(Event e) {
         Component origin = (Component)e.target;
         if (origin != null) {
--- a/jdk/src/java.desktop/macosx/classes/sun/lwawt/macosx/CPrinterDialogPeer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/macosx/classes/sun/lwawt/macosx/CPrinterDialogPeer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -68,6 +68,7 @@
     public void setResizable(boolean resizable) {}
     public void setEnabled(boolean enable) {}
     public void setBounds(int x, int y, int width, int height) {}
+    @SuppressWarnings("deprecation")
     public boolean handleEvent(Event e) { return false; }
     public void setForeground(Color c) {}
     public void setBackground(Color c) {}
--- a/jdk/src/java.desktop/macosx/classes/sun/lwawt/macosx/LWCToolkit.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/macosx/classes/sun/lwawt/macosx/LWCToolkit.java	Wed Jul 05 22:52:01 2017 +0200
@@ -532,6 +532,7 @@
      * @since     1.1
      */
     @Override
+    @SuppressWarnings("deprecation")
     public int getMenuShortcutKeyMask() {
         return Event.META_MASK;
     }
@@ -768,6 +769,7 @@
      * stroke.
      */
     @Override
+    @SuppressWarnings("deprecation")
     public int getFocusAcceleratorKeyMask() {
         return InputEvent.CTRL_MASK | InputEvent.ALT_MASK;
     }
@@ -777,6 +779,7 @@
      * printable character.
      */
     @Override
+    @SuppressWarnings("deprecation")
     public boolean isPrintableCharacterModifiersMask(int mods) {
         return ((mods & (InputEvent.META_MASK | InputEvent.CTRL_MASK)) == 0);
     }
--- a/jdk/src/java.desktop/macosx/native/libawt_lwawt/awt/JavaComponentAccessibility.m	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/macosx/native/libawt_lwawt/awt/JavaComponentAccessibility.m	Wed Jul 05 22:52:01 2017 +0200
@@ -136,7 +136,7 @@
         fJavaRole = [javaRole retain];
 
         fAccessible = (*env)->NewWeakGlobalRef(env, accessible);
-        
+        (*env)->ExceptionClear(env); // in case of OOME
         jobject jcomponent = [(AWTView *)fView awtComponent:env];
         fComponent = (*env)->NewWeakGlobalRef(env, jcomponent);
         (*env)->DeleteLocalRef(env, jcomponent);
--- a/jdk/src/java.desktop/share/classes/com/sun/awt/AWTUtilities.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/com/sun/awt/AWTUtilities.java	Wed Jul 05 22:52:01 2017 +0200
@@ -456,8 +456,7 @@
                     "The component argument should not be null.");
         }
 
-        AWTAccessor.getComponentAccessor().setMixingCutoutShape(component,
-                shape);
+        component.setMixingCutoutShape(shape);
     }
 }
 
--- a/jdk/src/java.desktop/share/classes/com/sun/java/swing/plaf/motif/MotifDesktopIconUI.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/com/sun/java/swing/plaf/motif/MotifDesktopIconUI.java	Wed Jul 05 22:52:01 2017 +0200
@@ -236,7 +236,7 @@
                 }
             });
         }
-
+        @SuppressWarnings("deprecation")
         void forwardEventToParent(MouseEvent e) {
             getParent().dispatchEvent(new MouseEvent(
                 getParent(), e.getID(), e.getWhen(), e.getModifiers(),
@@ -329,7 +329,7 @@
                 }
             });
         }
-
+        @SuppressWarnings("deprecation")
         void forwardEventToParent(MouseEvent e) {
             getParent().dispatchEvent(new MouseEvent(
                 getParent(), e.getID(), e.getWhen(), e.getModifiers(),
--- a/jdk/src/java.desktop/share/classes/com/sun/java/swing/plaf/motif/MotifGraphicsUtils.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/com/sun/java/swing/plaf/motif/MotifGraphicsUtils.java	Wed Jul 05 22:52:01 2017 +0200
@@ -139,10 +139,11 @@
     }
 
   /**
-   * This method is not being used to paint menu item since
+   * @deprecated This method is not being used to paint menu item since
    * 6.0 This code left for compatibility only. Do not use or
    * override it, this will not cause any visible effect.
    */
+  @Deprecated(since = "9")
   public static void paintMenuItem(Graphics g, JComponent c,
                                    Icon checkIcon, Icon arrowIcon,
                                    Color background, Color foreground,
--- a/jdk/src/java.desktop/share/classes/com/sun/java/swing/plaf/motif/MotifInternalFrameTitlePane.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/com/sun/java/swing/plaf/motif/MotifInternalFrameTitlePane.java	Wed Jul 05 22:52:01 2017 +0200
@@ -361,7 +361,7 @@
                 }
             });
         }
-
+        @SuppressWarnings("deprecation")
         void forwardEventToParent(MouseEvent e) {
             getParent().dispatchEvent(new MouseEvent(
                 getParent(), e.getID(), e.getWhen(), e.getModifiers(),
--- a/jdk/src/java.desktop/share/classes/com/sun/java/swing/plaf/motif/MotifLookAndFeel.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/com/sun/java/swing/plaf/motif/MotifLookAndFeel.java	Wed Jul 05 22:52:01 2017 +0200
@@ -523,7 +523,8 @@
 
         Object optionPaneMessageAreaBorder = new BorderUIResource.EmptyBorderUIResource(10,10,12,10);
 
-
+        @SuppressWarnings("deprecation")
+        final int metaMask = KeyEvent.META_MASK;
         Object[] defaults = {
 
             "Desktop.background", table.get("desktop"),
@@ -635,8 +636,7 @@
             "Menu.submenuPopupOffsetX", -2,
             "Menu.submenuPopupOffsetY", 3,
             "Menu.shortcutKeys", new int[]{
-                SwingUtilities2.getSystemMnemonicKeyMask(),
-                KeyEvent.META_MASK
+                SwingUtilities2.getSystemMnemonicKeyMask(), metaMask
             },
             "Menu.cancelMode", "hideMenuTree",
 
--- a/jdk/src/java.desktop/share/classes/com/sun/java/swing/plaf/motif/MotifPopupMenuUI.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/com/sun/java/swing/plaf/motif/MotifPopupMenuUI.java	Wed Jul 05 22:52:01 2017 +0200
@@ -107,6 +107,7 @@
         };
     }
 
+    @SuppressWarnings("deprecation")
     public boolean isPopupTrigger(MouseEvent e) {
         return ((e.getID()==MouseEvent.MOUSE_PRESSED)
                 && ((e.getModifiers() & MouseEvent.BUTTON3_MASK)!=0));
--- a/jdk/src/java.desktop/share/classes/com/sun/java/swing/plaf/motif/MotifTextUI.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/com/sun/java/swing/plaf/motif/MotifTextUI.java	Wed Jul 05 22:52:01 2017 +0200
@@ -155,6 +155,7 @@
     /**
      * Default bindings all keymaps implementing the Motif feel.
      */
+    @SuppressWarnings("deprecation")
     static final JTextComponent.KeyBinding[] defaultBindings = {
         new JTextComponent.KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_INSERT,
                                                                     InputEvent.CTRL_MASK),
--- a/jdk/src/java.desktop/share/classes/com/sun/java/swing/plaf/windows/WindowsRootPaneUI.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/com/sun/java/swing/plaf/windows/WindowsRootPaneUI.java	Wed Jul 05 22:52:01 2017 +0200
@@ -165,8 +165,11 @@
         }
 
         public boolean postProcessKeyEvent(KeyEvent ev) {
-            if(ev.isConsumed()) {
-                // do not manage consumed event
+            if(ev.isConsumed() && ev.getKeyCode() != KeyEvent.VK_ALT) {
+                // mnemonic combination, it's consumed, but we need
+                // set altKeyPressed to false, otherwise after selection
+                // component by mnemonic combination a menu will be open
+                altKeyPressed = false;
                 return false;
             }
             if (ev.getKeyCode() == KeyEvent.VK_ALT) {
--- a/jdk/src/java.desktop/share/classes/com/sun/java/swing/plaf/windows/WindowsTabbedPaneUI.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/com/sun/java/swing/plaf/windows/WindowsTabbedPaneUI.java	Wed Jul 05 22:52:01 2017 +0200
@@ -63,6 +63,7 @@
 
     private boolean contentOpaque = true;
 
+    @SuppressWarnings("deprecation")
     protected void installDefaults() {
         super.installDefaults();
         contentOpaque = UIManager.getBoolean("TabbedPane.contentOpaque");
--- a/jdk/src/java.desktop/share/classes/java/awt/AWTEvent.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/java/awt/AWTEvent.java	Wed Jul 05 22:52:01 2017 +0200
@@ -292,8 +292,12 @@
 
     /**
      * Constructs an AWTEvent object from the parameters of a 1.0-style event.
+     *
      * @param event the old-style event
+     * @deprecated It is recommended that {@link #AWTEvent(Object, int)} be used
+     *             instead
      */
+    @Deprecated(since = "9")
     public AWTEvent(Event event) {
         this(event.target, event.id);
     }
@@ -436,6 +440,7 @@
      * event class in java.awt.event because we don't want to make
      * it public and it needs to be called from java.awt.
      */
+    @SuppressWarnings("deprecation")
     Event convertToOld() {
         Object src = getSource();
         int newid = id;
--- a/jdk/src/java.desktop/share/classes/java/awt/AWTKeyStroke.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/java/awt/AWTKeyStroke.java	Wed Jul 05 22:52:01 2017 +0200
@@ -350,6 +350,7 @@
      * @throws NullPointerException if {@code anEvent} is null
      * @return the {@code AWTKeyStroke} that precipitated the event
      */
+    @SuppressWarnings("deprecation")
     public static AWTKeyStroke getAWTKeyStrokeForEvent(KeyEvent anEvent) {
         int id = anEvent.getID();
         switch(id) {
@@ -397,6 +398,7 @@
      * @throws IllegalArgumentException if {@code s} is {@code null},
      *        or is formatted incorrectly
      */
+    @SuppressWarnings("deprecation")
     public static AWTKeyStroke getAWTKeyStroke(String s) {
         if (s == null) {
             throw new IllegalArgumentException("String cannot be null");
@@ -708,6 +710,7 @@
         }
     }
 
+    @SuppressWarnings("deprecation")
     private static int mapOldModifiers(int modifiers) {
         if ((modifiers & InputEvent.SHIFT_MASK) != 0) {
             modifiers |= InputEvent.SHIFT_DOWN_MASK;
@@ -737,6 +740,7 @@
         return modifiers;
     }
 
+    @SuppressWarnings("deprecation")
     private static int mapNewModifiers(int modifiers) {
         if ((modifiers & InputEvent.SHIFT_DOWN_MASK) != 0) {
             modifiers |= InputEvent.SHIFT_MASK;
--- a/jdk/src/java.desktop/share/classes/java/awt/Component.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/java/awt/Component.java	Wed Jul 05 22:52:01 2017 +0200
@@ -5036,6 +5036,7 @@
      *
      * Returns whether or not event was dispatched to an ancestor
      */
+    @SuppressWarnings("deprecation")
     boolean dispatchMouseWheelToAncestor(MouseWheelEvent e) {
         int newX, newY;
         newX = e.getX() + getX(); // Coordinates take into account at least
@@ -10379,7 +10380,11 @@
     }
 
     /**
-     * Sets a 'mixing-cutout' shape for the given component.
+     * Sets a 'mixing-cutout' shape for this lightweight component.
+     *
+     * This method is used exclusively for the purposes of the
+     * Heavyweight/Lightweight Components Mixing feature and will
+     * have no effect if applied to a heavyweight component.
      *
      * By default a lightweight component is treated as an opaque rectangle for
      * the purposes of the Heavyweight/Lightweight Components Mixing feature.
@@ -10392,7 +10397,7 @@
      * <li>{@code null} - reverts the default cutout shape (the rectangle equal
      * to the component's {@code getBounds()})
      * <li><i>empty-shape</i> - does not cut out anything from heavyweight
-     * components. This makes the given lightweight component effectively
+     * components. This makes this lightweight component effectively
      * transparent. Note that descendants of the lightweight component still
      * affect the shapes of heavyweight components.  An example of an
      * <i>empty-shape</i> is {@code new Rectangle()}.
@@ -10406,16 +10411,11 @@
      * for the given glass pane component.  If a developer needs some other
      * 'mixing-cutout' shape for the glass pane (which is rare), this must be
      * changed manually after installing the glass pane to the root pane.
-     * <p>
-     * Note that the 'mixing-cutout' shape neither affects painting, nor the
-     * mouse events handling for the given component. It is used exclusively
-     * for the purposes of the Heavyweight/Lightweight Components Mixing
-     * feature.
      *
      * @param shape the new 'mixing-cutout' shape
      * @since 9
      */
-    void setMixingCutoutShape(Shape shape) {
+    public void setMixingCutoutShape(Shape shape) {
         Region region = shape == null ? null : Region.getInstance(shape, null);
 
         synchronized (getTreeLock()) {
--- a/jdk/src/java.desktop/share/classes/java/awt/Container.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/java/awt/Container.java	Wed Jul 05 22:52:01 2017 +0200
@@ -4728,6 +4728,7 @@
      * Listen for drag events posted in other hw components so we can
      * track enter/exit regardless of where a drag originated
      */
+    @SuppressWarnings("deprecation")
     public void eventDispatched(AWTEvent e) {
         boolean isForeignDrag = (e instanceof MouseEvent) &&
                                 !(e instanceof SunDropTargetEvent) &&
@@ -4826,6 +4827,7 @@
      * If the target has been removed, we don't bother to send the
      * message.
      */
+    @SuppressWarnings("deprecation")
     void retargetMouseEvent(Component target, int id, MouseEvent e) {
         if (target == null) {
             return; // mouse is over another hw component or target is disabled
--- a/jdk/src/java.desktop/share/classes/java/awt/Event.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/java/awt/Event.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1995, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1995, 2016, 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
@@ -24,8 +24,7 @@
  */
 package java.awt;
 
-import java.awt.event.*;
-import java.io.*;
+import java.awt.event.KeyEvent;
 
 /**
  * <b>NOTE:</b> The {@code Event} class is obsolete and is
@@ -56,9 +55,12 @@
  * {@code Event} class ({@code PGUP},
  * {@code PGDN}, {@code F1}, {@code F2}, etc).
  *
+ * @deprecated It is recommended that {@code AWTEvent} and its subclasses be
+ *             used instead
  * @author     Sami Shaio
  * @since      1.0
  */
+@Deprecated(since = "9")
 public class Event implements java.io.Serializable {
     private transient long data;
 
--- a/jdk/src/java.desktop/share/classes/java/awt/KeyboardFocusManager.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/java/awt/KeyboardFocusManager.java	Wed Jul 05 22:52:01 2017 +0200
@@ -415,6 +415,7 @@
      * Initializes a KeyboardFocusManager.
      */
     public KeyboardFocusManager() {
+        @SuppressWarnings("deprecation")
         AWTKeyStroke[][] defaultFocusTraversalKeyStrokes = {
                 {
                         AWTKeyStroke.getAWTKeyStroke(KeyEvent.VK_TAB, 0, false),
--- a/jdk/src/java.desktop/share/classes/java/awt/MenuBar.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/java/awt/MenuBar.java	Wed Jul 05 22:52:01 2017 +0200
@@ -375,6 +375,7 @@
      * keydown).  Returns true if there is an associated
      * keyboard event.
      */
+    @SuppressWarnings("deprecation")
     boolean handleShortcut(KeyEvent e) {
         // Is it a key event?
         int id = e.getID();
--- a/jdk/src/java.desktop/share/classes/java/awt/MenuComponent.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/java/awt/MenuComponent.java	Wed Jul 05 22:52:01 2017 +0200
@@ -379,6 +379,7 @@
             }
 
         } else { // backward compatibility
+            @SuppressWarnings("deprecation")
             Event olde = e.convertToOld();
             if (olde != null) {
                 postEvent(olde);
--- a/jdk/src/java.desktop/share/classes/java/awt/MenuItem.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/java/awt/MenuItem.java	Wed Jul 05 22:52:01 2017 +0200
@@ -435,6 +435,7 @@
      * keydown) and the item is enabled.
      * Returns true if there is an associated shortcut.
      */
+    @SuppressWarnings("deprecation")
     boolean handleShortcut(KeyEvent e) {
         MenuShortcut s = new MenuShortcut(e.getKeyCode(),
                              (e.getModifiers() & InputEvent.SHIFT_MASK) > 0);
--- a/jdk/src/java.desktop/share/classes/java/awt/MenuShortcut.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/java/awt/MenuShortcut.java	Wed Jul 05 22:52:01 2017 +0200
@@ -180,6 +180,7 @@
      * @return a string representation of this MenuShortcut.
      * @since 1.1
      */
+    @SuppressWarnings("deprecation")
     public String toString() {
         int modifiers = 0;
         if (!GraphicsEnvironment.isHeadless()) {
--- a/jdk/src/java.desktop/share/classes/java/awt/PopupMenu.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/java/awt/PopupMenu.java	Wed Jul 05 22:52:01 2017 +0200
@@ -154,6 +154,7 @@
      *                parent's hierarchy
      * @exception RuntimeException if the parent is not showing on screen
      */
+    @SuppressWarnings("deprecation")
     public void show(Component origin, int x, int y) {
         // Use localParent for thread safety.
         MenuContainer localParent = parent;
--- a/jdk/src/java.desktop/share/classes/java/awt/Robot.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/java/awt/Robot.java	Wed Jul 05 22:52:01 2017 +0200
@@ -137,6 +137,7 @@
         initLegalButtonMask();
     }
 
+    @SuppressWarnings("deprecation")
     private static synchronized void initLegalButtonMask() {
         if (LEGAL_BUTTON_MASK != 0) return;
 
--- a/jdk/src/java.desktop/share/classes/java/awt/Toolkit.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/java/awt/Toolkit.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1067,6 +1067,7 @@
      * @see       java.awt.MenuShortcut
      * @since     1.1
      */
+    @SuppressWarnings("deprecation")
     public int getMenuShortcutKeyMask() throws HeadlessException {
         GraphicsEnvironment.checkHeadless();
 
--- a/jdk/src/java.desktop/share/classes/java/awt/dnd/DragSourceDragEvent.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/java/awt/dnd/DragSourceDragEvent.java	Wed Jul 05 22:52:01 2017 +0200
@@ -281,6 +281,7 @@
      * The mouse modifiers have higher priority than overlaying key
      * modifiers.
      */
+    @SuppressWarnings("deprecation")
     private void setNewModifiers() {
         if ((gestureModifiers & InputEvent.BUTTON1_MASK) != 0) {
             gestureModifiers |= InputEvent.BUTTON1_DOWN_MASK;
@@ -305,6 +306,7 @@
     /**
      * Sets old modifiers by the new ones.
      */
+    @SuppressWarnings("deprecation")
     private void setOldModifiers() {
         if ((gestureModifiers & InputEvent.BUTTON1_DOWN_MASK) != 0) {
             gestureModifiers |= InputEvent.BUTTON1_MASK;
--- a/jdk/src/java.desktop/share/classes/java/awt/event/ActionEvent.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/java/awt/event/ActionEvent.java	Wed Jul 05 22:52:01 2017 +0200
@@ -26,7 +26,6 @@
 package java.awt.event;
 
 import java.awt.AWTEvent;
-import java.awt.Event;
 import java.lang.annotation.Native;
 
 /**
@@ -63,25 +62,25 @@
      * The shift modifier. An indicator that the shift key was held
      * down during the event.
      */
-    public static final int SHIFT_MASK          = Event.SHIFT_MASK;
+    public static final int SHIFT_MASK = 1 << 0;
 
     /**
      * The control modifier. An indicator that the control key was held
      * down during the event.
      */
-    public static final int CTRL_MASK           = Event.CTRL_MASK;
+    public static final int CTRL_MASK = 1 << 1;
 
     /**
      * The meta modifier. An indicator that the meta key was held
      * down during the event.
      */
-    public static final int META_MASK           = Event.META_MASK;
+    public static final int META_MASK = 1 << 2;
 
     /**
      * The alt modifier. An indicator that the alt key was held
      * down during the event.
      */
-    public static final int ALT_MASK            = Event.ALT_MASK;
+    public static final int ALT_MASK = 1 << 3;
 
 
     /**
@@ -274,6 +273,7 @@
      *
      * @return a string identifying the event and its associated command
      */
+    @SuppressWarnings("deprecation")
     public String paramString() {
         String typeStr;
         switch(id) {
--- a/jdk/src/java.desktop/share/classes/java/awt/event/InputEvent.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/java/awt/event/InputEvent.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1996, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1996, 2016, 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
@@ -62,51 +62,76 @@
 
     /**
      * The Shift key modifier constant.
-     * It is recommended that SHIFT_DOWN_MASK be used instead.
+     *
+     * @deprecated It is recommended that SHIFT_DOWN_MASK and
+     *             {@link #getModifiersEx()} be used instead
      */
+    @Deprecated(since = "9")
     public static final int SHIFT_MASK = Event.SHIFT_MASK;
 
     /**
      * The Control key modifier constant.
-     * It is recommended that CTRL_DOWN_MASK be used instead.
+     *
+     * @deprecated It is recommended that CTRL_DOWN_MASK and
+     *             {@link #getModifiersEx()} be used instead
      */
+    @Deprecated(since = "9")
     public static final int CTRL_MASK = Event.CTRL_MASK;
 
     /**
      * The Meta key modifier constant.
-     * It is recommended that META_DOWN_MASK be used instead.
+     *
+     * @deprecated It is recommended that META_DOWN_MASK and
+     *             {@link #getModifiersEx()} be used instead
      */
+    @Deprecated(since = "9")
     public static final int META_MASK = Event.META_MASK;
 
     /**
      * The Alt key modifier constant.
-     * It is recommended that ALT_DOWN_MASK be used instead.
+     *
+     * @deprecated It is recommended that ALT_DOWN_MASK and
+     *             {@link #getModifiersEx()} be used instead
      */
+    @Deprecated(since = "9")
     public static final int ALT_MASK = Event.ALT_MASK;
 
     /**
      * The AltGraph key modifier constant.
+     *
+     * @deprecated It is recommended that ALT_GRAPH_DOWN_MASK and
+     *             {@link #getModifiersEx()} be used instead
      */
+    @Deprecated(since = "9")
     public static final int ALT_GRAPH_MASK = 1 << 5;
 
     /**
      * The Mouse Button1 modifier constant.
-     * It is recommended that BUTTON1_DOWN_MASK be used instead.
+     *
+     * @deprecated It is recommended that BUTTON1_DOWN_MASK and
+     *             {@link #getModifiersEx()} be used instead
      */
+    @Deprecated(since = "9")
     public static final int BUTTON1_MASK = 1 << 4;
 
     /**
      * The Mouse Button2 modifier constant.
-     * It is recommended that BUTTON2_DOWN_MASK be used instead.
-     * Note that BUTTON2_MASK has the same value as ALT_MASK.
+     *
+     * @deprecated It is recommended that BUTTON2_DOWN_MASK and
+     *             {@link #getModifiersEx()} be used instead. Note that
+     *             BUTTON2_MASK has the same value as ALT_MASK.
      */
+    @Deprecated(since = "9")
     public static final int BUTTON2_MASK = Event.ALT_MASK;
 
     /**
      * The Mouse Button3 modifier constant.
-     * It is recommended that BUTTON3_DOWN_MASK be used instead.
-     * Note that BUTTON3_MASK has the same value as META_MASK.
+     *
+     * @deprecated It is recommended that BUTTON3_DOWN_MASK and
+     *             {@link #getModifiersEx()} be used instead. Note that
+     *             BUTTON3_MASK has the same value as META_MASK.
      */
+    @Deprecated(since = "9")
     public static final int BUTTON3_MASK = Event.META_MASK;
 
     /**
@@ -159,7 +184,7 @@
 
     /**
      * An array of extended modifiers for additional buttons.
-     * @see getButtonDownMasks
+     * @see #getButtonDownMasks()
      * There are twenty buttons fit into 4byte space.
      * one more bit is reserved for FIRST_HIGH_BIT.
      * @since 1.7
@@ -382,7 +407,7 @@
      * @return whether or not the Shift modifier is down on this event
      */
     public boolean isShiftDown() {
-        return (modifiers & SHIFT_MASK) != 0;
+        return (modifiers & SHIFT_DOWN_MASK) != 0;
     }
 
     /**
@@ -390,7 +415,7 @@
      * @return whether or not the Control modifier is down on this event
      */
     public boolean isControlDown() {
-        return (modifiers & CTRL_MASK) != 0;
+        return (modifiers & CTRL_DOWN_MASK) != 0;
     }
 
     /**
@@ -398,7 +423,7 @@
      * @return whether or not the Meta modifier is down on this event
      */
     public boolean isMetaDown() {
-        return (modifiers & META_MASK) != 0;
+        return (modifiers & META_DOWN_MASK) != 0;
     }
 
     /**
@@ -406,7 +431,7 @@
      * @return whether or not the Alt modifier is down on this event
      */
     public boolean isAltDown() {
-        return (modifiers & ALT_MASK) != 0;
+        return (modifiers & ALT_DOWN_MASK) != 0;
     }
 
     /**
@@ -414,7 +439,7 @@
      * @return whether or not the AltGraph modifier is down on this event
      */
     public boolean isAltGraphDown() {
-        return (modifiers & ALT_GRAPH_MASK) != 0;
+        return (modifiers & ALT_GRAPH_DOWN_MASK) != 0;
     }
 
     /**
@@ -428,8 +453,12 @@
 
     /**
      * Returns the modifier mask for this event.
+     *
      * @return the modifier mask for this event
+     * @deprecated It is recommended that extended modifier keys and
+     *             {@link #getModifiersEx()} be used instead
      */
+    @Deprecated(since = "9")
     public int getModifiers() {
         return modifiers & (JDK_1_3_MODIFIERS | HIGH_MODIFIERS);
     }
--- a/jdk/src/java.desktop/share/classes/java/awt/event/KeyEvent.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/java/awt/event/KeyEvent.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1169,6 +1169,7 @@
      * @see #getKeyLocation()
      * @since 1.4
      */
+    @SuppressWarnings("deprecation")
     public KeyEvent(Component source, int id, long when, int modifiers,
                     int keyCode, char keyChar, int keyLocation) {
         super(source, id, when, modifiers);
@@ -1561,7 +1562,10 @@
      * @return string a text description of the combination of modifier
      *                keys that were held down during the event
      * @see InputEvent#getModifiersExText(int)
+     * @deprecated It is recommended that extended modifier keys and
+     *             {@link InputEvent#getModifiersExText(int)} be used instead
      */
+    @Deprecated(since = "9")
     public static String getKeyModifiersText(int modifiers) {
         StringBuilder buf = new StringBuilder();
         if ((modifiers & InputEvent.META_MASK) != 0) {
@@ -1696,6 +1700,7 @@
      *
      * @return a string identifying the event and its attributes
      */
+    @SuppressWarnings("deprecation")
     public String paramString() {
         StringBuilder str = new StringBuilder(100);
 
@@ -1821,6 +1826,7 @@
      * Sets new modifiers by the old ones. The key modifiers
      * override overlapping mouse modifiers.
      */
+    @SuppressWarnings("deprecation")
     private void setNewModifiers() {
         if ((modifiers & SHIFT_MASK) != 0) {
             modifiers |= SHIFT_DOWN_MASK;
@@ -1845,6 +1851,7 @@
     /**
      * Sets old modifiers by the new ones.
      */
+    @SuppressWarnings("deprecation")
     private void setOldModifiers() {
         if ((modifiers & SHIFT_DOWN_MASK) != 0) {
             modifiers |= SHIFT_MASK;
@@ -1871,6 +1878,7 @@
      * override overlapping mouse modifiers.
      * @serial
      */
+    @SuppressWarnings("deprecation")
     private void readObject(ObjectInputStream s)
       throws IOException, ClassNotFoundException {
         s.defaultReadObject();
--- a/jdk/src/java.desktop/share/classes/java/awt/event/MouseEvent.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/java/awt/event/MouseEvent.java	Wed Jul 05 22:52:01 2017 +0200
@@ -733,6 +733,7 @@
      * @see InputEvent#getMaskForButton(int)
      * @since 1.6
      */
+    @SuppressWarnings("deprecation")
     public MouseEvent(Component source, int id, long when, int modifiers,
                       int x, int y, int xAbs, int yAbs,
                       int clickCount, boolean popupTrigger, int button)
@@ -943,6 +944,7 @@
      * @see InputEvent#getModifiersExText(int)
      * @since 1.4
      */
+    @SuppressWarnings("deprecation")
     public static String getMouseModifiersText(int modifiers) {
         StringBuilder buf = new StringBuilder();
         if ((modifiers & InputEvent.ALT_MASK) != 0) {
@@ -1007,6 +1009,7 @@
      *
      * @return a string identifying the event and its attributes
      */
+    @SuppressWarnings("deprecation")
     public String paramString() {
         StringBuilder str = new StringBuilder(80);
 
@@ -1066,6 +1069,7 @@
      * Sets new modifiers by the old ones.
      * Also sets button.
      */
+    @SuppressWarnings("deprecation")
     private void setNewModifiers() {
         if ((modifiers & BUTTON1_MASK) != 0) {
             modifiers |= BUTTON1_DOWN_MASK;
@@ -1120,6 +1124,7 @@
     /**
      * Sets old modifiers by the new ones.
      */
+    @SuppressWarnings("deprecation")
     private void setOldModifiers() {
         if (id == MOUSE_PRESSED
             || id == MOUSE_RELEASED
@@ -1168,6 +1173,7 @@
      * Sets new modifiers by the old ones.
      * @serial
      */
+    @SuppressWarnings("deprecation")
     private void readObject(ObjectInputStream s)
       throws IOException, ClassNotFoundException {
         s.defaultReadObject();
--- a/jdk/src/java.desktop/share/classes/java/awt/peer/PopupMenuPeer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/java/awt/peer/PopupMenuPeer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -46,5 +46,6 @@
      *
      * @see PopupMenu#show(java.awt.Component, int, int)
      */
+    @SuppressWarnings("deprecation")
     void show(Event e);
 }
--- a/jdk/src/java.desktop/share/classes/javax/swing/Autoscroller.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/Autoscroller.java	Wed Jul 05 22:52:01 2017 +0200
@@ -82,6 +82,7 @@
     /**
      * Starts the timer targeting the passed in component.
      */
+    @SuppressWarnings("deprecation")
     private void start(JComponent c, MouseEvent e) {
         Point screenLocation = c.getLocationOnScreen();
 
@@ -156,6 +157,7 @@
      * ActionListener method. Invoked when the Timer fires. This will scroll
      * if necessary.
      */
+    @SuppressWarnings("deprecation")
     public void actionPerformed(ActionEvent x) {
         JComponent component = Autoscroller.component;
 
--- a/jdk/src/java.desktop/share/classes/javax/swing/DefaultButtonModel.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/DefaultButtonModel.java	Wed Jul 05 22:52:01 2017 +0200
@@ -239,6 +239,7 @@
     /**
      * {@inheritDoc}
      */
+    @SuppressWarnings("deprecation")
     public void setPressed(boolean b) {
         if((isPressed() == b) || !isEnabled()) {
             return;
--- a/jdk/src/java.desktop/share/classes/javax/swing/JComboBox.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/JComboBox.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1235,6 +1235,7 @@
      *
      * @see EventListenerList
      */
+    @SuppressWarnings("deprecation")
     protected void fireActionEvent() {
         if (!firingActionEvent) {
             // Set flag to ensure that an infinite loop is not created
--- a/jdk/src/java.desktop/share/classes/javax/swing/JComponent.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/JComponent.java	Wed Jul 05 22:52:01 2017 +0200
@@ -429,6 +429,7 @@
      * Returns the Set of <code>KeyStroke</code>s to use if the component
      * is managing focus for forward focus traversal.
      */
+    @SuppressWarnings("deprecation")
     static Set<KeyStroke> getManagingFocusForwardTraversalKeys() {
         synchronized(JComponent.class) {
             if (managingFocusForwardTraversalKeys == null) {
@@ -445,6 +446,7 @@
      * Returns the Set of <code>KeyStroke</code>s to use if the component
      * is managing focus for backward focus traversal.
      */
+    @SuppressWarnings("deprecation")
     static Set<KeyStroke> getManagingFocusBackwardTraversalKeys() {
         synchronized(JComponent.class) {
             if (managingFocusBackwardTraversalKeys == null) {
@@ -2886,6 +2888,7 @@
      *
      * @since 1.3
      */
+    @SuppressWarnings("deprecation")
     protected boolean processKeyBinding(KeyStroke ks, KeyEvent e,
                                         int condition, boolean pressed) {
         InputMap map = getInputMap(condition, false);
--- a/jdk/src/java.desktop/share/classes/javax/swing/JFileChooser.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/JFileChooser.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1754,6 +1754,7 @@
      *                the event
      * @see EventListenerList
      */
+    @SuppressWarnings("deprecation")
     protected void fireActionPerformed(String command) {
         // Guaranteed to return a non-null array
         Object[] listeners = listenerList.getListenerList();
--- a/jdk/src/java.desktop/share/classes/javax/swing/JLayer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/JLayer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -286,8 +286,7 @@
             super.remove(oldGlassPane);
         }
         if (glassPane != null) {
-            AWTAccessor.getComponentAccessor().setMixingCutoutShape(glassPane,
-                    new Rectangle());
+            glassPane.setMixingCutoutShape(new Rectangle());
             glassPane.setVisible(isGlassPaneVisible);
             super.addImpl(glassPane, null, 0);
         }
--- a/jdk/src/java.desktop/share/classes/javax/swing/JList.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/JList.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1516,6 +1516,7 @@
      * @see JComponent#setToolTipText
      * @see JComponent#getToolTipText
      */
+    @SuppressWarnings("deprecation")
     public String getToolTipText(MouseEvent event) {
         if(event != null) {
             Point p = event.getPoint();
--- a/jdk/src/java.desktop/share/classes/javax/swing/JMenuItem.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/JMenuItem.java	Wed Jul 05 22:52:01 2017 +0200
@@ -412,6 +412,7 @@
      * @param path  the <code>MenuElement</code> path array
      * @param manager   the <code>MenuSelectionManager</code>
      */
+    @SuppressWarnings("deprecation")
     public void processMouseEvent(MouseEvent e,MenuElement path[],MenuSelectionManager manager) {
         processMenuDragMouseEvent(
                  new MenuDragMouseEvent(e.getComponent(), e.getID(),
@@ -435,6 +436,7 @@
      * @param path the <code>MenuElement</code> path array
      * @param manager   the <code>MenuSelectionManager</code>
      */
+    @SuppressWarnings("deprecation")
     public void processKeyEvent(KeyEvent e,MenuElement path[],MenuSelectionManager manager) {
         if (DEBUG) {
             System.out.println("in JMenuItem.processKeyEvent/3 for " + getText() +
--- a/jdk/src/java.desktop/share/classes/javax/swing/JPopupMenu.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/JPopupMenu.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1385,6 +1385,7 @@
      * @param path the <code>MenuElement</code> path array
      * @param manager   the <code>MenuSelectionManager</code>
      */
+    @SuppressWarnings("deprecation")
     public void processKeyEvent(KeyEvent e, MenuElement path[],
                                 MenuSelectionManager manager) {
         MenuKeyEvent mke = new MenuKeyEvent(e.getComponent(), e.getID(),
--- a/jdk/src/java.desktop/share/classes/javax/swing/JRootPane.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/JRootPane.java	Wed Jul 05 22:52:01 2017 +0200
@@ -663,8 +663,7 @@
             throw new NullPointerException("glassPane cannot be set to null.");
         }
 
-        AWTAccessor.getComponentAccessor().setMixingCutoutShape(glass,
-                new Rectangle());
+        glass.setMixingCutoutShape(new Rectangle());
 
         boolean visible = false;
         if (glassPane != null && glassPane.getParent() == this) {
--- a/jdk/src/java.desktop/share/classes/javax/swing/JTable.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/JTable.java	Wed Jul 05 22:52:01 2017 +0200
@@ -3410,8 +3410,10 @@
                 // Convert the event to the renderer's coordinate system
                 Rectangle cellRect = getCellRect(hitRowIndex, hitColumnIndex, false);
                 p.translate(-cellRect.x, -cellRect.y);
+                @SuppressWarnings("deprecation")
+                final int modifiers = event.getModifiers();
                 MouseEvent newEvent = new MouseEvent(component, event.getID(),
-                                          event.getWhen(), event.getModifiers(),
+                                          event.getWhen(), modifiers,
                                           p.x, p.y,
                                           event.getXOnScreen(),
                                           event.getYOnScreen(),
--- a/jdk/src/java.desktop/share/classes/javax/swing/JTextField.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/JTextField.java	Wed Jul 05 22:52:01 2017 +0200
@@ -485,6 +485,7 @@
      * first order.
      * @see EventListenerList
      */
+    @SuppressWarnings("deprecation")
     protected void fireActionPerformed() {
         // Guaranteed to return a non-null array
         Object[] listeners = listenerList.getListenerList();
--- a/jdk/src/java.desktop/share/classes/javax/swing/JToggleButton.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/JToggleButton.java	Wed Jul 05 22:52:01 2017 +0200
@@ -372,6 +372,7 @@
         /**
          * Sets the pressed state of the toggle button.
          */
+        @SuppressWarnings("deprecation")
         public void setPressed(boolean b) {
             if ((isPressed() == b) || !isEnabled()) {
                 return;
--- a/jdk/src/java.desktop/share/classes/javax/swing/JTree.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/JTree.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1568,9 +1568,10 @@
                     Rectangle       pathBounds = getPathBounds(path);
 
                     p.translate(-pathBounds.x, -pathBounds.y);
+                    @SuppressWarnings("deprecation")
+                    final int modifiers = event.getModifiers();
                     newEvent = new MouseEvent(rComponent, event.getID(),
-                                          event.getWhen(),
-                                              event.getModifiers(),
+                                          event.getWhen(), modifiers,
                                               p.x, p.y,
                                               event.getXOnScreen(),
                                               event.getYOnScreen(),
--- a/jdk/src/java.desktop/share/classes/javax/swing/KeyboardManager.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/KeyboardManager.java	Wed Jul 05 22:52:01 2017 +0200
@@ -207,6 +207,7 @@
       * want a crack at the event.
       * If one of them wants it, then it will "DO-THE-RIGHT-THING"
       */
+    @SuppressWarnings("deprecation")
     public boolean fireKeyboardAction(KeyEvent e, boolean pressed, Container topAncestor) {
 
          if (e.isConsumed()) {
--- a/jdk/src/java.desktop/share/classes/javax/swing/MenuSelectionManager.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/MenuSelectionManager.java	Wed Jul 05 22:52:01 2017 +0200
@@ -212,6 +212,7 @@
      *
      * @param event  a MouseEvent object
      */
+    @SuppressWarnings("deprecation")
     public void processMouseEvent(MouseEvent event) {
         int screenX,screenY;
         Point p;
--- a/jdk/src/java.desktop/share/classes/javax/swing/SwingUtilities.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/SwingUtilities.java	Wed Jul 05 22:52:01 2017 +0200
@@ -346,6 +346,7 @@
      *
      * @return the new mouse event
      */
+    @SuppressWarnings("deprecation")
     public static MouseEvent convertMouseEvent(Component source,
                                                MouseEvent sourceEvent,
                                                Component destination) {
--- a/jdk/src/java.desktop/share/classes/javax/swing/ToolTipManager.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/ToolTipManager.java	Wed Jul 05 22:52:01 2017 +0200
@@ -89,6 +89,7 @@
      */
     protected boolean heavyWeightPopupEnabled = false;
 
+    @SuppressWarnings("deprecation")
     ToolTipManager() {
         enterTimer = new Timer(750, new insideTimerAction());
         enterTimer.setRepeats(false);
--- a/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicComboBoxUI.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicComboBoxUI.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1839,6 +1839,7 @@
         // key.  If it finds a key event that wasn't a navigation key it
         // dispatches it to JComboBox.selectWithKeyChar() so that it can do
         // type-ahead.
+        @SuppressWarnings("deprecation")
         public void keyPressed( KeyEvent e ) {
             if ( isNavigationKey(e.getKeyCode(), e.getModifiers()) ) {
                 lastTime = 0L;
--- a/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicComboPopup.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicComboPopup.java	Wed Jul 05 22:52:01 2017 +0200
@@ -528,6 +528,7 @@
      */
     protected JList<Object> createList() {
         return new JList<Object>( comboBox.getModel() ) {
+            @SuppressWarnings("deprecation")
             public void processMouseEvent(MouseEvent e)  {
                 if (BasicGraphicsUtils.isMenuShortcutKeyDown(e))  {
                     // Fix for 4234053. Filter out the Control Key from the list.
@@ -1238,6 +1239,7 @@
     protected MouseEvent convertMouseEvent( MouseEvent e ) {
         Point convertedPoint = SwingUtilities.convertPoint( (Component)e.getSource(),
                                                             e.getPoint(), list );
+        @SuppressWarnings("deprecation")
         MouseEvent newEvent = new MouseEvent( (Component)e.getSource(),
                                               e.getID(),
                                               e.getWhen(),
--- a/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicGraphicsUtils.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicGraphicsUtils.java	Wed Jul 05 22:52:01 2017 +0200
@@ -382,6 +382,7 @@
         return c.getComponentOrientation().isLeftToRight();
     }
 
+    @SuppressWarnings("deprecation")
     static boolean isMenuShortcutKeyDown(InputEvent event) {
         return (event.getModifiers() &
                 Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()) != 0;
--- a/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicInternalFrameUI.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicInternalFrameUI.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1024,7 +1024,7 @@
                 return;
             }
         }
-
+        @SuppressWarnings("deprecation")
         public void mouseDragged(MouseEvent e) {
 
             if ( startingBounds == null ) {
--- a/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicMenuItemUI.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicMenuItemUI.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1026,6 +1026,7 @@
                 manager.processMouseEvent(e);
             }
         }
+        @SuppressWarnings("deprecation")
         public void mouseEntered(MouseEvent e) {
             MenuSelectionManager manager = MenuSelectionManager.defaultManager();
             int modifiers = e.getModifiers();
@@ -1037,6 +1038,7 @@
             manager.setSelectedPath(getPath());
              }
         }
+        @SuppressWarnings("deprecation")
         public void mouseExited(MouseEvent e) {
             MenuSelectionManager manager = MenuSelectionManager.defaultManager();
 
--- a/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicMenuUI.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicMenuUI.java	Wed Jul 05 22:52:01 2017 +0200
@@ -123,6 +123,7 @@
                                            getPropertyPrefix() + ".actionMap");
     }
 
+    @SuppressWarnings("deprecation")
     void updateMnemonicBinding() {
         int mnemonic = menuItem.getModel().getMnemonic();
         int[] shortcutKeys = (int[])DefaultLookup.get(menuItem, this,
--- a/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicPopupMenuUI.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicPopupMenuUI.java	Wed Jul 05 22:52:01 2017 +0200
@@ -268,6 +268,7 @@
         return list;
     }
 
+    @SuppressWarnings("deprecation")
     public boolean isPopupTrigger(MouseEvent e) {
         return ((e.getID()==MouseEvent.MOUSE_RELEASED)
                 && ((e.getModifiers() & MouseEvent.BUTTON3_MASK)!=0));
--- a/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicSplitPaneUI.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicSplitPaneUI.java	Wed Jul 05 22:52:01 2017 +0200
@@ -328,6 +328,7 @@
     /**
      * Installs the UI defaults.
      */
+    @SuppressWarnings("deprecation")
     protected void installDefaults(){
         LookAndFeel.installBorder(splitPane, "SplitPane.border");
         LookAndFeel.installColors(splitPane, "SplitPane.background",
--- a/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicTableUI.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicTableUI.java	Wed Jul 05 22:52:01 2017 +0200
@@ -868,6 +868,7 @@
 
         public void keyReleased(KeyEvent e) { }
 
+        @SuppressWarnings("deprecation")
         public void keyTyped(KeyEvent e) {
             KeyStroke keyStroke = KeyStroke.getKeyStroke(e.getKeyChar(),
                     e.getModifiers());
--- a/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicTextUI.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicTextUI.java	Wed Jul 05 22:52:01 2017 +0200
@@ -525,7 +525,7 @@
      * adding 'TAB' and 'SHIFT-TAB' to traversalKeysSet in case
      * editor is non editable
      */
-
+    @SuppressWarnings("deprecation")
     void updateFocusTraversalKeys() {
         /*
          * Fix for 4514331 Non-editable JTextArea and similar
--- a/jdk/src/java.desktop/share/classes/javax/swing/plaf/metal/MetalRootPaneUI.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/plaf/metal/MetalRootPaneUI.java	Wed Jul 05 22:52:01 2017 +0200
@@ -898,6 +898,7 @@
             w.setCursor(lastCursor);
         }
 
+        @SuppressWarnings("deprecation")
         public void mouseClicked(MouseEvent ev) {
             Window w = (Window)ev.getSource();
             Frame f = null;
--- a/jdk/src/java.desktop/share/classes/javax/swing/plaf/metal/MetalToolTipUI.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/plaf/metal/MetalToolTipUI.java	Wed Jul 05 22:52:01 2017 +0200
@@ -192,6 +192,7 @@
     // that subclasses that randomly invoke this method will see varying
     // results. If this becomes an issue, MetalToolTipUI should no longer be
     // shared.
+    @SuppressWarnings("deprecation")
     public String getAcceleratorString() {
         if (tip == null || isAcceleratorHidden()) {
             return "";
--- a/jdk/src/java.desktop/share/classes/javax/swing/plaf/synth/SynthSplitPaneUI.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/plaf/synth/SynthSplitPaneUI.java	Wed Jul 05 22:52:01 2017 +0200
@@ -80,6 +80,7 @@
      * Installs the UI defaults.
      */
     @Override
+    @SuppressWarnings("deprecation")
     protected void installDefaults() {
         updateStyle(splitPane);
 
--- a/jdk/src/java.desktop/share/classes/javax/swing/table/JTableHeader.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/table/JTableHeader.java	Wed Jul 05 22:52:01 2017 +0200
@@ -384,6 +384,7 @@
      *                          renderer and, therefore, the proper tip
      * @return the tool tip for this component
      */
+    @SuppressWarnings("deprecation")
     public String getToolTipText(MouseEvent event) {
         String tip = null;
         Point p = event.getPoint();
--- a/jdk/src/java.desktop/share/classes/javax/swing/text/DefaultCaret.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/text/DefaultCaret.java	Wed Jul 05 22:52:01 2017 +0200
@@ -372,6 +372,7 @@
     /**
      * Selects word based on the MouseEvent
      */
+    @SuppressWarnings("deprecation")
     private void selectWord(MouseEvent e) {
         if (selectedWordEvent != null
             && selectedWordEvent.getX() == e.getX()
@@ -405,6 +406,7 @@
      * @param e the mouse event
      * @see MouseListener#mouseClicked
      */
+    @SuppressWarnings("deprecation")
     public void mouseClicked(MouseEvent e) {
         if (getComponent() == null) {
             return;
@@ -513,6 +515,7 @@
     /**
      * Adjusts the caret location based on the MouseEvent.
      */
+    @SuppressWarnings("deprecation")
     private void adjustCaret(MouseEvent e) {
         if ((e.getModifiers() & ActionEvent.SHIFT_MASK) != 0 &&
             getDot() != -1) {
--- a/jdk/src/java.desktop/share/classes/javax/swing/text/JTextComponent.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/javax/swing/text/JTextComponent.java	Wed Jul 05 22:52:01 2017 +0200
@@ -4103,6 +4103,7 @@
             get(FOCUSED_COMPONENT);
     }
 
+    @SuppressWarnings("deprecation")
     private int getCurrentEventModifiers() {
         int modifiers = 0;
         AWTEvent currentEvent = EventQueue.getCurrentEvent();
--- a/jdk/src/java.desktop/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -26,6 +26,8 @@
 /**
  * Defines the AWT and Swing user interface toolkits, plus APIs for
  * accessibility, audio, imaging, printing, and JavaBeans.
+ *
+ * @since 9
  */
 module java.desktop {
     requires transitive java.datatransfer;
@@ -88,9 +90,6 @@
     exports sun.awt to
         jdk.accessibility;
 
-    exports com.sun.awt to
-        jdk.desktop;
-
     opens javax.swing.plaf.basic to
         jdk.jconsole;
     opens com.sun.java.swing.plaf.windows to
--- a/jdk/src/java.desktop/share/classes/sun/awt/AWTAccessor.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/sun/awt/AWTAccessor.java	Wed Jul 05 22:52:01 2017 +0200
@@ -93,12 +93,6 @@
          * its parent.
          */
         Rectangle getBounds(Component comp);
-        /*
-         * Sets the shape of a lw component to cut out from hw components.
-         *
-         * See 6797587, 6776743, 6768307, and 6768332 for details
-         */
-        void setMixingCutoutShape(Component comp, Shape shape);
 
         /**
          * Sets GraphicsConfiguration value for the component.
--- a/jdk/src/java.desktop/share/classes/sun/awt/NullComponentPeer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/sun/awt/NullComponentPeer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -126,6 +126,7 @@
     public void coalescePaintEvent(PaintEvent e) {
     }
 
+    @SuppressWarnings("deprecation")
     public boolean handleEvent(Event e) {
         return false;
     }
--- a/jdk/src/java.desktop/share/classes/sun/awt/SunToolkit.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/sun/awt/SunToolkit.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1049,6 +1049,7 @@
     /**
      * Returns key modifiers used by Swing to set up a focus accelerator key stroke.
      */
+    @SuppressWarnings("deprecation")
     public int getFocusAcceleratorKeyMask() {
         return InputEvent.ALT_MASK;
     }
@@ -1059,6 +1060,7 @@
      * the way things work on Windows: here, pressing ctrl + alt allows user to enter
      * characters from the extended character set (like euro sign or math symbols)
      */
+    @SuppressWarnings("deprecation")
     public boolean isPrintableCharacterModifiersMask(int mods) {
         return ((mods & InputEvent.ALT_MASK) == (mods & InputEvent.CTRL_MASK));
     }
--- a/jdk/src/java.desktop/share/classes/sun/swing/FilePane.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/sun/swing/FilePane.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1831,6 +1831,7 @@
     private class Handler implements MouseListener {
         private MouseListener doubleClickListener;
 
+        @SuppressWarnings("deprecation")
         public void mouseClicked(MouseEvent evt) {
             JComponent source = (JComponent)evt.getSource();
 
--- a/jdk/src/java.desktop/share/classes/sun/swing/MenuItemLayoutHelper.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/sun/swing/MenuItemLayoutHelper.java	Wed Jul 05 22:52:01 2017 +0200
@@ -175,6 +175,7 @@
         arrowSize.origWidth = arrowSize.width;
     }
 
+    @SuppressWarnings("deprecation")
     private String getAccText(String acceleratorDelimiter) {
         String accText = "";
         KeyStroke accelerator = mi.getAccelerator();
--- a/jdk/src/java.desktop/share/classes/sun/swing/SwingUtilities2.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/share/classes/sun/swing/SwingUtilities2.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1460,7 +1460,7 @@
      *
      * @param ie InputEvent to check
      */
-
+    @SuppressWarnings("deprecation")
     private static boolean isAccessClipboardGesture(InputEvent ie) {
         boolean allowedGesture = false;
         if (ie instanceof KeyEvent) { //we can validate only keyboard gestures
@@ -2129,6 +2129,7 @@
         return -1;
     }
 
+    @SuppressWarnings("deprecation")
     public static int getSystemMnemonicKeyMask() {
         Toolkit toolkit = Toolkit.getDefaultToolkit();
         if (toolkit instanceof SunToolkit) {
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/InfoWindow.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/InfoWindow.java	Wed Jul 05 22:52:01 2017 +0200
@@ -429,7 +429,7 @@
                 gtkImagesLoaded = true;
             }
         }
-
+        @SuppressWarnings("deprecation")
         private class ActionPerformer extends MouseAdapter {
             public void mouseClicked(MouseEvent e) {
                 // hide the balloon by any click
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/ListHelper.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/ListHelper.java	Wed Jul 05 22:52:01 2017 +0200
@@ -385,7 +385,7 @@
         }
         return false;
     }
-
+    @SuppressWarnings("deprecation")
     void handleVSBEvent(MouseEvent e, Rectangle bounds, int x, int y) {
         int sbHeight = hsbVis ? bounds.height - SCROLLBAR_WIDTH : bounds.height;
 
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/XBaseMenuWindow.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/XBaseMenuWindow.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1087,7 +1087,9 @@
                       }
                   } else {
                       //Invoke action event
-                      item.action(mouseEvent.getWhen(), mouseEvent.getModifiers());
+                      @SuppressWarnings("deprecation")
+                      final int modifiers = mouseEvent.getModifiers();
+                      item.action(mouseEvent.getWhen(), modifiers);
                       ungrabInput();
                   }
               } else {
@@ -1200,7 +1202,9 @@
               if (citem instanceof XMenuPeer) {
                   cwnd.selectItem(citem, true);
               } else if (citem != null) {
-                  citem.action(event.getWhen(), event.getModifiers());
+                  @SuppressWarnings("deprecation")
+                  final int modifiers = event.getModifiers();
+                  citem.action(event.getWhen(), modifiers);
                   ungrabInput();
               }
               break;
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/XButtonPeer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/XButtonPeer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -120,7 +120,9 @@
               if (XToolkit.isLeftMouseButton(e)) {
                   if (armed)
                   {
-                      action(e.getWhen(),e.getModifiers());
+                      @SuppressWarnings("deprecation")
+                      final int modifiers = e.getModifiers();
+                      action(e.getWhen(), modifiers);
                   }
                   pressed = false;
                   armed = false;
@@ -168,7 +170,9 @@
                   pressed=true;
                   armed=true;
                   repaint();
-                  action(e.getWhen(),e.getModifiers());
+                  @SuppressWarnings("deprecation")
+                  final int modifiers = e.getModifiers();
+                  action(e.getWhen(), modifiers);
               }
 
               break;
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/XChoicePeer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/XChoicePeer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -482,7 +482,7 @@
         firstPress = false;
         dragStartIdx = -1;
     }
-
+    @SuppressWarnings("deprecation")
     public void mouseDragged(MouseEvent e) {
         /*
          * fix for 5003166. On Motif user are unable to drag
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/XEmbedServerTester.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/XEmbedServerTester.java	Wed Jul 05 22:52:01 2017 +0200
@@ -452,6 +452,7 @@
         waitWindowActivated(res);
         return res;
     }
+    @SuppressWarnings("deprecation")
     private int activateServerNoWait(int prev) {
         xembedLog.fine("Activating server");
         int res = getEventPos();
@@ -467,6 +468,7 @@
         robot.mouseRelease(InputEvent.BUTTON1_MASK);
         return res;
     }
+    @SuppressWarnings("deprecation")
     private int deactivateServer() {
         xembedLog.fine("Deactivating server");
         int res = getEventPos();
@@ -480,6 +482,7 @@
         waitWindowDeactivated(res);
         return res;
     }
+    @SuppressWarnings("deprecation")
     private int focusServer() {
         xembedLog.fine("Focusing server");
         boolean weFocused = focused;
@@ -740,6 +743,7 @@
     private void ungrabKey() {
         sendMessage(XEmbedHelper.NON_STANDARD_XEMBED_GTK_UNGRAB_KEY, 0, accel_keysym, accel_mods);
     }
+    @SuppressWarnings("deprecation")
     private int showModalDialog() {
         xembedLog.fine("Showing modal dialog");
         int res = getEventPos();
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/XListPeer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/XListPeer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -573,7 +573,7 @@
             repaint();
         }
     }
-
+    @SuppressWarnings("deprecation")
     void mousePressed(MouseEvent mouseEvent) {
         if (log.isLoggable(PlatformLogger.Level.FINER)) {
             log.finer(mouseEvent.toString() + ", hsb " + hsbVis + ", vsb " + vsbVis);
@@ -641,6 +641,7 @@
             isMousePressed = true;
         }
     }
+    @SuppressWarnings("deprecation")
     void mouseReleased(MouseEvent mouseEvent) {
         if (isEnabled() && mouseEvent.getButton() == MouseEvent.BUTTON1) {
             //winReleaseCursorFocus();
@@ -685,6 +686,7 @@
         }
     }
 
+    @SuppressWarnings("deprecation")
     void mouseDragged(MouseEvent mouseEvent) {
         // TODO: can you drag w/ any other buttons?  what about multiple buttons?
         if (isEnabled() &&
@@ -810,7 +812,7 @@
               break;
         }
     }
-
+    @SuppressWarnings("deprecation")
     void keyPressed(KeyEvent e) {
         int keyCode = e.getKeyCode();
         if (log.isLoggable(PlatformLogger.Level.FINE)) {
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/XMenuBarPeer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/XMenuBarPeer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -503,6 +503,7 @@
      * This function is called from XWindow
      * @see XWindow.handleF10onEDT()
      */
+    @SuppressWarnings("deprecation")
     void handleF10KeyPress(KeyEvent event) {
         int keyState = event.getModifiers();
         if (((keyState & InputEvent.ALT_MASK) != 0) ||
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/XPopupMenuPeer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/XPopupMenuPeer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -131,6 +131,7 @@
     /*
      * From PopupMenuPeer
      */
+    @SuppressWarnings("deprecation")
     public void show(Event e) {
         target = (Component)e.target;
         // Get menus from the target.
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/XScrollPanePeer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/XScrollPanePeer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -468,6 +468,7 @@
      * MouseEvent.MOUSE_EXITED
      * MouseEvent.MOUSE_DRAGGED
      */
+    @SuppressWarnings("deprecation")
     public void handleJavaMouseEvent( MouseEvent mouseEvent ) {
         super.handleJavaMouseEvent(mouseEvent);
         int modifiers = mouseEvent.getModifiers();
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/XScrollbar.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/XScrollbar.java	Wed Jul 05 22:52:01 2017 +0200
@@ -457,6 +457,7 @@
      * MouseEvent.MOUSE_EXITED
      * MouseEvent.MOUSE_DRAGGED
      */
+    @SuppressWarnings("deprecation")
     public void handleMouseEvent(int id, int modifiers, int x, int y) {
         if ((modifiers & InputEvent.BUTTON1_MASK) == 0) {
             return;
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/XScrollbarPeer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/XScrollbarPeer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -126,6 +126,7 @@
      * MouseEvent.MOUSE_EXITED
      * MouseEvent.MOUSE_DRAGGED
      */
+    @SuppressWarnings("deprecation")
     public void handleJavaMouseEvent( MouseEvent mouseEvent ) {
         super.handleJavaMouseEvent(mouseEvent);
 
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/XTextAreaPeer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/XTextAreaPeer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1344,6 +1344,7 @@
             }
         }
 
+        @SuppressWarnings("deprecation")
         private static MouseEvent newMouseEvent(
             Component source, Point point, MouseEvent template )
         {
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/XTrayIconPeer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/XTrayIconPeer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -477,6 +477,7 @@
             e.setSource(xtiPeer.target);
             XToolkit.postEvent(XToolkit.targetToAppContext(e.getSource()), e);
         }
+        @SuppressWarnings("deprecation")
         public void mouseClicked(MouseEvent e) {
             if ((e.getClickCount() == 1 || xtiPeer.balloon.isVisible()) &&
                 e.getButton() == MouseEvent.BUTTON1)
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/XWindow.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/XWindow.java	Wed Jul 05 22:52:01 2017 +0200
@@ -621,7 +621,7 @@
         // 4 and 5 buttons are usually considered assigned to a first wheel
         return button == XConstants.buttons[3] || button == XConstants.buttons[4];
     }
-
+    @SuppressWarnings("deprecation")
     static int getXModifiers(AWTKeyStroke stroke) {
         int mods = stroke.getModifiers();
         int res = 0;
--- a/jdk/src/java.desktop/unix/classes/sun/print/IPPPrintService.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/unix/classes/sun/print/IPPPrintService.java	Wed Jul 05 22:52:01 2017 +0200
@@ -59,6 +59,7 @@
 
 import java.util.Iterator;
 import java.util.HashSet;
+import java.util.Map;
 
 
 public class IPPPrintService implements PrintService, SunPrinterJobService {
@@ -1758,6 +1759,19 @@
 
                     if (responseMap != null && responseMap.length > 0) {
                         getAttMap = responseMap[0];
+                        // If there is extra hashmap created due to duplicate
+                        // key/attribute present in IPPresponse, then use that
+                        // map too by appending to getAttMap after removing the
+                        // duplicate key/value
+                        if (responseMap.length > 1) {
+                            for (int i = 1; i < responseMap.length; i++) {
+                                for (Map.Entry<String, AttributeClass> entry : responseMap[i].entrySet()) {
+                                    if (!getAttMap.containsKey(entry.getValue())) {
+                                        getAttMap.put(entry.getKey(), entry.getValue());
+                                    }
+                                }
+                            }
+                        }
                     }
                 } else {
                     debug_println(debugPrefix+"opGetAttributes - null input stream");
--- a/jdk/src/java.desktop/windows/classes/sun/awt/windows/WButtonPeer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/windows/classes/sun/awt/windows/WButtonPeer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -95,6 +95,7 @@
     private static native void initIDs();
 
     @Override
+    @SuppressWarnings("deprecation")
     public boolean handleJavaKeyEvent(KeyEvent e) {
          switch (e.getID()) {
             case KeyEvent.KEY_RELEASED:
--- a/jdk/src/java.desktop/windows/classes/sun/awt/windows/WFileDialogPeer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/windows/classes/sun/awt/windows/WFileDialogPeer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -263,6 +263,7 @@
     void disable() {}
     @Override
     public void reshape(int x, int y, int width, int height) {}
+    @SuppressWarnings("deprecation")
     public boolean handleEvent(Event e) { return false; }
     @Override
     public void setForeground(Color c) {}
--- a/jdk/src/java.desktop/windows/classes/sun/awt/windows/WPopupMenuPeer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/windows/classes/sun/awt/windows/WPopupMenuPeer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -70,6 +70,7 @@
 
     private native void createMenu(WComponentPeer parent);
 
+    @SuppressWarnings("deprecation")
     public void show(Event e) {
         Component origin = (Component)e.target;
         WComponentPeer peer = (WComponentPeer) WToolkit.targetToPeer(origin);
@@ -97,6 +98,7 @@
      */
     void show(Component origin, Point p) {
         WComponentPeer peer = (WComponentPeer) WToolkit.targetToPeer(origin);
+        @SuppressWarnings("deprecation")
         Event e = new Event(origin, 0, Event.MOUSE_DOWN, p.x, p.y, 0, 0);
         if (peer == null) {
             Component nativeOrigin = WToolkit.getNativeContainer(origin);
@@ -107,5 +109,6 @@
         _show(e);
     }
 
+    @SuppressWarnings("deprecation")
     private native void _show(Event e);
 }
--- a/jdk/src/java.desktop/windows/classes/sun/awt/windows/WPrintDialogPeer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/windows/classes/sun/awt/windows/WPrintDialogPeer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -135,6 +135,7 @@
     void disable() {}
     @Override
     public void reshape(int x, int y, int width, int height) {}
+    @SuppressWarnings("deprecation")
     public boolean handleEvent(Event e) { return false; }
     @Override
     public void setForeground(Color c) {}
--- a/jdk/src/java.desktop/windows/classes/sun/awt/windows/WTextFieldPeer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.desktop/windows/classes/sun/awt/windows/WTextFieldPeer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -43,6 +43,7 @@
     }
 
     @Override
+    @SuppressWarnings("deprecation")
     public boolean handleJavaKeyEvent(KeyEvent e) {
         switch (e.getID()) {
            case KeyEvent.KEY_TYPED:
--- a/jdk/src/java.instrument/share/classes/java/lang/instrument/ClassFileTransformer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.instrument/share/classes/java/lang/instrument/ClassFileTransformer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -229,6 +229,7 @@
      *         or {@code null} if no transform is performed
      *
      * @since  9
+     * @spec JPMS
      */
     default byte[]
     transform(  Module              module,
--- a/jdk/src/java.instrument/share/classes/java/lang/instrument/Instrumentation.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.instrument/share/classes/java/lang/instrument/Instrumentation.java	Wed Jul 05 22:52:01 2017 +0200
@@ -714,6 +714,7 @@
      * @throws NullPointerException if any of the arguments are {@code null} or
      *         any of the Sets or Maps contains a {@code null} key or value
      * @since 9
+     * @spec JPMS
      */
     void redefineModule(Module module,
                         Set<Module> extraReads,
--- a/jdk/src/java.instrument/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.instrument/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -26,6 +26,8 @@
 /**
  * Defines services that allow agents to
  * instrument programs running on the JVM.
+ *
+ * @since 9
  */
 module java.instrument {
     exports java.lang.instrument;
--- a/jdk/src/java.logging/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.logging/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Defines the Java Logging API.
+ *
+ * @since 9
  */
 module java.logging {
     exports java.util.logging;
--- a/jdk/src/java.management.rmi/share/classes/javax/management/remote/rmi/RMIConnector.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.management.rmi/share/classes/javax/management/remote/rmi/RMIConnector.java	Wed Jul 05 22:52:01 2017 +0200
@@ -38,6 +38,7 @@
 import java.io.ObjectInputStream;
 import java.io.ObjectStreamClass;
 import java.io.Serializable;
+import java.lang.module.ModuleDescriptor;
 import java.lang.ref.WeakReference;
 import java.lang.reflect.Constructor;
 import java.lang.reflect.InvocationHandler;
@@ -107,6 +108,8 @@
 import sun.rmi.transport.LiveRef;
 import java.io.NotSerializableException;
 
+import static java.lang.module.ModuleDescriptor.Modifier.SYNTHETIC;
+
 /**
  * <p>A connection to a remote RMI connector.  Usually, such
  * connections are made using {@link
@@ -2020,8 +2023,14 @@
                 Module rmiModule = RemoteRef.class.getModule();
 
                 String pkg = packageOf(pRefClassName);
-                assert pkg != null && pkg.length() > 0 && !pkg.equals(packageOf(proxyRefCName));
-                Module m = Modules.defineModule(cl, "jdk.remoteref", Collections.singleton(pkg));
+                assert pkg != null && pkg.length() > 0 &&
+                        !pkg.equals(packageOf(proxyRefCName));
+
+                ModuleDescriptor descriptor =
+                    ModuleDescriptor.newModule("jdk.remoteref", Set.of(SYNTHETIC))
+                        .packages(Set.of(pkg))
+                        .build();
+                Module m = Modules.defineModule(cl, descriptor, null);
 
                 // jdk.remoteref needs to read to java.base and jmxModule
                 Modules.addReads(m, Object.class.getModule());
--- a/jdk/src/java.management.rmi/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.management.rmi/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -46,6 +46,7 @@
  *           and load the appropriate {@code JMXConnectorServerProvider} service
  *           implementation for the given protocol.
  *
+ * @since 9
  */
 module java.management.rmi {
 
--- a/jdk/src/java.management/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.management/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -28,6 +28,8 @@
  * <P>
  * The JMX API consists of interfaces for monitoring and management of the
  * JVM and other components in the Java runtime.
+ *
+ * @since 9
  */
 module java.management {
 
--- a/jdk/src/java.naming/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.naming/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Defines the Java Naming and Directory Interface (JNDI) API.
+ *
+ * @since 9
  */
 module java.naming {
     requires java.security.sasl;
--- a/jdk/src/java.prefs/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.prefs/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Defines the Preferences API.
+ *
+ * @since 9
  */
 module java.prefs {
     requires java.xml;
--- a/jdk/src/java.rmi/share/classes/java/rmi/activation/ActivationInstantiator.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.rmi/share/classes/java/rmi/activation/ActivationInstantiator.java	Wed Jul 05 22:52:01 2017 +0200
@@ -60,7 +60,20 @@
     * initialization data, and
     *
     * <li> returning a MarshalledObject containing the stub for the
-    * remote object it created </ul>
+    * remote object it created.</ul>
+    *
+    * <p>In order for activation to be successful, one of the following requirements
+    * must be met, otherwise {@link ActivationException} is thrown:
+    *
+    * <ul><li>The class to be activated and the special activation constructor are both public,
+    * and the class resides in a package that is
+    * {@linkplain java.lang.reflect.Module#isExported(String,java.lang.reflect.Module) exported}
+    * to at least the {@code java.rmi} module; or
+    *
+    * <li>The class to be activated resides in a package that is
+    * {@linkplain java.lang.reflect.Module#isOpen(String,java.lang.reflect.Module) open}
+    * to at least the {@code java.rmi} module.
+    * </ul>
     *
     * @param id the object's activation identifier
     * @param desc the object's descriptor
--- a/jdk/src/java.rmi/share/classes/java/rmi/activation/Activator.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.rmi/share/classes/java/rmi/activation/Activator.java	Wed Jul 05 22:52:01 2017 +0200
@@ -48,7 +48,7 @@
  * The <code>Activator</code> works closely with
  * <code>ActivationSystem</code>, which provides a means for registering
  * groups and objects within those groups, and <code>ActivationMonitor</code>,
- * which recives information about active and inactive objects and inactive
+ * which receives information about active and inactive objects and inactive
  * groups. <p>
  *
  * The activator is responsible for monitoring and detecting when
--- a/jdk/src/java.rmi/share/classes/java/rmi/server/UnicastRemoteObject.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.rmi/share/classes/java/rmi/server/UnicastRemoteObject.java	Wed Jul 05 22:52:01 2017 +0200
@@ -107,8 +107,9 @@
  * the binary name of the root class with the suffix {@code _Stub}.
  *
  * <li>The stub class is loaded by name using the class loader of the root
- * class. The stub class must extend {@link RemoteStub} and must have a
- * public constructor that has one parameter of type {@link RemoteRef}.
+ * class. The stub class must be public, it must extend {@link RemoteStub}, it must
+ * reside in a package that is exported to at least the {@code java.rmi} module, and it
+ * must have a public constructor that has one parameter of type {@link RemoteRef}.
  *
  * <li>Finally, an instance of the stub class is constructed with a
  * {@link RemoteRef}.
@@ -124,12 +125,21 @@
  *
  * <ul>
  *
- * <li>The proxy's class is defined by the class loader of the remote
- * object's class.
+ * <li>The proxy's class is defined according to the specifications for the
+ * <a href="{@docRoot}/java/lang/reflect/Proxy.html#membership">
+ * {@code Proxy}
+ * </a>
+ * class, using the class loader of the remote object's class.
  *
  * <li>The proxy implements all the remote interfaces implemented by the
  * remote object's class.
  *
+ * <li>Each remote interface must either be public and reside in a package that is
+ * {@linkplain java.lang.reflect.Module#isExported(String,java.lang.reflect.Module) exported}
+ * to at least the {@code java.rmi} module, or it must reside in a package that is
+ * {@linkplain java.lang.reflect.Module#isOpen(String,java.lang.reflect.Module) open}
+ * to at least the {@code java.rmi} module.
+ *
  * <li>The proxy's invocation handler is a {@link
  * RemoteObjectInvocationHandler} instance constructed with a
  * {@link RemoteRef}.
--- a/jdk/src/java.rmi/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.rmi/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Defines the Remote Method Invocation (RMI) API.
+ *
+ * @since 9
  */
 module java.rmi {
     requires java.logging;
--- a/jdk/src/java.scripting/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.scripting/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Defines the Scripting API.
+ *
+ * @since 9
  */
 module java.scripting {
     exports javax.script;
--- a/jdk/src/java.se.ee/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.se.ee/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -28,6 +28,8 @@
  * <P>
  * This module requires {@code java.se} and supplements it with modules
  * that define CORBA and Java EE APIs. These modules are upgradeable.
+ *
+ * @since 9
  */
 @SuppressWarnings("deprecation")
 module java.se.ee {
--- a/jdk/src/java.se/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.se/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -28,6 +28,8 @@
  * <P>
  * The modules defining CORBA and Java EE APIs are not required by
  * this module, but they are required by {@code java.se.ee}.
+ *
+ * @since 9
  */
 module java.se {
     requires transitive java.compiler;
--- a/jdk/src/java.security.jgss/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.security.jgss/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -27,6 +27,8 @@
  * Defines the Java binding of the IETF Generic Security Services API (GSS-API).
  * <P>
  * This module also contains GSS-API mechanisms including Kerberos v5 and SPNEGO.
+ *
+ * @since 9
  */
 module java.security.jgss {
     requires java.naming;
--- a/jdk/src/java.security.sasl/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.security.sasl/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -29,6 +29,8 @@
  * <P>
  * This module also contains SASL mechanisms including DIGEST-MD5,
  * CRAM-MD5, and NTLM.
+ *
+ * @since 9
  */
 module java.security.sasl {
     requires java.logging;
--- a/jdk/src/java.smartcardio/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.smartcardio/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Defines the Java Smart Card I/O API.
+ *
+ * @since 9
  */
 module java.smartcardio {
     exports javax.smartcardio;
--- a/jdk/src/java.sql.rowset/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.sql.rowset/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Defines the JDBC RowSet API.
+ *
+ * @since 9
  */
 module java.sql.rowset {
     requires transitive java.logging;
--- a/jdk/src/java.sql/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.sql/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Defines the JDBC API.
+ *
+ * @since 9
  */
 module java.sql {
     requires transitive java.logging;
--- a/jdk/src/java.transaction/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.transaction/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -28,6 +28,8 @@
  * <P>
  * The subset consists of RMI exception types which are mapped to CORBA system
  * exceptions by the 'Java Language to IDL Mapping Specification'.
+ *
+ * @since 9
  */
 module java.transaction {
     requires transitive java.rmi;
--- a/jdk/src/java.xml.crypto/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/java.xml.crypto/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Defines an API for XML cryptography.
+ *
+ * @since 9
  */
 module java.xml.crypto {
     requires transitive java.xml;
--- a/jdk/src/jdk.attach/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.attach/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Defines the attach API.
+ *
+ * @since 9
  */
 module jdk.attach {
     requires jdk.internal.jvmstat;
--- a/jdk/src/jdk.crypto.ucrypto/solaris/conf/security/ucrypto-solaris.cfg	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.crypto.ucrypto/solaris/conf/security/ucrypto-solaris.cfg	Wed Jul 05 22:52:01 2017 +0200
@@ -2,8 +2,5 @@
 # Configuration file for the OracleUcrypto provider
 #
 disabledServices = {
-  # disabled due to Solaris bug 7121679
-  Cipher.AES/CFB128/PKCS5Padding
-  Cipher.AES/CFB128/NoPadding
 }
 
--- a/jdk/src/jdk.desktop/share/classes/jdk/awt/AWTUtils.java	Mon Feb 13 11:57:56 2017 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,95 +0,0 @@
-/*
- * Copyright (c) 2016, 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 jdk.awt;
-
-import java.awt.Component;
-import java.awt.Shape;
-
-import com.sun.awt.AWTUtilities;
-
-/**
- * A class to allow access to JDK-specific utility methods.
- * Methods in this class are always deprecated since a caller
- * should be aware they may be removed and replaced in the future.
- * Access using reflection is highly recommended.
- * @since 9
- */
-public final class AWTUtils {
-
-    /**
-     * No-one should be creating instances of this class.
-     */
-    private AWTUtils() {
-    }
-
-    /**
-     * Sets a 'mixing-cutout' shape for the given component.
-     *
-     * By default a lightweight component is treated as an opaque rectangle for
-     * the purposes of the Heavyweight/Lightweight Components Mixing feature.
-     * This method enables developers to set an arbitrary shape to be cut out
-     * from heavyweight components positioned underneath the lightweight
-     * component in the z-order.
-     * <p>
-     * The {@code shape} argument may have the following values:
-     * <ul>
-     * <li>{@code null} - reverts the default cutout shape (the rectangle equal
-     * to the component's {@code getBounds()})
-     * <li><i>empty-shape</i> - does not cut out anything from heavyweight
-     * components. This makes the given lightweight component effectively
-     * transparent. Note that descendants of the lightweight component still
-     * affect the shapes of heavyweight components.  An example of an
-     * <i>empty-shape</i> is {@code new Rectangle()}.
-     * <li><i>non-empty-shape</i> - the given shape will be cut out from
-     * heavyweight components.
-     * </ul>
-     * <p>
-     * The most common example when the 'mixing-cutout' shape is needed is a
-     * glass pane component. The {@link JRootPane#setGlassPane()} method
-     * automatically sets the <i>empty-shape</i> as the 'mixing-cutout' shape
-     * for the given glass pane component.  If a developer needs some other
-     * 'mixing-cutout' shape for the glass pane (which is rare), this must be
-     * changed manually after installing the glass pane to the root pane.
-     * <p>
-     * Note that the 'mixing-cutout' shape neither affects painting, nor the
-     * mouse events handling for the given component. It is used exclusively
-     * for the purposes of the Heavyweight/Lightweight Components Mixing
-     * feature.
-     *
-     * @param component the component that needs non-default
-     * 'mixing-cutout' shape
-     * @param shape the new 'mixing-cutout' shape
-     * @throws NullPointerException if the component argument is {@code null}
-     * @deprecated This API may be removed or replaced.
-     */
-    @Deprecated
-    @SuppressWarnings("deprecation")
-    public static void setComponentMixingCutoutShape(Component component,
-                                                     Shape shape) {
-
-        AWTUtilities.setComponentMixingCutoutShape(component, shape);
-    }
-}
--- a/jdk/src/jdk.desktop/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,34 +0,0 @@
-/*
- * Copyright (c) 2016, 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.
- */
-
-/*
- * Provides non-SE desktop APIs.
- */
-
-module jdk.desktop {
-    requires transitive java.desktop;
-
-    exports jdk.awt;
-}
--- a/jdk/src/jdk.editpad/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.editpad/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Implementation of the edit pad service.
+ *
+ * @since 9
  */
 module jdk.editpad {
     requires jdk.internal.ed;
--- a/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/AsyncSSLDelegate.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/AsyncSSLDelegate.java	Wed Jul 05 22:52:01 2017 +0200
@@ -609,11 +609,13 @@
         }
 
         // SSLParameters.getApplicationProtocols() can't return null
+        // JDK 8 EXCL START
         for (String approto : p.getApplicationProtocols()) {
             sb.append("\n    application protocol: {")
               .append(params.size()).append("}");
             params.add(approto);
         }
+        // JDK 8 EXCL END
 
         if (p.getProtocols() != null) {
             for (String protocol : p.getProtocols()) {
--- a/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/DefaultPublisher.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/DefaultPublisher.java	Wed Jul 05 22:52:01 2017 +0200
@@ -91,11 +91,13 @@
                         for (long i = 0; i < nbItemsDemanded && !done.get(); i++) {
                             try {
                                 Optional<T> item = Objects.requireNonNull(supplier.get());
-                                item.ifPresentOrElse(subscriber::onNext, () -> {
+                                if (item.isPresent()) {
+                                    subscriber.onNext(item.get());
+                                } else {
                                     if (done.compareAndSet(false, true)) {
                                         subscriber.onComplete();
                                     }
-                                });
+                                }
                             } catch (RuntimeException e) {
                                 if (done.compareAndSet(false, true)) {
                                     subscriber.onError(e);
--- a/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/HttpResponse.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/HttpResponse.java	Wed Jul 05 22:52:01 2017 +0200
@@ -30,6 +30,8 @@
 import java.net.URI;
 import jdk.incubator.http.ResponseProcessors.MultiFile;
 import jdk.incubator.http.ResponseProcessors.MultiProcessorImpl;
+import static jdk.incubator.http.internal.common.Utils.unchecked;
+import static jdk.incubator.http.internal.common.Utils.charsetFrom;
 import java.nio.ByteBuffer;
 import java.nio.charset.Charset;
 import java.nio.charset.StandardCharsets;
@@ -269,19 +271,6 @@
             };
         }
 
-        /**
-         * Get the Charset from the Content-encoding header. Defaults to
-         * UTF_8
-         */
-        private static Charset charsetFrom(HttpHeaders headers) {
-            String encoding = headers.firstValue("Content-encoding")
-                    .orElse("UTF_8");
-            try {
-                return Charset.forName(encoding);
-            } catch (IllegalArgumentException e) {
-                return StandardCharsets.UTF_8;
-            }
-        }
 
         /**
          * Returns a {@code BodyHandler<Path>} that returns a
@@ -342,10 +331,6 @@
             };
         }
 
-        private static UncheckedIOException unchecked(IOException e) {
-            return new UncheckedIOException(e);
-        }
-
         /**
          * Returns a {@code BodyHandler<Path>} that returns a
          * {@link BodyProcessor BodyProcessor}{@code <Path>} obtained from
@@ -743,48 +728,5 @@
             return asMap(pushHandler, true);
         }
 
-        /**
-         * Returns a {@code MultiProcessor} which writes the response bodies to
-         * files under a given root directory and which returns an aggregate
-         * response map that is a {@code Map<HttpRequest, HttpResponse<Path>>}.
-         * The keyset of the {@code Map} represents the original request and any
-         * additional requests generated by the server. The values are the
-         * responses containing the paths of the destination files. Each file
-         * uses the URI path of the request relative to the destination parent
-         * directorycprovided.
-         *
-         * <p>
-         * All incoming additional requests (push promises) are accepted by this
-         * multi response processor. Errors are effectively ignored and any
-         * failed responses are simply omitted from the result {@code Map}.
-         * Other implementations of {@code MultiProcessor} may handle these
-         * situations.
-         *
-         * <p>
-         * <b>Example usage</b>
-         * <pre>
-         * {@code
-         *    HttpClient client = ..
-         *    HttpRequest request = HttpRequest
-         *               .create(new URI("https://www.foo.com/"))
-         *               .version(Version.HTTP2)
-         *               .GET();
-         *
-         *    Map<HttpRequest, HttpResponse<Path>>> map = client
-         *               .sendAsync(HttpResponse.MultiProcessor.multiFile("/usr/destination"))
-         *               .join();
-         *
-         * }
-         * </pre>
-         * TEMPORARILY REMOVING THIS FROM API. MIGHT NOT BE NEEDED.
-         *
-         * @param destination the destination parent directory of all response
-         * bodies
-         * @return a MultiProcessor
-         */
-        private static MultiProcessor<MultiMapResult<Path>,Path> multiFile(Path destination) {
-            MultiFile mf = new MultiFile(destination);
-            return new MultiProcessorImpl<Path>(mf::handlePush, true);
-        }
     }
 }
--- a/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/ResponseProcessors.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/ResponseProcessors.java	Wed Jul 05 22:52:01 2017 +0200
@@ -252,7 +252,7 @@
 
         @Override
         public void onError(HttpRequest request, Throwable t) {
-            results.put(request, CompletableFuture.failedFuture(t));
+            results.put(request, MinimalFuture.failedFuture(t));
         }
 
         @Override
--- a/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/SSLDelegate.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/SSLDelegate.java	Wed Jul 05 22:52:01 2017 +0200
@@ -449,9 +449,11 @@
         for (String cipher : p.getCipherSuites()) {
                 System.out.printf("cipher: %s\n", cipher);
         }
+        // JDK 8 EXCL START
         for (String approto : p.getApplicationProtocols()) {
                 System.out.printf("application protocol: %s\n", approto);
         }
+        // JDK 8 EXCL END
         for (String protocol : p.getProtocols()) {
                 System.out.printf("protocol: %s\n", protocol);
         }
--- a/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/internal/common/MinimalFuture.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/internal/common/MinimalFuture.java	Wed Jul 05 22:52:01 2017 +0200
@@ -110,7 +110,6 @@
         }
     }
 
-    @Override
     public <U> MinimalFuture<U> newIncompleteFuture() {
         return new MinimalFuture<>();
     }
--- a/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/internal/common/Queue.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/internal/common/Queue.java	Wed Jul 05 22:52:01 2017 +0200
@@ -118,11 +118,13 @@
     public synchronized void closeExceptionally(Throwable t) {
         if (exception == null) exception = t;
         else if (t != null && t != exception) {
-            Stream.of(exception.getSuppressed())
+            if (!Stream.of(exception.getSuppressed())
                 .filter(x -> x == t)
                 .findFirst()
-                .ifPresentOrElse((x) -> {},
-                                 () -> exception.addSuppressed(t));
+                .isPresent())
+            {
+                exception.addSuppressed(t);
+            }
         }
         close();
     }
--- a/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/internal/common/Utils.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/internal/common/Utils.java	Wed Jul 05 22:52:01 2017 +0200
@@ -32,12 +32,14 @@
 import java.io.ByteArrayOutputStream;
 import java.io.Closeable;
 import java.io.IOException;
+import java.io.UncheckedIOException;
 import java.io.PrintStream;
 import java.io.UnsupportedEncodingException;
 import java.net.NetPermission;
 import java.net.URI;
 import java.net.URLPermission;
 import java.nio.ByteBuffer;
+import java.nio.charset.Charset;
 import java.nio.charset.StandardCharsets;
 import java.security.AccessController;
 import java.security.PrivilegedAction;
@@ -54,6 +56,7 @@
 import java.util.concurrent.Executors;
 import java.util.concurrent.LinkedBlockingQueue;
 import java.util.function.Predicate;
+import jdk.incubator.http.HttpHeaders;
 
 /**
  * Miscellaneous utilities
@@ -259,9 +262,11 @@
         SSLParameters p1 = new SSLParameters();
         p1.setAlgorithmConstraints(p.getAlgorithmConstraints());
         p1.setCipherSuites(p.getCipherSuites());
+        // JDK 8 EXCL START
         p1.setEnableRetransmissions(p.getEnableRetransmissions());
+        p1.setMaximumPacketSize(p.getMaximumPacketSize());
+        // JDK 8 EXCL END
         p1.setEndpointIdentificationAlgorithm(p.getEndpointIdentificationAlgorithm());
-        p1.setMaximumPacketSize(p.getMaximumPacketSize());
         p1.setNeedClientAuth(p.getNeedClientAuth());
         String[] protocols = p.getProtocols();
         if (protocols != null) {
@@ -475,4 +480,21 @@
         return newb;
     }
 
+    /**
+     * Get the Charset from the Content-encoding header. Defaults to
+     * UTF_8
+     */
+    public static Charset charsetFrom(HttpHeaders headers) {
+        String encoding = headers.firstValue("Content-encoding")
+                .orElse("UTF_8");
+        try {
+            return Charset.forName(encoding);
+        } catch (IllegalArgumentException e) {
+            return StandardCharsets.UTF_8;
+        }
+    }
+
+    public static UncheckedIOException unchecked(IOException e) {
+        return new UncheckedIOException(e);
+    }
 }
--- a/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/internal/websocket/FrameConsumer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/internal/websocket/FrameConsumer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -26,6 +26,7 @@
 package jdk.incubator.http.internal.websocket;
 
 import jdk.incubator.http.WebSocket.MessagePart;
+import jdk.incubator.http.internal.common.Log;
 import jdk.incubator.http.internal.websocket.Frame.Opcode;
 
 import java.nio.ByteBuffer;
@@ -33,13 +34,11 @@
 import java.nio.charset.CharacterCodingException;
 
 import static java.lang.String.format;
-import static java.lang.System.Logger.Level.TRACE;
 import static java.nio.charset.StandardCharsets.UTF_8;
 import static java.util.Objects.requireNonNull;
 import static jdk.incubator.http.internal.common.Utils.dump;
 import static jdk.incubator.http.internal.websocket.StatusCodes.NO_STATUS_CODE;
 import static jdk.incubator.http.internal.websocket.StatusCodes.checkIncomingCode;
-import static jdk.incubator.http.internal.websocket.WebSocketImpl.logger;
 
 /*
  * Consumes frame parts and notifies a message consumer, when there is
@@ -71,17 +70,13 @@
 
     @Override
     public void fin(boolean value) {
-        if (logger.isLoggable(TRACE)) {
-            logger.log(TRACE, "Reading fin: {0}", value);
-        }
+        Log.logTrace("Reading fin: {0}", value);
         fin = value;
     }
 
     @Override
     public void rsv1(boolean value) {
-        if (logger.isLoggable(TRACE)) {
-            logger.log(TRACE, "Reading rsv1: {0}", value);
-        }
+        Log.logTrace("Reading rsv1: {0}", value);
         if (value) {
             throw new FailWebSocketException("Unexpected rsv1 bit");
         }
@@ -89,9 +84,7 @@
 
     @Override
     public void rsv2(boolean value) {
-        if (logger.isLoggable(TRACE)) {
-            logger.log(TRACE, "Reading rsv2: {0}", value);
-        }
+        Log.logTrace("Reading rsv2: {0}", value);
         if (value) {
             throw new FailWebSocketException("Unexpected rsv2 bit");
         }
@@ -99,9 +92,7 @@
 
     @Override
     public void rsv3(boolean value) {
-        if (logger.isLoggable(TRACE)) {
-            logger.log(TRACE, "Reading rsv3: {0}", value);
-        }
+        Log.logTrace("Reading rsv3: {0}", value);
         if (value) {
             throw new FailWebSocketException("Unexpected rsv3 bit");
         }
@@ -109,7 +100,7 @@
 
     @Override
     public void opcode(Opcode v) {
-        logger.log(TRACE, "Reading opcode: {0}", v);
+        Log.logTrace("Reading opcode: {0}", v);
         if (v == Opcode.PING || v == Opcode.PONG || v == Opcode.CLOSE) {
             if (!fin) {
                 throw new FailWebSocketException("Fragmented control frame  " + v);
@@ -137,9 +128,7 @@
 
     @Override
     public void mask(boolean value) {
-        if (logger.isLoggable(TRACE)) {
-            logger.log(TRACE, "Reading mask: {0}", value);
-        }
+        Log.logTrace("Reading mask: {0}", value);
         if (value) {
             throw new FailWebSocketException("Masked frame received");
         }
@@ -147,10 +136,7 @@
 
     @Override
     public void payloadLen(long value) {
-        if (logger.isLoggable(TRACE)) {
-            // Checked for being loggable because of autoboxing of 'value'
-            logger.log(TRACE, "Reading payloadLen: {0}", value);
-        }
+        Log.logTrace("Reading payloadLen: {0}", value);
         if (opcode.isControl()) {
             if (value > 125) {
                 throw new FailWebSocketException(
@@ -178,9 +164,7 @@
 
     @Override
     public void payloadData(ByteBuffer data) {
-        if (logger.isLoggable(TRACE)) {
-            logger.log(TRACE, "Reading payloadData: data={0}", data);
-        }
+        Log.logTrace("Reading payloadData: data={0}", data);
         unconsumedPayloadLen -= data.remaining();
         boolean isLast = unconsumedPayloadLen == 0;
         if (opcode.isControl()) {
--- a/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/internal/websocket/UTF8AccumulatingDecoder.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/internal/websocket/UTF8AccumulatingDecoder.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 package jdk.incubator.http.internal.websocket;
 
+import jdk.incubator.http.internal.common.Log;
+
 import java.nio.ByteBuffer;
 import java.nio.CharBuffer;
 import java.nio.charset.CharacterCodingException;
@@ -32,10 +34,8 @@
 import java.nio.charset.CoderResult;
 import java.nio.charset.CodingErrorAction;
 
-import static java.lang.System.Logger.Level.WARNING;
 import static java.nio.charset.StandardCharsets.UTF_8;
 import static jdk.incubator.http.internal.common.Utils.EMPTY_BYTEBUFFER;
-import static jdk.incubator.http.internal.websocket.WebSocketImpl.logger;
 
 final class UTF8AccumulatingDecoder {
 
@@ -74,9 +74,8 @@
         // Since it's UTF-8, the assumption is leftovers.remaining() < 4
         // (i.e. small). Otherwise a shared buffer should be used
         if (!(leftovers.remaining() < 4)) {
-            logger.log(WARNING,
-                       "The size of decoding leftovers is greater than expected: {0}",
-                       leftovers.remaining());
+            Log.logError("The size of decoding leftovers is greater than expected: {0}",
+                         leftovers.remaining());
         }
         b.position(b.limit()); // As if we always read to the end
         // Decoder promises that in the case of endOfInput == true:
--- a/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/internal/websocket/WebSocketImpl.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.incubator.httpclient/share/classes/jdk/incubator/http/internal/websocket/WebSocketImpl.java	Wed Jul 05 22:52:01 2017 +0200
@@ -26,6 +26,7 @@
 package jdk.incubator.http.internal.websocket;
 
 import jdk.incubator.http.WebSocket;
+import jdk.incubator.http.internal.common.Log;
 import jdk.incubator.http.internal.common.Pair;
 import jdk.incubator.http.internal.websocket.OpeningHandshake.Result;
 import jdk.incubator.http.internal.websocket.OutgoingMessage.Binary;
@@ -47,8 +48,6 @@
 import java.util.function.Consumer;
 import java.util.function.Function;
 
-import static java.lang.System.Logger.Level.ERROR;
-import static java.lang.System.Logger.Level.TRACE;
 import static java.util.Objects.requireNonNull;
 import static java.util.concurrent.CompletableFuture.failedFuture;
 import static jdk.incubator.http.internal.common.Pair.pair;
@@ -61,8 +60,6 @@
  */
 final class WebSocketImpl implements WebSocket {
 
-    static final System.Logger logger = System.getLogger("jdk.httpclient.WebSocket");
-
     private final URI uri;
     private final String subprotocol;
     private final RawChannel channel;
@@ -142,7 +139,7 @@
                     try {
                         channel.close();
                     } catch (IOException e) {
-                        logger.log(ERROR, e);
+                        Log.logError(e);
                     } finally {
                         closed.set(true);
                     }
@@ -168,14 +165,14 @@
     private void signalError(Throwable error) {
         synchronized (lock) {
             if (lastMethodInvoked) {
-                logger.log(ERROR, error);
+                Log.logError(error);
             } else {
                 lastMethodInvoked = true;
                 receiver.close();
                 try {
                     listener.onError(this, error);
                 } catch (Exception e) {
-                    logger.log(ERROR, e);
+                    Log.logError(e);
                 }
             }
         }
@@ -190,7 +187,7 @@
         try {
             channel.shutdownInput();
         } catch (IOException e) {
-            logger.log(ERROR, e);
+            Log.logError(e);
         }
         boolean wasComplete = !closeReceived.complete(null);
         if (wasComplete) {
@@ -210,7 +207,7 @@
             enqueueClose(new Close(code, ""))
                     .whenComplete((r1, error1) -> {
                         if (error1 != null) {
-                            logger.log(ERROR, error1);
+                            Log.logError(error1);
                         }
                     });
         });
@@ -223,14 +220,14 @@
     private CompletionStage<?> signalClose(int statusCode, String reason) {
         synchronized (lock) {
             if (lastMethodInvoked) {
-                logger.log(TRACE, "Close: {0}, ''{1}''", statusCode, reason);
+                Log.logTrace("Close: {0}, ''{1}''", statusCode, reason);
             } else {
                 lastMethodInvoked = true;
                 receiver.close();
                 try {
                     return listener.onClose(this, statusCode, reason);
                 } catch (Exception e) {
-                    logger.log(ERROR, e);
+                    Log.logError(e);
                 }
             }
         }
@@ -289,7 +286,7 @@
             try {
                 channel.shutdownOutput();
             } catch (IOException e) {
-                logger.log(ERROR, e);
+                Log.logError(e);
             }
             boolean wasComplete = !closeSent.complete(null);
             if (wasComplete) {
--- a/jdk/src/jdk.incubator.httpclient/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.incubator.httpclient/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -26,6 +26,8 @@
 /**
  * Defines the high-level HTTP and WebSocket API.
  * {@Incubating}
+ *
+ * @since 9
  */
 module jdk.incubator.httpclient {
     requires java.base;
--- a/jdk/src/jdk.internal.ed/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.internal.ed/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -26,6 +26,8 @@
 /**
  * Internal editor support for JDK tools.  Includes the Service Provider
  * Interface to built-in editors.
+ *
+ * @since 9
  */
 module jdk.internal.ed {
 
--- a/jdk/src/jdk.internal.le/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.internal.le/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Internal API for line editing
+ *
+ * @since 9
  */
 module jdk.internal.le {
     exports jdk.internal.jline to
--- a/jdk/src/jdk.internal.opt/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.internal.opt/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Internal option processing API
+ *
+ * @since 9
  */
 module jdk.internal.opt {
     exports jdk.internal.joptsimple to jdk.jlink, jdk.jshell;
--- a/jdk/src/jdk.jartool/share/classes/com/sun/jarsigner/ContentSigner.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.jartool/share/classes/com/sun/jarsigner/ContentSigner.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2017, 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
@@ -38,7 +38,7 @@
  * @deprecated This class has been deprecated.
  */
 
-@Deprecated
+@Deprecated(since="9")
 public abstract class ContentSigner {
 
     /**
--- a/jdk/src/jdk.jartool/share/classes/com/sun/jarsigner/ContentSignerParameters.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.jartool/share/classes/com/sun/jarsigner/ContentSignerParameters.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 2017, 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
@@ -36,7 +36,7 @@
  * @author Vincent Ryan
  * @deprecated This class has been deprecated.
  */
-@Deprecated
+@Deprecated(since="9")
 public interface ContentSignerParameters {
 
     /**
--- a/jdk/src/jdk.jartool/share/classes/sun/tools/jar/GNUStyleOptions.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.jartool/share/classes/sun/tools/jar/GNUStyleOptions.java	Wed Jul 05 22:52:01 2017 +0200
@@ -157,8 +157,7 @@
                     for (String dir : dirs) {
                         paths[i++] = Paths.get(dir);
                     }
-                    jartool.moduleFinder =
-                        new ModulePath(Runtime.version(), true, paths);
+                    jartool.moduleFinder = ModulePath.of(Runtime.version(), true, paths);
                 }
             },
             new Option(false, OptionType.CREATE_UPDATE, "--do-not-resolve-by-default") {
--- a/jdk/src/jdk.jartool/share/classes/sun/tools/jar/Main.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.jartool/share/classes/sun/tools/jar/Main.java	Wed Jul 05 22:52:01 2017 +0200
@@ -158,7 +158,7 @@
     static final String MANIFEST_DIR = "META-INF/";
     static final String VERSIONS_DIR = MANIFEST_DIR + "versions/";
     static final String VERSION = "1.0";
-
+    static final int VERSIONS_DIR_LENGTH = VERSIONS_DIR.length();
     private static ResourceBundle rsrc;
 
     /**
@@ -681,7 +681,7 @@
     void addPackageIfNamed(Set<String> packages, String name) {
         if (name.startsWith(VERSIONS_DIR)) {
             // trim the version dir prefix
-            int i0 = VERSIONS_DIR.length();
+            int i0 = VERSIONS_DIR_LENGTH;
             int i = name.indexOf('/', i0);
             if (i <= 0) {
                 warn(formatMsg("warn.release.unexpected.versioned.entry", name));
@@ -699,7 +699,7 @@
         }
         String pn = toPackageName(name);
         // add if this is a class or resource in a package
-        if (Checks.isJavaIdentifier(pn)) {
+        if (Checks.isPackageName(pn)) {
             packages.add(pn);
         }
     }
@@ -1727,12 +1727,16 @@
     private boolean printModuleDescriptor(ZipFile zipFile)
         throws IOException
     {
-        ZipEntry entry = zipFile.getEntry(MODULE_INFO);
-        if (entry ==  null)
+        ZipEntry[] zes = zipFile.stream()
+            .filter(e -> isModuleInfoEntry(e.getName()))
+            .sorted(Validator.ENTRY_COMPARATOR)
+            .toArray(ZipEntry[]::new);
+        if (zes.length == 0)
             return false;
-
-        try (InputStream is = zipFile.getInputStream(entry)) {
-            printModuleDescriptor(is);
+        for (ZipEntry ze : zes) {
+            try (InputStream is = zipFile.getInputStream(ze)) {
+                printModuleDescriptor(is, ze.getName());
+            }
         }
         return true;
     }
@@ -1742,16 +1746,23 @@
     {
         try (BufferedInputStream bis = new BufferedInputStream(fis);
              ZipInputStream zis = new ZipInputStream(bis)) {
-
             ZipEntry e;
             while ((e = zis.getNextEntry()) != null) {
-                if (e.getName().equals(MODULE_INFO)) {
-                    printModuleDescriptor(zis);
-                    return true;
+                String ename = e.getName();
+                if (isModuleInfoEntry(ename)){
+                    moduleInfos.put(ename, zis.readAllBytes());
                 }
             }
         }
-        return false;
+        if (moduleInfos.size() == 0)
+            return false;
+        String[] names = moduleInfos.keySet().stream()
+            .sorted(Validator.ENTRYNAME_COMPARATOR)
+            .toArray(String[]::new);
+        for (String name : names) {
+            printModuleDescriptor(new ByteArrayInputStream(moduleInfos.get(name)), name);
+        }
+        return true;
     }
 
     static <T> String toString(Collection<T> set) {
@@ -1760,7 +1771,7 @@
                   .collect(joining(" "));
     }
 
-    private void printModuleDescriptor(InputStream entryInputStream)
+    private void printModuleDescriptor(InputStream entryInputStream, String ename)
         throws IOException
     {
         ModuleInfo.Attributes attrs = ModuleInfo.read(entryInputStream, null);
@@ -1768,10 +1779,12 @@
         ModuleHashes hashes = attrs.recordedHashes();
 
         StringBuilder sb = new StringBuilder();
-        sb.append("\n");
+        sb.append("\nmodule ")
+          .append(md.toNameAndVersion())
+          .append(" (").append(ename).append(")");
+
         if (md.isOpen())
-            sb.append("open ");
-        sb.append(md.toNameAndVersion());
+            sb.append("\n  open ");
 
         md.requires().stream()
             .sorted(Comparator.comparing(Requires::name))
@@ -1879,7 +1892,7 @@
             if (end == 0)
                 return true;
             if (name.startsWith(VERSIONS_DIR)) {
-                int off = VERSIONS_DIR.length();
+                int off = VERSIONS_DIR_LENGTH;
                 if (off == end)      // meta-inf/versions/module-info.class
                     return false;
                 while (off < end - 1) {
@@ -1995,7 +2008,7 @@
             }
             // get a resolved module graph
             Configuration config =
-                Configuration.empty().resolveRequires(system, finder, roots);
+                Configuration.empty().resolve(system, finder, roots);
 
             // filter modules resolved from the system module finder
             this.modules = config.modules().stream()
--- a/jdk/src/jdk.jartool/share/classes/sun/tools/jar/Validator.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.jartool/share/classes/sun/tools/jar/Validator.java	Wed Jul 05 22:52:01 2017 +0200
@@ -49,6 +49,7 @@
 
 import static java.util.jar.JarFile.MANIFEST_NAME;
 import static sun.tools.jar.Main.VERSIONS_DIR;
+import static sun.tools.jar.Main.VERSIONS_DIR_LENGTH;
 import static sun.tools.jar.Main.MODULE_INFO;
 import static sun.tools.jar.Main.getMsg;
 import static sun.tools.jar.Main.formatMsg;
@@ -59,19 +60,19 @@
 final class Validator {
     private final static boolean DEBUG = Boolean.getBoolean("jar.debug");
     private final  Map<String,FingerPrint> fps = new HashMap<>();
-    private static final int vdlen = VERSIONS_DIR.length();
     private final Main main;
     private final JarFile jf;
     private int oldVersion = -1;
     private String currentTopLevelName;
     private boolean isValid = true;
-    private Set<String> concealedPkgs;
+    private Set<String> concealedPkgs = Collections.emptySet();
     private ModuleDescriptor md;
+    private String mdName;
 
     private Validator(Main main, JarFile jf) {
         this.main = main;
         this.jf = jf;
-        loadModuleDescriptor();
+        checkModuleDescriptor(MODULE_INFO);
     }
 
     static boolean validate(Main main, JarFile jf) throws IOException {
@@ -83,7 +84,7 @@
             jf.stream()
               .filter(e -> !e.isDirectory() &&
                       !e.getName().equals(MANIFEST_NAME))
-              .sorted(entryComparator)
+              .sorted(ENTRY_COMPARATOR)
               .forEachOrdered(e -> validate(e));
             return isValid;
         } catch (InvalidJarException e) {
@@ -102,9 +103,8 @@
     // sort base entries before versioned entries, and sort entry classes with
     // nested classes so that the top level class appears before the associated
     // nested class
-    private static Comparator<JarEntry> entryComparator = (je1, je2) ->  {
-        String s1 = je1.getName();
-        String s2 = je2.getName();
+    static Comparator<String> ENTRYNAME_COMPARATOR = (s1, s2) ->  {
+
         if (s1.equals(s2)) return 0;
         boolean b1 = s1.startsWith(VERSIONS_DIR);
         boolean b2 = s2.startsWith(VERSIONS_DIR);
@@ -140,6 +140,9 @@
         return l1 - l2;
     };
 
+    static Comparator<ZipEntry> ENTRY_COMPARATOR =
+        Comparator.comparing(ZipEntry::getName, ENTRYNAME_COMPARATOR);
+
     /*
      *  Validator has state and assumes entries provided to accept are ordered
      *  from base entries first and then through the versioned entries in
@@ -158,24 +161,25 @@
 
         // validate the versioned module-info
         if (isModuleInfoEntry(entryName)) {
-            if (entryName.length() != MODULE_INFO.length())
-                checkModuleDescriptor(je);
+            if (!entryName.equals(mdName))
+                checkModuleDescriptor(entryName);
             return;
         }
 
         // figure out the version and basename from the JarEntry
         int version;
         String basename;
+        String versionStr = null;;
         if (entryName.startsWith(VERSIONS_DIR)) {
-            int n = entryName.indexOf("/", vdlen);
+            int n = entryName.indexOf("/", VERSIONS_DIR_LENGTH);
             if (n == -1) {
                 error(formatMsg("error.validator.version.notnumber", entryName));
                 isValid = false;
                 return;
             }
-            String v = entryName.substring(vdlen, n);
+            versionStr = entryName.substring(VERSIONS_DIR_LENGTH, n);
             try {
-                version = Integer.parseInt(v);
+                version = Integer.parseInt(versionStr);
             } catch (NumberFormatException x) {
                 error(formatMsg("error.validator.version.notnumber", entryName));
                 isValid = false;
@@ -196,6 +200,11 @@
         if (oldVersion != version) {
             oldVersion = version;
             currentTopLevelName = null;
+            if (md == null && versionStr != null) {
+                // don't have a base module-info.class yet, try to see if
+                // a versioned one exists
+                checkModuleDescriptor(VERSIONS_DIR + versionStr + "/" + MODULE_INFO);
+            }
         }
 
         // analyze the entry, keeping key attributes
@@ -308,61 +317,52 @@
         return;
     }
 
-    private void loadModuleDescriptor() {
-        ZipEntry je = jf.getEntry(MODULE_INFO);
-        if (je != null) {
-            try (InputStream jis = jf.getInputStream(je)) {
-                md = ModuleDescriptor.read(jis);
-                concealedPkgs = new HashSet<>(md.packages());
-                md.exports().stream().map(Exports::source).forEach(concealedPkgs::remove);
-                md.opens().stream().map(Opens::source).forEach(concealedPkgs::remove);
-                return;
-            } catch (Exception x) {
-                error(x.getMessage() + " : " + je.getName());
-                this.isValid = false;
-            }
-        }
-        md = null;
-        concealedPkgs = Collections.emptySet();
-    }
-
-    private static boolean isPlatformModule(String name) {
-        return name.startsWith("java.") || name.startsWith("jdk.");
-    }
-
     /**
      * Checks whether or not the given versioned module descriptor's attributes
-     * are valid when compared against the root module descriptor.
+     * are valid when compared against the root/base module descriptor.
      *
-     * A versioned module descriptor must be identical to the root module
+     * A versioned module descriptor must be identical to the root/base module
      * descriptor, with two exceptions:
      *  - A versioned descriptor can have different non-public `requires`
      *    clauses of platform ( `java.*` and `jdk.*` ) modules, and
      *  - A versioned descriptor can have different `uses` clauses, even of
      *    service types defined outside of the platform modules.
      */
-    private void checkModuleDescriptor(JarEntry je) {
-        try (InputStream is = jf.getInputStream(je)) {
-            ModuleDescriptor root = this.md;
-            ModuleDescriptor md = null;
-            try {
-                md = ModuleDescriptor.read(is);
-            } catch (InvalidModuleDescriptorException x) {
-                error(x.getMessage());
-                isValid = false;
-                return;
-            }
-            if (root == null) {
-                this.md = md;
-            } else {
-                if (!root.name().equals(md.name())) {
+    private void checkModuleDescriptor(String miName) {
+        ZipEntry je = jf.getEntry(miName);
+        if (je != null) {
+            try (InputStream jis = jf.getInputStream(je)) {
+                ModuleDescriptor md = ModuleDescriptor.read(jis);
+                // Initialize the base md if it's not yet. A "base" md can be either the
+                // root module-info.class or the first versioned module-info.class
+                ModuleDescriptor base = this.md;
+
+                if (base == null) {
+                    concealedPkgs = new HashSet<>(md.packages());
+                    md.exports().stream().map(Exports::source).forEach(concealedPkgs::remove);
+                    md.opens().stream().map(Opens::source).forEach(concealedPkgs::remove);
+                    // must have the implementation class of the services it 'provides'.
+                    if (md.provides().stream().map(Provides::providers)
+                          .flatMap(List::stream)
+                          .filter(p -> jf.getEntry(toBinaryName(p)) == null)
+                          .peek(p -> error(formatMsg("error.missing.provider", p)))
+                          .count() != 0) {
+                        isValid = false;
+                        return;
+                    }
+                    this.md = md;
+                    this.mdName = miName;
+                    return;
+                }
+
+                if (!base.name().equals(md.name())) {
                     error(getMsg("error.validator.info.name.notequal"));
                     isValid = false;
                 }
-                if (!root.requires().equals(md.requires())) {
-                    Set<Requires> rootRequires = root.requires();
+                if (!base.requires().equals(md.requires())) {
+                    Set<Requires> baseRequires = base.requires();
                     for (Requires r : md.requires()) {
-                        if (rootRequires.contains(r))
+                        if (baseRequires.contains(r))
                             continue;
                         if (r.modifiers().contains(Requires.Modifier.TRANSITIVE)) {
                             error(getMsg("error.validator.info.requires.transitive"));
@@ -372,7 +372,7 @@
                             isValid = false;
                         }
                     }
-                    for (Requires r : rootRequires) {
+                    for (Requires r : baseRequires) {
                         Set<Requires> mdRequires = md.requires();
                         if (mdRequires.contains(r))
                             continue;
@@ -382,33 +382,37 @@
                         }
                     }
                 }
-                if (!root.exports().equals(md.exports())) {
+                if (!base.exports().equals(md.exports())) {
                     error(getMsg("error.validator.info.exports.notequal"));
                     isValid = false;
                 }
-                if (!root.opens().equals(md.opens())) {
+                if (!base.opens().equals(md.opens())) {
                     error(getMsg("error.validator.info.opens.notequal"));
                     isValid = false;
                 }
-                if (!root.provides().equals(md.provides())) {
+                if (!base.provides().equals(md.provides())) {
                     error(getMsg("error.validator.info.provides.notequal"));
                     isValid = false;
                 }
-                if (!root.mainClass().equals(md.mainClass())) {
+                if (!base.mainClass().equals(md.mainClass())) {
                     error(formatMsg("error.validator.info.manclass.notequal", je.getName()));
                     isValid = false;
                 }
-                if (!root.version().equals(md.version())) {
+                if (!base.version().equals(md.version())) {
                     error(formatMsg("error.validator.info.version.notequal", je.getName()));
                     isValid = false;
                 }
+            } catch (Exception x) {
+                error(x.getMessage() + " : " + miName);
+                this.isValid = false;
             }
-        } catch (IOException x) {
-            error(x.getMessage());
-            isValid = false;
         }
     }
 
+    private static boolean isPlatformModule(String name) {
+        return name.startsWith("java.") || name.startsWith("jdk.");
+    }
+
     private boolean checkInternalName(String entryName, String basename, String internalName) {
         String className = className(basename);
         if (internalName.equals(className)) {
--- a/jdk/src/jdk.jconsole/share/classes/sun/tools/jconsole/JConsole.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.jconsole/share/classes/sun/tools/jconsole/JConsole.java	Wed Jul 05 22:52:01 2017 +0200
@@ -128,7 +128,7 @@
             hotspotMI.setMnemonic(Resources.getMnemonicInt(Messages.HOTSPOT_MBEANS_ELLIPSIS));
             hotspotMI.setAccelerator(KeyStroke.
                                      getKeyStroke(KeyEvent.VK_H,
-                                                  InputEvent.CTRL_MASK));
+                                                  InputEvent.CTRL_DOWN_MASK));
             hotspotMI.addActionListener(this);
             connectionMenu.add(hotspotMI);
 
@@ -138,7 +138,7 @@
         connectMI = new JMenuItem(Messages.NEW_CONNECTION_ELLIPSIS);
         connectMI.setMnemonic(Resources.getMnemonicInt(Messages.NEW_CONNECTION_ELLIPSIS));
         connectMI.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_N,
-                                                        InputEvent.CTRL_MASK));
+                                                        InputEvent.CTRL_DOWN_MASK));
         connectMI.addActionListener(this);
         connectionMenu.add(connectMI);
 
@@ -147,7 +147,7 @@
         exitMI = new JMenuItem(Messages.EXIT);
         exitMI.setMnemonic(Resources.getMnemonicInt(Messages.EXIT));
         exitMI.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_F4,
-                                                     InputEvent.ALT_MASK));
+                                                     InputEvent.ALT_DOWN_MASK));
         exitMI.addActionListener(this);
         connectionMenu.add(exitMI);
 
@@ -223,7 +223,7 @@
             tileMI = new JMenuItem(Messages.TILE);
             tileMI.setMnemonic(Resources.getMnemonicInt(Messages.TILE));
             tileMI.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_T,
-                                                         InputEvent.CTRL_MASK));
+                                                         InputEvent.CTRL_DOWN_MASK));
             tileMI.addActionListener(JConsole.this);
             add(tileMI);
 
--- a/jdk/src/jdk.jconsole/share/classes/sun/tools/jconsole/VMPanel.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.jconsole/share/classes/sun/tools/jconsole/VMPanel.java	Wed Jul 05 22:52:01 2017 +0200
@@ -124,7 +124,9 @@
         addMouseListener(new MouseAdapter() {
 
             public void mouseClicked(MouseEvent e) {
-                if (connectedIconBounds != null && (e.getModifiers() & MouseEvent.BUTTON1_MASK) != 0 && connectedIconBounds.contains(e.getPoint())) {
+                if (connectedIconBounds != null
+                        && (e.getModifiersEx() & MouseEvent.BUTTON1_DOWN_MASK) != 0
+                        && connectedIconBounds.contains(e.getPoint())) {
 
                     if (isConnected()) {
                         userDisconnected = true;
--- a/jdk/src/jdk.jconsole/share/classes/sun/tools/jconsole/inspector/Utils.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.jconsole/share/classes/sun/tools/jconsole/inspector/Utils.java	Wed Jul 05 22:52:01 2017 +0200
@@ -438,7 +438,7 @@
         public void keyPressed(KeyEvent e) {
             // Accept "copy" key strokes
             KeyStroke ks = KeyStroke.getKeyStroke(
-                    e.getKeyCode(), e.getModifiers());
+                    e.getKeyCode(), e.getModifiersEx());
             JComponent comp = (JComponent) e.getSource();
             for (int i = 0; i < 3; i++) {
                 InputMap im = comp.getInputMap(i);
--- a/jdk/src/jdk.jdi/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.jdi/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Defines the Java Debugger Interface.
+ *
+ * @since 9
  */
 module jdk.jdi {
     requires jdk.attach;
--- a/jdk/src/jdk.jdwp.agent/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.jdwp.agent/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Java Debug Wire Protocol.
+ *
+ * @since 9
  */
 module jdk.jdwp.agent {
 }
--- a/jdk/src/jdk.jlink/share/classes/jdk/tools/jimage/resources/jimage.properties	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.jlink/share/classes/jdk/tools/jimage/resources/jimage.properties	Wed Jul 05 22:52:01 2017 +0200
@@ -98,3 +98,4 @@
 err.no.jimage=no jimage provided
 err.option.unsupported={0} not supported: {1}
 err.unknown.option=unknown option: {0}
+err.cannot.create.dir=cannot create directory {0}
--- a/jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/builder/DefaultImageBuilder.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/builder/DefaultImageBuilder.java	Wed Jul 05 22:52:01 2017 +0200
@@ -362,7 +362,7 @@
         String module = "/" + entry.moduleName() + "/";
         String filename = entry.path().substring(module.length());
 
-        // Remove radical native|config|...
+        // Remove radical lib|config|...
         return filename.substring(filename.indexOf('/') + 1);
     }
 
--- a/jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/AbstractResourcePoolEntry.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/AbstractResourcePoolEntry.java	Wed Jul 05 22:52:01 2017 +0200
@@ -38,7 +38,7 @@
  * <li>For jimage content: /{module name}/{package1}/.../{packageN}/{file
  * name}</li>
  * <li>For other files (shared lib, launchers, config, ...):/{module name}/
- * {@literal bin|conf|native}/{dir1}>/.../{dirN}/{file name}</li>
+ * {@literal bin|conf|lib}/{dir1}>/.../{dirN}/{file name}</li>
  * </ul>
  */
 abstract class AbstractResourcePoolEntry implements ResourcePoolEntry {
--- a/jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/JlinkTask.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/JlinkTask.java	Wed Jul 05 22:52:01 2017 +0200
@@ -29,6 +29,7 @@
 import java.io.PrintWriter;
 import java.io.UncheckedIOException;
 import java.lang.module.Configuration;
+import java.lang.module.FindException;
 import java.lang.module.ModuleDescriptor;
 import java.lang.module.ModuleFinder;
 import java.lang.module.ModuleReference;
@@ -232,7 +233,7 @@
 
             return EXIT_OK;
         } catch (PluginException | IllegalArgumentException |
-                 UncheckedIOException |IOException | ResolutionException e) {
+                 UncheckedIOException |IOException | FindException | ResolutionException e) {
             log.println(taskHelper.getMessage("error.prefix") + " " + e.getMessage());
             if (DEBUG) {
                 e.printStackTrace(log);
@@ -370,7 +371,7 @@
      */
     private ModuleFinder modulePathFinder() {
         Path[] entries = options.modulePath.toArray(new Path[0]);
-        ModuleFinder finder = new ModulePath(Runtime.version(), true, entries);
+        ModuleFinder finder = ModulePath.of(Runtime.version(), true, entries);
         if (!options.limitMods.isEmpty()) {
             finder = limitFinder(finder, options.limitMods, Collections.emptySet());
         }
@@ -388,7 +389,7 @@
                                                Set<String> roots)
     {
         Path[] entries = paths.toArray(new Path[0]);
-        ModuleFinder finder = new ModulePath(Runtime.version(), true, entries);
+        ModuleFinder finder = ModulePath.of(Runtime.version(), true, entries);
 
         // if limitmods is specified then limit the universe
         if (!limitMods.isEmpty()) {
@@ -418,9 +419,9 @@
         }
 
         Configuration cf = Configuration.empty()
-                .resolveRequires(finder,
-                                 ModuleFinder.of(),
-                                 roots);
+                .resolve(finder,
+                         ModuleFinder.of(),
+                         roots);
 
         // emit warning for modules that end with a digit
         cf.modules().stream()
@@ -458,9 +459,9 @@
 
         // resolve all root modules
         Configuration cf = Configuration.empty()
-                .resolveRequires(finder,
-                                 ModuleFinder.of(),
-                                 roots);
+                .resolve(finder,
+                         ModuleFinder.of(),
+                         roots);
 
         // module name -> reference
         Map<String, ModuleReference> map = new HashMap<>();
--- a/jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/ResourcePoolConfiguration.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/ResourcePoolConfiguration.java	Wed Jul 05 22:52:01 2017 +0200
@@ -51,7 +51,7 @@
         ModuleDescriptor md = mod.descriptor();
 
         // drop hashes
-        ModuleDescriptor.Builder builder = ModuleDescriptor.module(md.name());
+        ModuleDescriptor.Builder builder = ModuleDescriptor.newModule(md.name());
         md.requires().stream()
           .forEach(builder::requires);
         md.exports().stream()
@@ -62,12 +62,7 @@
           .forEach(builder::uses);
         md.provides().stream()
           .forEach(builder::provides);
-
-        // build the proper concealed packages
-        Set<String> concealed = new HashSet<>(mod.packages());
-        md.exports().stream().map(ModuleDescriptor.Exports::source).forEach(concealed::remove);
-        md.opens().stream().map(ModuleDescriptor.Opens::source).forEach(concealed::remove);
-        concealed.stream().forEach(builder::contains);
+        builder.packages(md.packages());
 
         md.version().ifPresent(builder::version);
         md.mainClass().ifPresent(builder::mainClass);
@@ -124,7 +119,7 @@
             }
         };
 
-        return Configuration.empty().resolveRequires(
+        return Configuration.empty().resolve(
             finder, ModuleFinder.of(), nameToModRef.keySet());
     }
 }
--- a/jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/TaskHelper.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/TaskHelper.java	Wed Jul 05 22:52:01 2017 +0200
@@ -718,13 +718,13 @@
     static Layer createPluginsLayer(List<Path> paths) {
 
         Path[] dirs = paths.toArray(new Path[0]);
-        ModuleFinder finder = new ModulePath(Runtime.version(), true, dirs);
+        ModuleFinder finder = ModulePath.of(Runtime.version(), true, dirs);
         Configuration bootConfiguration = Layer.boot().configuration();
         try {
             Configuration cf = bootConfiguration
-                .resolveRequiresAndUses(ModuleFinder.of(),
-                                        finder,
-                                        Collections.emptySet());
+                .resolveAndBind(ModuleFinder.of(),
+                                finder,
+                                Collections.emptySet());
             ClassLoader scl = ClassLoader.getSystemClassLoader();
             return Layer.boot().defineModulesWithOneLoader(cf, scl);
         } catch (Exception ex) {
--- a/jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/plugins/ExcludeVMPlugin.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/plugins/ExcludeVMPlugin.java	Wed Jul 05 22:52:01 2017 +0200
@@ -95,9 +95,9 @@
 
     /**
      * VM paths:
-     * /java.base/native/{architecture}/{server|client|minimal}/{shared lib}
-     * e.g.: /java.base/native/amd64/server/libjvm.so
-     * /java.base/native/server/libjvm.dylib
+     * /java.base/lib/{architecture}/{server|client|minimal}/{shared lib}
+     * e.g.: /java.base/lib/server/libjvm.so
+     * /java.base/lib/server/libjvm.dylib
      */
     private List<ResourcePoolEntry> getVMs(ResourcePoolModule javaBase, String[] jvmlibs) {
         List<ResourcePoolEntry> ret = javaBase.entries().filter((t) -> {
@@ -198,17 +198,17 @@
             }
             case CLIENT: {
                 target = Jvm.CLIENT;
-                exclude = "/java.base/native**server/**,/java.base/native**minimal/**";
+                exclude = "/java.base/lib**server/**,/java.base/lib**minimal/**";
                 break;
             }
             case SERVER: {
                 target = Jvm.SERVER;
-                exclude = "/java.base/native**client/**,/java.base/native**minimal/**";
+                exclude = "/java.base/lib**client/**,/java.base/lib**minimal/**";
                 break;
             }
             case MINIMAL: {
                 target = Jvm.MINIMAL;
-                exclude = "/java.base/native**server/**,/java.base/native**client/**";
+                exclude = "/java.base/lib**server/**,/java.base/lib**client/**";
                 break;
             }
             default: {
--- a/jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/plugins/SystemModulesPlugin.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/plugins/SystemModulesPlugin.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2017, 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
@@ -46,11 +46,16 @@
 import java.util.function.IntSupplier;
 
 import jdk.internal.module.Checks;
+import jdk.internal.module.ClassFileAttributes;
+import jdk.internal.module.ClassFileConstants;
 import jdk.internal.module.ModuleHashes;
 import jdk.internal.module.ModuleInfo.Attributes;
 import jdk.internal.module.ModuleInfoExtender;
 import jdk.internal.module.ModuleResolution;
 import jdk.internal.module.SystemModules;
+import jdk.internal.org.objectweb.asm.Attribute;
+import jdk.internal.org.objectweb.asm.ClassReader;
+import jdk.internal.org.objectweb.asm.ClassVisitor;
 import jdk.internal.org.objectweb.asm.ClassWriter;
 import jdk.internal.org.objectweb.asm.MethodVisitor;
 import jdk.internal.org.objectweb.asm.Opcodes;
@@ -109,6 +114,11 @@
     }
 
     @Override
+    public String getArgumentsDescription() {
+        return PluginsResourceBundle.getArgument(NAME);
+    }
+
+    @Override
     public void configure(Map<String, String> config) {
         String arg = config.get(NAME);
         if (arg != null) {
@@ -171,10 +181,11 @@
     }
 
     static class ModuleInfo {
+        private final ByteArrayInputStream bain;
         private final Attributes attrs;
         private final Set<String> packages;
-        private final ByteArrayInputStream bain;
         private final boolean dropModuleTarget;
+        private final boolean addModulePackages;
         private ModuleDescriptor descriptor;  // may be different that the original one
 
         ModuleInfo(byte[] bytes, Set<String> packages, boolean dropModuleTarget)
@@ -182,15 +193,21 @@
         {
             this.bain = new ByteArrayInputStream(bytes);
             this.packages = packages;
-
             this.attrs = jdk.internal.module.ModuleInfo.read(bain, null);
+            // If ModulePackages attribute is present, the packages from this
+            // module descriptor returns the packages in that attribute.
+            // If it's not present, ModuleDescriptor::packages only contains
+            // the exported and open packages from module-info.class
             this.descriptor = attrs.descriptor();
             if (descriptor.isAutomatic()) {
                 throw new InternalError("linking automatic module is not supported");
             }
 
+            // add ModulePackages attribute if this module contains some packages
+            // and ModulePackages is not present
+            this.addModulePackages = packages.size() > 0 && !hasModulePackages();
+            // drop target attribute only if any OS property is present
             if (dropModuleTarget) {
-                // drop target attribute only if any OS property is present
                 this.dropModuleTarget =
                     descriptor.osName().isPresent() ||
                     descriptor.osArch().isPresent() ||
@@ -276,53 +293,71 @@
             }
         }
 
+        boolean hasModulePackages() throws IOException {
+            Set<String> attrTypes = new HashSet<>();
+            ClassVisitor cv = new ClassVisitor(Opcodes.ASM5) {
+                @Override
+                public void visitAttribute(Attribute attr) {
+                    attrTypes.add(attr.type);
+                }
+            };
+
+            // prototype of attributes that should be parsed
+            Attribute[] attrs = new Attribute[] {
+                new ClassFileAttributes.ModulePackagesAttribute()
+            };
+
+            try (InputStream in = getInputStream()) {
+                // parse module-info.class
+                ClassReader cr = new ClassReader(in);
+                cr.accept(cv, attrs, 0);
+                return attrTypes.contains(ClassFileConstants.MODULE_PACKAGES);
+            }
+        }
+
         /**
          * Returns true if module-info.class should be written
          * 1. add ModulePackages attribute if not present; or
          * 2. drop ModuleTarget attribute except java.base
          */
         boolean shouldRewrite() {
-            return shouldAddModulePackages() || shouldDropModuleTarget();
-        }
-
-        boolean shouldAddModulePackages() {
-            return (descriptor.packages().isEmpty() && packages.size() > 0);
-        }
-
-        boolean shouldDropModuleTarget() {
-            return dropModuleTarget &&
-                        (descriptor.osName().isPresent() ||
-                         descriptor.osArch().isPresent() ||
-                         descriptor.osVersion().isPresent());
+            return addModulePackages || dropModuleTarget;
         }
 
         /**
          * Returns the bytes for the module-info.class with ModulePackages
-         * if it contains at least one package
+         * attribute added and/or with ModuleTarget attribute dropped.
          */
         byte[] getBytes() throws IOException {
-            bain.reset();
-
-            // add ModulePackages attribute if not exist
-            if (shouldRewrite()) {
-                ModuleInfoRewriter rewriter = new ModuleInfoRewriter(bain);
-                if (shouldAddModulePackages()) {
-                    rewriter.addModulePackages(packages);
+            try (InputStream in = getInputStream()) {
+                if (shouldRewrite()) {
+                    ModuleInfoRewriter rewriter = new ModuleInfoRewriter(in);
+                    if (addModulePackages) {
+                        rewriter.addModulePackages(packages);
+                    }
+                    if (dropModuleTarget) {
+                        rewriter.dropModuleTarget();
+                    }
+                    // rewritten module descriptor
+                    byte[] bytes = rewriter.getBytes();
+                    try (ByteArrayInputStream bain = new ByteArrayInputStream(bytes)) {
+                        this.descriptor = ModuleDescriptor.read(bain);
+                    }
+                    return bytes;
+                } else {
+                    return in.readAllBytes();
                 }
-                if (shouldDropModuleTarget()) {
-                    rewriter.dropModuleTarget();
-                }
-                // rewritten module descriptor
-                byte[] bytes = rewriter.getBytes();
-                try (ByteArrayInputStream bain = new ByteArrayInputStream(bytes)) {
-                     this.descriptor = ModuleDescriptor.read(bain);
-                }
-                return bytes;
-            } else {
-                return bain.readAllBytes();
             }
         }
 
+        /*
+         * Returns the input stream of the module-info.class
+         */
+        InputStream getInputStream() {
+            bain.reset();
+            return bain;
+        }
+
         class ModuleInfoRewriter extends ByteArrayOutputStream {
             final ModuleInfoExtender extender;
             ModuleInfoRewriter(InputStream in) {
@@ -771,9 +806,12 @@
                 if (md.isOpen()) {
                     setModuleBit("open", true);
                 }
-                if (md.isSynthetic()) {
+                if (md.modifiers().contains(ModuleDescriptor.Modifier.SYNTHETIC)) {
                     setModuleBit("synthetic", true);
                 }
+                if (md.modifiers().contains(ModuleDescriptor.Modifier.MANDATED)) {
+                    setModuleBit("mandated", true);
+                }
             }
 
             /*
--- a/jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/resources/plugins.properties	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/resources/plugins.properties	Wed Jul 05 22:52:01 2017 +0200
@@ -62,7 +62,7 @@
 exclude-files.argument=<pattern-list> of files to exclude
 
 exclude-files.description=\
-Specify files to exclude. e.g.: **.java,glob:/java.base/native/client/**
+Specify files to exclude. e.g.: **.java,glob:/java.base/lib/client/**
 
 exclude-resources.argument=<pattern-list> resources to exclude
 
--- a/jdk/src/jdk.jlink/share/classes/jdk/tools/jmod/JmodTask.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.jlink/share/classes/jdk/tools/jmod/JmodTask.java	Wed Jul 05 22:52:01 2017 +0200
@@ -34,6 +34,7 @@
 import java.io.PrintWriter;
 import java.io.UncheckedIOException;
 import java.lang.module.Configuration;
+import java.lang.module.FindException;
 import java.lang.module.ModuleReader;
 import java.lang.module.ModuleReference;
 import java.lang.module.ModuleFinder;
@@ -851,8 +852,8 @@
             // get a resolved module graph
             Configuration config = null;
             try {
-                config = Configuration.empty().resolveRequires(system, finder, roots);
-            } catch (ResolutionException e) {
+                config = Configuration.empty().resolve(system, finder, roots);
+            } catch (FindException | ResolutionException e) {
                 throw new CommandException("err.module.resolution.fail", e.getMessage());
             }
 
@@ -1392,7 +1393,7 @@
                 options.legalNotices = getLastElement(opts.valuesOf(legalNotices));
             if (opts.has(modulePath)) {
                 Path[] dirs = getLastElement(opts.valuesOf(modulePath)).toArray(new Path[0]);
-                options.moduleFinder = new ModulePath(Runtime.version(), true, dirs);
+                options.moduleFinder = ModulePath.of(Runtime.version(), true, dirs);
             }
             if (opts.has(moduleVersion))
                 options.moduleVersion = getLastElement(opts.valuesOf(moduleVersion));
--- a/jdk/src/jdk.security.auth/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.security.auth/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -26,6 +26,8 @@
 /**
  * Contains the implementation of the javax.security.auth.* interfaces and
  * various authentication modules.
+ *
+ * @since 9
  */
 module jdk.security.auth {
     requires transitive java.naming;
--- a/jdk/src/jdk.security.jgss/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/src/jdk.security.jgss/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -26,6 +26,8 @@
 /**
  * Defines Java extensions to the GSS-API and an implementation of the SASL
  * GSSAPI mechanism.
+ *
+ * @since 9
  */
 module jdk.security.jgss {
     requires transitive java.security.jgss;
--- a/jdk/test/ProblemList.txt	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/ProblemList.txt	Wed Jul 05 22:52:01 2017 +0200
@@ -251,12 +251,11 @@
 
 tools/pack200/CommandLineTests.java                             8059906 generic-all
 
-tools/launcher/ArgsEnvVar.java					8173712 generic-all
 tools/launcher/FXLauncherTest.java                              8068049 linux-all,macosx-all
 
-tools/jimage/JImageExtractTest.java                             8169713 generic-all
-tools/jimage/JImageListTest.java                                8169713 generic-all
-tools/jimage/JImageVerifyTest.java                              8169713 generic-all
+tools/jimage/JImageExtractTest.java                             8170120 generic-all
+tools/jimage/JImageListTest.java                                8170120 generic-all
+tools/jimage/JImageVerifyTest.java                              8170120 generic-all
 
 
 tools/jlink/multireleasejar/JLinkMultiReleaseJarTest.java       8169971 windows-x64
@@ -267,7 +266,7 @@
 
 com/sun/jdi/RedefineImplementor.sh                              8004127 generic-all
 
-com/sun/jdi/JdbMethodExitTest.sh                                6902121 generic-all
+com/sun/jdi/JdbMethodExitTest.sh                                8171483 generic-all
 
 com/sun/jdi/RepStep.java                                        8043571 generic-all
 
@@ -296,6 +295,8 @@
 
 sun/tools/jcmd/TestJcmdSanity.java                              8031482 windows-all
 
+sun/tools/jstat/jstatClassloadOutput1.sh                        8173942 generic-all
+
 sun/jvmstat/monitor/MonitoredVm/MonitorVmStartTerminate.java    8057732 generic-all
 
 demo/jvmti/compiledMethodLoad/CompiledMethodLoadTest.java       8151899 generic-all
@@ -308,6 +309,6 @@
 
 javax/rmi/PortableRemoteObject/8146975/RmiIiopReturnValueTest.java 8169737 linux-all
 
-javax/xml/ws/clientjar/TestWsImport.java			8170370 generic-all
+javax/xml/ws/clientjar/TestWsImport.java			8173317 generic-all
 
 ############################################################################
--- a/jdk/test/TEST.groups	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/TEST.groups	Wed Jul 05 22:52:01 2017 +0200
@@ -273,6 +273,7 @@
     jdk/internal/jline \
     com/sun/jndi \
     com/sun/corba \
+    org/omg/CORBA \
     lib/testlibrary \
     sample
 
--- a/jdk/test/com/oracle/security/ucrypto/TestAES.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/com/oracle/security/ucrypto/TestAES.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2014, 2017, 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
@@ -23,7 +23,7 @@
 
 /*
  * @test
- * @bug 7088989 8014374 8167512
+ * @bug 7088989 8014374 8167512 8173708
  * @summary Ensure the AES ciphers of OracleUcrypto provider works correctly
  * @key randomness
  * @run main TestAES
@@ -177,6 +177,12 @@
                     k += c.doFinal(eout, firstPartLen+1, eout.length - firstPartLen - 1, dout, k);
                     if (!checkArrays(in, in.length, dout, k)) testPassed = false;
                 } catch(Exception ex) {
+                    if (ex instanceof BadPaddingException &&
+                            algos[i].indexOf("CFB128") != -1 &&
+                            p.getName().equals("OracleUcrypto")) {
+                        System.out.println("Ignore due to a pre-S11.3 bug: " + ex);
+                        continue;
+                    }
                     System.out.println("Unexpected Exception: " + algos[i]);
                     ex.printStackTrace();
                     testPassed = false;
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/com/sun/java/swing/plaf/windows/Test8173145.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,123 @@
+/*
+ * Copyright (c) 2017, 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
+   @bug 8173145
+   @summary Menu is activated after using mnemonic Alt/Key combination
+   @modules java.desktop/com.sun.java.swing.plaf.windows
+   @run main Test8173145
+*/
+
+import java.awt.*;
+import java.awt.event.KeyEvent;
+import java.lang.reflect.InvocationTargetException;
+
+import javax.swing.*;
+
+public class Test8173145 {
+
+    private volatile static JButton btn;
+    private volatile static boolean uiCreated;
+
+    public static void main(String[] args) throws InvocationTargetException, InterruptedException, AWTException {
+        SwingUtilities.invokeAndWait(new Runnable() {
+            @Override
+            public void run() {
+                try {
+                    uiCreated = createGUI();
+                } catch (Exception e) {
+                    e.printStackTrace();
+                }
+            }
+        });
+
+        if (uiCreated) {
+            test();
+        } else {
+            //no windows l&f, skip the test
+        }
+    }
+
+    private static void test() {
+        final Robot robot;
+        try {
+            robot = new Robot();
+        } catch (AWTException e) {
+            throw new RuntimeException(e);
+        }
+        robot.setAutoDelay(100);
+        robot.waitForIdle();
+
+        robot.keyPress(KeyEvent.VK_ALT);
+        robot.keyPress(KeyEvent.VK_M);
+        robot.keyRelease(KeyEvent.VK_M);
+        robot.keyRelease(KeyEvent.VK_ALT);
+
+        Component focusOwner = KeyboardFocusManager.getCurrentKeyboardFocusManager().getFocusOwner();
+
+        if (focusOwner != btn) {
+            throw new RuntimeException("Wrong focus owner");
+        }
+    }
+
+    private static boolean createGUI() {
+        try {
+            UIManager.setLookAndFeel("com.sun.java.swing.plaf.windows.WindowsLookAndFeel");
+        } catch (Exception e) {
+            return false;
+        }
+        JFrame f = new JFrame();
+
+        JPanel panel = new JPanel();
+        btn = new JButton("Mmmmm");
+        btn.setMnemonic(KeyEvent.VK_M);
+        btn.setDisplayedMnemonicIndex(0);
+        panel.add(btn);
+
+        JTextField tf = new JTextField();
+        tf.setColumns(10);
+        panel.add(tf);
+
+        f.setJMenuBar(getMenuBar());
+        f.add(panel);
+        f.pack();
+        f.setVisible(true);
+        tf.requestFocus();
+        return true;
+    }
+
+    static JMenuBar getMenuBar() {
+        JMenuBar menuBar;
+        JMenu menu;
+
+        menuBar = new JMenuBar();
+
+        menu = new JMenu("Menu");
+        menuBar.add(menu);
+
+        JMenuItem mi = new JMenuItem("test");
+        menu.add(mi);
+
+        return menuBar;
+    }
+}
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/OpaqueOverlapping.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/OpaqueOverlapping.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2014, 2017, 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
@@ -22,7 +22,6 @@
  */
 
 
-import com.sun.awt.AWTUtilities;
 import java.awt.Frame;
 import java.awt.Panel;
 import java.awt.Point;
@@ -44,11 +43,10 @@
 /*
  * @test
  * @key headful
- * @bug 6776743
+ * @bug 6776743 8173409
  * @summary Opaque overlapping test for each AWT component
  * @library /java/awt/patchlib  ../../regtesthelpers
- * @modules java.desktop/com.sun.awt
- *          java.desktop/java.awt.peer
+ * @modules java.desktop/java.awt.peer
  *          java.desktop/sun.awt
  * @build java.desktop/java.awt.Helper
  * @build Util
@@ -134,12 +132,10 @@
         // flag value.
         for (int i = 0; i < 9; ++i) {
             if (i == 3) {
-                AWTUtilities.setComponentMixingCutoutShape(light,
-                        new Rectangle());
+                light.setMixingCutoutShape(new Rectangle());
             }
             if (i == 6) {
-                AWTUtilities.setComponentMixingCutoutShape(light,
-                        null);
+                light.setMixingCutoutShape(null);
             }
 
             robot.mousePress(InputEvent.BUTTON1_MASK);
--- a/jdk/test/java/awt/Mixing/OpaqueTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/awt/Mixing/OpaqueTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -24,11 +24,10 @@
 /*
   @test
   @key headful
-  @bug 4811096
+  @bug 4811096 8173409
   @summary Tests whether opaque and non-opaque components mix correctly
   @author anthony.petrov@...: area=awt.mixing
   @library ../regtesthelpers
-  @modules java.desktop/com.sun.awt
   @build Util
   @run main OpaqueTest
 */
@@ -44,7 +43,6 @@
 import java.awt.event.*;
 import javax.swing.*;
 import test.java.awt.regtesthelpers.Util;
-import com.sun.awt.AWTUtilities;
 
 
 
@@ -125,12 +123,10 @@
         // flag value.
         for (int i = 0; i < 9; ++i) {
             if (i == 3) {
-                AWTUtilities.setComponentMixingCutoutShape(light,
-                        new Rectangle());
+                light.setMixingCutoutShape(new Rectangle());
             }
             if (i == 6) {
-                AWTUtilities.setComponentMixingCutoutShape(light,
-                        null);
+                light.setMixingCutoutShape(null);
             }
 
             robot.mousePress(InputEvent.BUTTON1_MASK);
--- a/jdk/test/java/awt/jdk/TestJDKAWTUtils.java	Mon Feb 13 11:57:56 2017 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,59 +0,0 @@
-/*
- * Copyright (c) 2016, 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.
- */
-
-/*
- * @test
- * @bug 8167126
- */
-import java.awt.BorderLayout;
-import java.awt.Font;
-import java.awt.Rectangle;
-import javax.swing.JButton;
-import javax.swing.JFrame;
-import javax.swing.JPanel;
-import javax.swing.SwingUtilities;
-
-public class TestJDKAWTUtils {
-
-    static JFrame f;
-    public static void main(String[] args) throws Exception {
-
-        SwingUtilities.invokeAndWait(() -> {
-            f = new JFrame("test");
-            JPanel p = new JPanel();
-            JButton b = new JButton("Hello");
-            b.setFont(new Font(Font.DIALOG, Font.PLAIN, 80));
-            p.setLayout(new BorderLayout());
-            p.add("Center", b);
-            f.getContentPane().add(p);
-            f.pack();
-            f.setVisible(true);
-            Rectangle r = new Rectangle(0, 0, 50, 50);
-            jdk.awt.AWTUtils.setComponentMixingCutoutShape(b, r);
-        });
-        Thread.sleep(2000);
-        SwingUtilities.invokeAndWait(() -> f.dispose());
-    }
-}
--- a/jdk/test/java/awt/print/PrinterJob/PrintAttributeUpdateTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/awt/print/PrinterJob/PrintAttributeUpdateTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -23,7 +23,7 @@
 
  /*
   @test
-  @bug 8042713
+  @bug 8042713 8170578
   @summary  Print Dialog does not update attribute set with page range
   @run main/manual PrintAttributeUpdateTest
  */
--- a/jdk/test/java/io/FilePermission/ReadFileOnPath.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/io/FilePermission/ReadFileOnPath.java	Wed Jul 05 22:52:01 2017 +0200
@@ -57,7 +57,7 @@
                 "module-info.class", "base", "p/App.class", "p/child");
 
         // exploded module
-        test("--module-path", "modules", "-m", "m/p.App", "SS+++++");
+        test("--module-path", "modules", "-m", "m/p.App", "SS++++0");
 
         // module in jar
         test("--module-path", "new.jar", "-m", "m/p.App", "SSSS++0");
--- a/jdk/test/java/lang/Class/forName/modules/TestLayer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/Class/forName/modules/TestLayer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -46,9 +46,9 @@
         ModuleFinder finder = ModuleFinder.of(MODS_DIR);
 
         Configuration parent = Layer.boot().configuration();
-        Configuration cf = parent.resolveRequiresAndUses(ModuleFinder.of(),
-                                                         finder,
-                                                         modules);
+        Configuration cf = parent.resolveAndBind(ModuleFinder.of(),
+                                                 finder,
+                                                 modules);
 
         ClassLoader scl = ClassLoader.getSystemClassLoader();
         Layer layer = Layer.boot().defineModulesWithManyLoaders(cf, scl);
--- a/jdk/test/java/lang/Class/forName/modules/src/m3/p3/NoAccess.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/Class/forName/modules/src/m3/p3/NoAccess.java	Wed Jul 05 22:52:01 2017 +0200
@@ -50,9 +50,9 @@
         Layer bootLayer = Layer.boot();
         Configuration parent = bootLayer.configuration();
 
-        Configuration cf = parent.resolveRequiresAndUses(finder,
-                                                         ModuleFinder.of(),
-                                                         Set.of("m1", "m2"));
+        Configuration cf = parent.resolveAndBind(finder,
+                                                 ModuleFinder.of(),
+                                                 Set.of("m1", "m2"));
 
         ClassLoader scl = ClassLoader.getSystemClassLoader();
         Layer layer = bootLayer.defineModulesWithManyLoaders(cf, scl);
--- a/jdk/test/java/lang/Class/getPackageName/Basic.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/Class/getPackageName/Basic.java	Wed Jul 05 22:52:01 2017 +0200
@@ -154,8 +154,8 @@
         return new Object[][] {
 
             { Basic.class,                  TEST_PACKAGE },
-            { Basic[].class,                null },
-            { Basic[][].class,              null },
+            { Basic[].class,                TEST_PACKAGE },
+            { Basic[][].class,              TEST_PACKAGE },
 
             { getNestedClass1(),            TEST_PACKAGE },
             { getNestedClass2(),            TEST_PACKAGE },
@@ -174,14 +174,14 @@
             { getAnonymousClass6(),         TEST_PACKAGE },
 
             { Object.class,                 "java.lang" },
-            { Object[].class,               null },
-            { Object[][].class,             null },
+            { Object[].class,               "java.lang" },
+            { Object[][].class,             "java.lang" },
 
-            { int.class,                    null },
-            { int[].class,                  null },
-            { int[][].class,                null },
+            { int.class,                    "java.lang" },
+            { int[].class,                  "java.lang" },
+            { int[][].class,                "java.lang" },
 
-            { void.class,                   null },
+            { void.class,                   "java.lang" },
 
         };
     }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/ClassLoader/securityManager/ClassLoaderTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,297 @@
+/*
+ * Copyright (c) 2017, 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
+ * @bug 8168423
+ * @summary Different types of ClassLoader running with(out) SecurityManager and
+ *          (in)valid security policy file.
+ * @library /lib/testlibrary
+ * @modules java.base/jdk.internal.module
+ * @build JarUtils CompilerUtils
+ * @run main/timeout=240 ClassLoaderTest
+ */
+import java.io.File;
+import java.io.OutputStream;
+import java.nio.file.Files;
+import java.nio.file.Path;
+import java.nio.file.Paths;
+import java.nio.file.StandardCopyOption;
+import java.util.Map;
+import java.util.HashMap;
+import java.lang.module.ModuleDescriptor;
+import jdk.internal.module.ModuleInfoWriter;
+import jdk.testlibrary.ProcessTools;
+
+public class ClassLoaderTest {
+
+    private static final String SRC = System.getProperty("test.src");
+    private static final Path CL_SRC = Paths.get(SRC, "TestClassLoader.java");
+    private static final Path C_SRC = Paths.get(SRC, "TestClient.java");
+    private static final Path CL_BIN = Paths.get("classes", "clbin");
+    private static final Path C_BIN = Paths.get("classes", "cbin");
+    private static final Path ARTIFACT_DIR = Paths.get("jars");
+    private static final Path VALID_POLICY = Paths.get(SRC, "valid.policy");
+    private static final Path INVALID_POLICY
+            = Paths.get(SRC, "malformed.policy");
+    private static final Path NO_POLICY = null;
+    private static final String LOCALE = "-Duser.language=en -Duser.region=US";
+    /*
+     * Here is the naming convention followed for each jar.
+     * cl.jar   - Regular custom class loader jar.
+     * mcl.jar  - Modular custom class loader jar.
+     * c.jar    - Regular client jar.
+     * mc.jar   - Modular client jar.
+     * amc.jar  - Modular client referring automated custom class loader jar.
+     */
+    private static final Path CL_JAR = ARTIFACT_DIR.resolve("cl.jar");
+    private static final Path MCL_JAR = ARTIFACT_DIR.resolve("mcl.jar");
+    private static final Path C_JAR = ARTIFACT_DIR.resolve("c.jar");
+    private static final Path MC_JAR = ARTIFACT_DIR.resolve("mc.jar");
+    private static final Path AMC_JAR = ARTIFACT_DIR.resolve("amc.jar");
+    private static final Map<String, String> MSG_MAP = new HashMap<>();
+
+    static {
+        // This mapping help process finding expected message based
+        // on the key passed as argument while executing java command.
+        MSG_MAP.put("MissingModule", "Module cl not found, required by mc");
+        MSG_MAP.put("ErrorPolicy", "java.security.policy: error parsing file");
+        MSG_MAP.put(
+                "SystemCL", "jdk.internal.loader.ClassLoaders$AppClassLoader");
+        MSG_MAP.put("CustomCL", "cl.TestClassLoader");
+    }
+
+    public static void main(String[] args) throws Exception {
+
+        // Generates regular and modular jars before start processing it.
+        setUp();
+        processForEachPolicyFile();
+    }
+
+    /**
+     * Test cases are based on the following logic,
+     *  for (policyFile : {"NO_POLICY", "VALID", "MALFORMED"}) {
+     *      for (classLoader : {"SystemClassLoader", "CustomClassLoader"}){
+     *          for (clientModule : {"NAMED", "AUTOMATIC", "UNNAMED"}) {
+     *              for (classLoaderModule : {"NAMED", "AUTOMATIC", "UNNAMED"}) {
+     *                  Create and run java command for each possible Test case
+     *              }
+     *          }
+     *      }
+     *  }
+     */
+    private static void processForEachPolicyFile() throws Exception {
+
+        final String regCLloc = CL_JAR.toFile().getAbsolutePath();
+        final String modCLloc = MCL_JAR.toFile().getAbsolutePath();
+        final String regCloc = C_JAR.toFile().getAbsolutePath();
+        final String modCloc = MC_JAR.toFile().getAbsolutePath();
+        final String autoModCloc = AMC_JAR.toFile().getAbsolutePath();
+        final String separator = File.pathSeparator;
+
+        for (Path policy
+                : new Path[]{NO_POLICY, VALID_POLICY, INVALID_POLICY}) {
+            final String policyFile = (policy != null)
+                    ? policy.toFile().getAbsolutePath() : null;
+            final boolean malformedPolicy
+                    = (policy == null) ? false : policy.equals(INVALID_POLICY);
+
+            for (boolean useSCL : new boolean[]{true, false}) {
+                final String clVmArg = (useSCL) ? ""
+                        : "-Djava.system.class.loader=cl.TestClassLoader";
+                final String autoAddModArg
+                        = (useSCL) ? "" : "--add-modules=cl";
+                final String addmodArg = (useSCL) ? "" : "--add-modules=mcl";
+                final String sMArg = (policy != null) ? String.format(
+                        "-Djava.security.manager -Djava.security.policy=%s",
+                        policyFile) : "";
+                final String smMsg = (policy != null) ? "With SecurityManager"
+                        : "Without SecurityManager";
+                final String expectedResult = ((!malformedPolicy)
+                        ? ((useSCL) ? "PASS SystemCL" : "PASS CustomCL")
+                        : "FAIL ErrorPolicy");
+
+                // NAMED-NAMED, NAMED-AUTOMATIC, NAMED-UNNAMED
+                System.out.printf("Case:- Modular Client and %s %s%n",
+                        ((useSCL) ? "SystemClassLoader"
+                                : "Modular CustomClassLoader"), smMsg);
+                execute(new String[]{String.format(
+                    "--module-path %s%s%s %s %s %s -m mc/c.TestClient",
+                    modCloc, separator, modCLloc, LOCALE, clVmArg, sMArg),
+                    expectedResult});
+                System.out.printf("Case:- Modular Client and %s %s%n", ((useSCL)
+                        ? "SystemClassLoader"
+                        : "Automatic modular CustomClassLoader"), smMsg);
+                execute(new String[]{String.format(
+                    "--module-path %s%s%s %s %s %s -m mc/c.TestClient",
+                    autoModCloc, separator, regCLloc, LOCALE, clVmArg, sMArg),
+                    expectedResult});
+                System.out.printf("Case:- Modular Client and %s %s%n", ((useSCL)
+                        ? "SystemClassLoader"
+                        : "Unknown modular CustomClassLoader"), smMsg);
+                execute(new String[]{String.format(
+                    "--module-path %s -cp %s %s %s %s -m mc/c.TestClient",
+                    autoModCloc, regCLloc, LOCALE, clVmArg, sMArg),
+                    "FAIL MissingModule"});
+
+                // AUTOMATIC-NAMED, AUTOMATIC-AUTOMATIC, AUTOMATIC-UNNAMED
+                System.out.printf("Case:- Automated modular Client and %s %s%n",
+                        ((useSCL) ? "SystemClassLoader"
+                                : "Modular CustomClassLoader"), smMsg);
+                execute(new String[]{String.format(
+                    "--module-path %s%s%s %s %s %s %s -m c/c.TestClient",
+                    regCloc, separator, modCLloc, addmodArg, LOCALE, clVmArg,
+                    sMArg), expectedResult});
+                System.out.printf("Case:- Automated modular Client and %s %s%n",
+                        ((useSCL) ? "SystemClassLoader"
+                                : "Automatic modular CustomClassLoader"),
+                        smMsg);
+                execute(new String[]{String.format(
+                    "--module-path %s%s%s %s %s %s %s -m c/c.TestClient",
+                    regCloc, separator, regCLloc, autoAddModArg, LOCALE,
+                    clVmArg, sMArg), expectedResult});
+                System.out.printf("Case:- Automated modular Client and %s %s%n",
+                        ((useSCL) ? "SystemClassLoader"
+                                : "Unknown modular CustomClassLoader"), smMsg);
+                execute(new String[]{String.format(
+                    "--module-path %s -cp %s %s %s %s -m c/c.TestClient",
+                    regCloc, regCLloc, LOCALE, clVmArg, sMArg),
+                    expectedResult});
+
+                // UNNAMED-NAMED, UNNAMED-AUTOMATIC, UNNAMED-UNNAMED
+                System.out.printf("Case:- Unknown modular Client and %s %s%n",
+                        ((useSCL) ? "SystemClassLoader"
+                                : "Modular CustomClassLoader"), smMsg);
+                execute(new String[]{String.format(
+                    "-cp %s --module-path %s %s %s %s %s c.TestClient",
+                    regCloc, modCLloc, addmodArg, LOCALE, clVmArg, sMArg),
+                    expectedResult});
+                System.out.printf("Case:- Unknown modular Client and %s %s%n",
+                        ((useSCL) ? "SystemClassLoader"
+                                : "Automatic modular CustomClassLoader"),
+                        smMsg);
+                execute(new String[]{String.format(
+                    "-cp %s --module-path %s %s %s %s %s c.TestClient",
+                    regCloc, regCLloc, autoAddModArg, LOCALE, clVmArg, sMArg),
+                    expectedResult});
+                System.out.printf("Case:- Unknown modular Client and %s %s%n",
+                        ((useSCL) ? "SystemClassLoader"
+                                : "Unknown modular CustomClassLoader"), smMsg);
+                execute(new String[]{String.format(
+                    "-cp %s%s%s %s %s %s c.TestClient", regCloc, separator,
+                    regCLloc, LOCALE, clVmArg, sMArg), expectedResult});
+
+                // Regular jars in module-path and Modular jars in class-path.
+                System.out.printf("Case:- Regular Client and %s "
+                        + "inside --module-path %s.%n", ((useSCL)
+                                ? "SystemClassLoader"
+                                : "Unknown modular CustomClassLoader"), smMsg);
+                execute(new String[]{String.format(
+                    "--module-path %s%s%s %s %s %s %s -m c/c.TestClient",
+                    regCloc, separator, regCLloc, autoAddModArg, LOCALE,
+                    clVmArg, sMArg), expectedResult});
+                System.out.printf("Case:- Modular Client and %s in -cp %s%n",
+                        ((useSCL) ? "SystemClassLoader"
+                                : "Modular CustomClassLoader"), smMsg);
+                execute(new String[]{String.format(
+                    "-cp %s%s%s %s %s %s c.TestClient", modCloc, separator,
+                    modCLloc, LOCALE, clVmArg, sMArg), expectedResult});
+            }
+        }
+    }
+
+    /**
+     * Execute with command arguments and process the result.
+     */
+    private static void execute(String[] args) throws Exception {
+
+        String status = null;
+        String msgKey = null;
+        if ((args != null && args.length > 1)) {
+            String[] secArgs = args[1].split("\\s+");
+            status = (secArgs.length > 0) ? secArgs[0] : null;
+            msgKey = (secArgs.length > 1) ? secArgs[1] : null;
+        }
+        String out = ProcessTools.executeTestJvm(args[0].split("\\s+"))
+                .getOutput();
+        // Handle response.
+        if ((status != null && "PASS".equals(status) && msgKey != null
+                && out.contains(MSG_MAP.get(msgKey)))) {
+            System.out.printf("PASS: Expected Result: %s.%n",
+                    MSG_MAP.get(msgKey));
+        } else if ((status != null && "FAIL".equals(status) && msgKey != null
+                && out.contains(MSG_MAP.get(msgKey)))) {
+            System.out.printf("PASS: Expected Failure: %s.%n",
+                    MSG_MAP.get(msgKey));
+        } else if (out.contains("Exception") || out.contains("Error")) {
+            System.out.printf("OUTPUT: %s", out);
+            throw new RuntimeException("FAIL: Unknown Exception.");
+        } else {
+            System.out.printf("OUTPUT: %s", out);
+            throw new RuntimeException("FAIL: Unknown Test case found");
+        }
+    }
+
+    /**
+     * Creates regular/modular jar files for TestClient and TestClassLoader.
+     */
+    private static void setUp() throws Exception {
+
+        boolean compiled = CompilerUtils.compile(CL_SRC, CL_BIN);
+        compiled &= CompilerUtils.compile(C_SRC, C_BIN);
+        if (!compiled) {
+            throw new RuntimeException("Test Setup failed.");
+        }
+        // Generate regular jar files for TestClient and TestClassLoader
+        JarUtils.createJarFile(CL_JAR, CL_BIN);
+        JarUtils.createJarFile(C_JAR, C_BIN);
+        // Generate modular jar files for TestClient and TestClassLoader with
+        // their corresponding ModuleDescriptor.
+        Files.copy(CL_JAR, MCL_JAR, StandardCopyOption.REPLACE_EXISTING);
+        updateModuleDescr(MCL_JAR, ModuleDescriptor.newModule("mcl")
+                .exports("cl").requires("java.base").build());
+        Files.copy(C_JAR, MC_JAR, StandardCopyOption.REPLACE_EXISTING);
+        updateModuleDescr(MC_JAR, ModuleDescriptor.newModule("mc")
+                .exports("c").requires("java.base").requires("mcl").build());
+        Files.copy(C_JAR, AMC_JAR, StandardCopyOption.REPLACE_EXISTING);
+        updateModuleDescr(AMC_JAR, ModuleDescriptor.newModule("mc")
+                .exports("c").requires("java.base").requires("cl").build());
+    }
+
+    /**
+     * Update regular jars and include module-info.class inside it to make
+     * modular jars.
+     */
+    private static void updateModuleDescr(Path jar, ModuleDescriptor mDescr)
+            throws Exception {
+        if (mDescr != null) {
+            Path dir = Files.createTempDirectory("tmp");
+            Path mi = dir.resolve("module-info.class");
+            try (OutputStream out = Files.newOutputStream(mi)) {
+                ModuleInfoWriter.write(mDescr, out);
+            }
+            System.out.format("Adding 'module-info.class' to jar '%s'%n", jar);
+            JarUtils.updateJarFile(jar, dir);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/ClassLoader/securityManager/TestClassLoader.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,34 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+package cl;
+
+public class TestClassLoader extends ClassLoader {
+
+    /**
+     * This constructor is used to set the parent ClassLoader
+     */
+    public TestClassLoader(ClassLoader parent) {
+        super(parent);
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/ClassLoader/securityManager/TestClient.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,34 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+package c;
+
+public class TestClient {
+
+    public static void main(String[] args) {
+
+        // Initialize policy file.
+        System.getProperty("test.src");
+        System.out.printf("ContextClassLoader: %s%n",
+                Thread.currentThread().getContextClassLoader().toString());
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/ClassLoader/securityManager/malformed.policy	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,4 @@
+grant {
+    xyz;
+    permission java.util.PropertyPermission "test.src", "read";
+}
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/ClassLoader/securityManager/valid.policy	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,4 @@
+grant codeBase "file:./jars/*" {
+    permission java.lang.RuntimePermission "createClassLoader";
+    permission java.util.PropertyPermission "test.src", "read";
+};
\ No newline at end of file
--- a/jdk/test/java/lang/SecurityManager/CheckPackageAccess.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/SecurityManager/CheckPackageAccess.java	Wed Jul 05 22:52:01 2017 +0200
@@ -33,6 +33,7 @@
 
 import java.lang.module.ModuleFinder;
 import java.lang.module.ModuleReference;
+import java.lang.reflect.Layer;
 import java.util.Arrays;
 import java.util.List;
 import java.util.Optional;
@@ -80,25 +81,33 @@
         }
 
         void test() {
-            System.out.println("Testing module " + moduleName);
+            final boolean isModulePresent =
+                        Layer.boot().findModule(moduleName).isPresent();
+            System.out.format("Testing module: %1$s. Module is%2$s present.\n",
+                        moduleName, isModulePresent ? "" : " NOT");
 
-            // access to exported pkg should pass
-            testNonRestricted(exports);
+            if (isModulePresent) {
 
-            // access to opened pkg should pass
-            opens.ifPresent(Test::testNonRestricted);
+                // access to exported pkg should pass
+                testNonRestricted(exports);
+
+                // access to opened pkg should pass
+                opens.ifPresent(Test::testNonRestricted);
 
-            // access to concealed pkg should fail
-            testRestricted(conceals);
+                // access to concealed pkg should fail
+                testRestricted(conceals);
 
-            // access to qualified export pkg should fail
-            qualExports.ifPresent(Test::testRestricted);
+                // access to qualified export pkg should fail
+                qualExports.ifPresent(Test::testRestricted);
 
-            // access to qualified open pkg should fail
-            qualOpens.ifPresent(Test::testRestricted);
+                // access to qualified open pkg should fail
+                qualOpens.ifPresent(Test::testRestricted);
 
-            // access to qualified opened pkg that is also exported should pass
-            qualOpensAndExports.ifPresent(Test::testNonRestricted);
+                // access to qualified opened pkg that is also exported should pass
+                qualOpensAndExports.ifPresent(Test::testNonRestricted);
+            } else {
+                System.out.println("Skipping tests for module.");
+            }
         }
 
         private static void testRestricted(String pkg) {
--- a/jdk/test/java/lang/StackTraceElement/WithClassLoaderName.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/StackTraceElement/WithClassLoaderName.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -26,6 +26,7 @@
  * @bug 6479237
  * @summary Basic test StackTraceElement with class loader names
  * @library lib /lib/testlibrary
+ * @modules jdk.compiler
  * @build m1/* WithClassLoaderName
  * @run main/othervm m1/com.app.Main
  * @run main/othervm WithClassLoaderName
--- a/jdk/test/java/lang/StackWalker/Basic.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/StackWalker/Basic.java	Wed Jul 05 22:52:01 2017 +0200
@@ -23,18 +23,21 @@
 
 /*
  * @test
- * @bug 8140450
+ * @bug 8140450 8173898
  * @summary Basic test for the StackWalker::walk method
  * @run testng Basic
  */
 
 import java.lang.StackWalker.StackFrame;
 import java.util.List;
+import java.util.Objects;
 import java.util.stream.Collectors;
+import java.util.stream.Stream;
 import static java.lang.StackWalker.Option.*;
 
 import org.testng.annotations.DataProvider;
 import org.testng.annotations.Test;
+import static org.testng.Assert.*;
 
 public class Basic {
     private static boolean verbose = false;
@@ -60,6 +63,17 @@
         }
     }
 
+    @Test
+    public static void testWalkFromConstructor() throws Exception {
+        System.out.println("testWalkFromConstructor:");
+        List<String> found = ((ConstructorNewInstance)ConstructorNewInstance.class.getMethod("create")
+                             .invoke(null)).collectedFrames();
+        assertEquals(List.of(ConstructorNewInstance.class.getName()+"::<init>",
+                             ConstructorNewInstance.class.getName()+"::create",
+                             Basic.class.getName()+"::testWalkFromConstructor"),
+                     found);
+    }
+
     private final int depth;
     Basic(int depth) {
         this.depth = depth;
@@ -77,6 +91,47 @@
         assertEquals(limit, frames.size());
     }
 
+    static class ConstructorNewInstance {
+        static final StackWalker walker =
+            StackWalker.getInstance(StackWalker.Option.RETAIN_CLASS_REFERENCE);
+        List<String> testFramesOrReflectionFrames;
+        public ConstructorNewInstance() {
+            testFramesOrReflectionFrames = walker.walk(this::parse);
+        }
+        public List<String> collectedFrames() {
+            return testFramesOrReflectionFrames;
+        }
+        public boolean accept(StackFrame f) {
+            // Frames whose class names don't contain "."
+            // are our own test frames. These are the ones
+            // we expect.
+            // Frames whose class names contain ".reflect."
+            // are reflection frames. None should be present,
+            // since they are supposed to be filtered by
+            // by StackWalker. If we find any, we want to fail.
+            if (!f.getClassName().contains(".")
+                || f.getClassName().contains(".reflect.")) {
+                System.out.println("    " + f);
+                return true;
+            }
+            // Filter out all other frames (in particular
+            // those from the test framework) in order to
+            // have predictable results.
+            return false;
+        }
+        public String frame(StackFrame f) {
+            return f.getClassName() + "::" + f.getMethodName();
+        }
+        List<String> parse(Stream<StackFrame> s) {
+            return s.filter(this::accept)
+                    .map(this::frame)
+                    .collect(Collectors.toList());
+        }
+        public static ConstructorNewInstance create() throws Exception {
+            return ConstructorNewInstance.class.getConstructor().newInstance();
+        }
+    }
+
     class StackBuilder {
         private final int stackDepth;
         private final int limit;
@@ -131,9 +186,4 @@
         }
     }
 
-    static void assertEquals(int x, int y) {
-        if (x != y) {
-            throw new RuntimeException(x + " != " + y);
-        }
-    }
 }
--- a/jdk/test/java/lang/StackWalker/CallerFromMain.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/StackWalker/CallerFromMain.java	Wed Jul 05 22:52:01 2017 +0200
@@ -51,7 +51,7 @@
         try {
             Class<?> c = sw.getCallerClass();
             throw new RuntimeException("UOE not thrown. Caller: " + c);
-        } catch (IllegalStateException e) {}
+        } catch (IllegalCallerException e) {}
 
         // StackWalker::getCallerClass
         // Runnable::run
--- a/jdk/test/java/lang/StackWalker/CountLocalSlots.java	Mon Feb 13 11:57:56 2017 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,62 +0,0 @@
-/*
- * Copyright (c) 2016, 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
- * @bug 8147039
- * @summary Confirm locals[] always has expected length, even for "dead" locals
- * @modules java.base/java.lang:open
- * @compile LocalsAndOperands.java
- * @run testng/othervm -Xcomp CountLocalSlots
- */
-
-import org.testng.annotations.Test;
-import java.lang.StackWalker.StackFrame;
-
-public class CountLocalSlots {
-    final static boolean debug = true;
-
-    @Test(dataProvider = "provider", dataProviderClass = LocalsAndOperands.class)
-    public void countLocalSlots(StackFrame... frames) {
-        for (StackFrame frame : frames) {
-            if (debug) {
-                System.out.println("Running countLocalSlots");
-                LocalsAndOperands.dumpStackWithLocals(frames);
-            }
-            // Confirm expected number of locals
-            String methodName = frame.getMethodName();
-            Integer expectedObj = (Integer) LocalsAndOperands.Tester.NUM_LOCALS.get(methodName);
-            if (expectedObj == null) {
-                if (!debug) { LocalsAndOperands.dumpStackWithLocals(frames); }
-                throw new RuntimeException("No NUM_LOCALS entry for " +
-                        methodName + "().  Update test?");
-            }
-            Object[] locals = (Object[]) LocalsAndOperands.invokeGetLocals(frame);
-            if (locals.length != expectedObj) {
-                if (!debug) { LocalsAndOperands.dumpStackWithLocals(frames); }
-                throw new RuntimeException(methodName + "(): number of locals (" +
-                        locals.length + ") did not match expected (" + expectedObj + ")");
-            }
-        }
-    }
-}
--- a/jdk/test/java/lang/StackWalker/LocalsAndOperands.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/StackWalker/LocalsAndOperands.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2017, 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
@@ -23,33 +23,54 @@
 
 /*
  * @test
- * @bug 8020968 8147039
+ * @bug 8020968 8147039 8156073
  * @summary Tests for locals and operands
  * @modules java.base/java.lang:open
- * @run testng LocalsAndOperands
+ * @run testng/othervm -Xint -DtestUnused=true LocalsAndOperands
+ * @run testng/othervm -Xcomp LocalsAndOperands
+ * @run testng/othervm -Xcomp -XX:-TieredCompilation LocalsAndOperands
  */
 
 import org.testng.annotations.*;
+import static org.testng.Assert.*;
 import java.lang.StackWalker.StackFrame;
+import static java.lang.StackWalker.Option.*;
 import java.lang.reflect.*;
 import java.util.*;
 import java.util.stream.*;
 
 public class LocalsAndOperands {
-    static final boolean debug = true;
+    static final boolean debug = false;
+    static final boolean is32bit;
+    static final boolean testUnused;
 
     static Class<?> liveStackFrameClass;
-    static Class<?> primitiveValueClass;
+    static Class<?> primitiveSlotClass;
+    static Class<?> primitiveSlot32Class;
+    static Class<?> primitiveSlot64Class;
+
     static StackWalker extendedWalker;
     static Method getLocals;
     static Method getOperands;
     static Method getMonitors;
-    static Method primitiveType;
+    static Method primitiveSize;
+    static Method primitiveLongValue;
+    static Method primitiveIntValue;
+    static Method getExtendedWalker;
+
+    private static final long LOWER_LONG_VAL = 4L; // Lower bits
+    private static final long UPPER_LONG_VAL = 0x123400000000L; // Upper bits
+    private static final long NEG_LONG_VAL = Long.MIN_VALUE;
+
+    private static final double LOWER_DOUBLE_VAL = Double.longBitsToDouble(0xABCDL);
+    private static final double UPPER_DOUBLE_VAL = Double.longBitsToDouble(0x432100000000L);
 
     static {
         try {
             liveStackFrameClass = Class.forName("java.lang.LiveStackFrame");
-            primitiveValueClass = Class.forName("java.lang.LiveStackFrame$PrimitiveValue");
+            primitiveSlotClass = Class.forName("java.lang.LiveStackFrame$PrimitiveSlot");
+            primitiveSlot32Class = Class.forName("java.lang.LiveStackFrameInfo$PrimitiveSlot32");
+            primitiveSlot64Class = Class.forName("java.lang.LiveStackFrameInfo$PrimitiveSlot64");
 
             getLocals = liveStackFrameClass.getDeclaredMethod("getLocals");
             getLocals.setAccessible(true);
@@ -60,12 +81,31 @@
             getMonitors = liveStackFrameClass.getDeclaredMethod("getMonitors");
             getMonitors.setAccessible(true);
 
-            primitiveType = primitiveValueClass.getDeclaredMethod("type");
-            primitiveType.setAccessible(true);
+            primitiveSize = primitiveSlotClass.getDeclaredMethod("size");
+            primitiveSize.setAccessible(true);
+
+            primitiveLongValue = primitiveSlotClass.getDeclaredMethod("longValue");
+            primitiveLongValue.setAccessible(true);
+
+            primitiveIntValue = primitiveSlotClass.getDeclaredMethod("intValue");
+            primitiveIntValue.setAccessible(true);
 
-            Method method = liveStackFrameClass.getMethod("getStackWalker");
-            method.setAccessible(true);
-            extendedWalker = (StackWalker) method.invoke(null);
+            getExtendedWalker = liveStackFrameClass.getMethod("getStackWalker", Set.class);
+            getExtendedWalker.setAccessible(true);
+            extendedWalker = (StackWalker) getExtendedWalker.invoke(null,
+                    EnumSet.noneOf(StackWalker.Option.class));
+
+            String dataModel = System.getProperty("sun.arch.data.model");
+            if ("32".equals(dataModel)) {
+                is32bit = true;
+            } else if ("64".equals(dataModel)) {
+                is32bit= false;
+            } else {
+                throw new RuntimeException("Weird data model:" + dataModel);
+            }
+            System.out.println("VM bits: " + dataModel);
+
+            testUnused = System.getProperty("testUnused") != null;
         } catch (Throwable t) { throw new RuntimeException(t); }
     }
 
@@ -80,47 +120,17 @@
      * DataProviders *
      *****************/
 
-    /** Calls testLocals() and provides LiveStackFrames for testLocals* methods */
-    @DataProvider
-    public static StackFrame[][] provider() {
-        return new StackFrame[][] {
-            new Tester().testLocals()
-        };
-    }
-
-    /**
-     * Calls testLocalsKeepAlive() and provides LiveStackFrames for testLocals* methods.
-     * Local variables in testLocalsKeepAlive() are ensured to not become dead.
-     */
+    /** Calls KnownLocalsTester.testLocals* and provides LiveStackFrames */
     @DataProvider
-    public static StackFrame[][] keepAliveProvider() {
-        return new StackFrame[][] {
-            new Tester().testLocalsKeepAlive()
-        };
-    }
-
-    /**
-     * Provides StackFrames from a StackWalker without the LOCALS_AND_OPERANDS
-     * option.
-     */
-    @DataProvider
-    public static StackFrame[][] noLocalsProvider() {
-        // Use default StackWalker
-        return new StackFrame[][] {
-            new Tester(StackWalker.getInstance(), true).testLocals()
-        };
-    }
-
-    /**
-     * Calls testLocals() and provides LiveStackFrames for *all* called methods,
-     * including test infrastructure (jtreg, testng, etc)
-     *
-     */
-    @DataProvider
-    public static StackFrame[][] unfilteredProvider() {
-        return new StackFrame[][] {
-            new Tester(extendedWalker, false).testLocals()
-        };
+    public static StackFrame[][] knownLocalsProvider() {
+        List<StackFrame[]> list = new ArrayList<>(3);
+        list.add(new KnownLocalsTester().testLocalsKeepAlive());
+        list.add(new KnownLocalsTester().testLocalsKeepAliveArgs(0xA, 'z',
+                "himom", 0x3FF00000000L + 0xFFFF, Math.PI));
+        if (testUnused) {
+            list.add(new KnownLocalsTester().testLocalsUnused());
+        }
+        return list.toArray(new StackFrame[1][1]);
     }
 
     /****************
@@ -128,135 +138,123 @@
      ****************/
 
     /**
-     * Check for expected local values and types in the LiveStackFrame
+     * Check for expected local values in the LiveStackFrame
      */
-    @Test(dataProvider = "keepAliveProvider")
+    @Test(dataProvider = "knownLocalsProvider")
     public static void checkLocalValues(StackFrame... frames) {
-        if (debug) {
-            System.out.println("Running checkLocalValues");
-            dumpStackWithLocals(frames);
-        }
-        Arrays.stream(frames).filter(f -> f.getMethodName()
-                                           .equals("testLocalsKeepAlive"))
-                                           .forEach(
-            f -> {
-                Object[] locals = invokeGetLocals(f);
-                for (int i = 0; i < locals.length; i++) {
-                    // Value
-                    String expected = Tester.LOCAL_VALUES[i];
-                    Object observed = locals[i];
-                    if (expected != null /* skip nulls in golden values */ &&
-                            !expected.equals(observed.toString())) {
-                        System.err.println("Local value mismatch:");
-                        if (!debug) { dumpStackWithLocals(frames); }
-                        throw new RuntimeException("local " + i + " value is " +
-                                observed + ", expected " + expected);
-                    }
-
-                    // Type
-                    expected = Tester.LOCAL_TYPES[i];
-                    observed = type(locals[i]);
-                    if (expected != null /* skip nulls in golden values */ &&
-                            !expected.equals(observed)) {
-                        System.err.println("Local type mismatch:");
-                        if (!debug) { dumpStackWithLocals(frames); }
-                        throw new RuntimeException("local " + i + " type is " +
-                                observed + ", expected " + expected);
-                    }
-                }
-            }
-        );
+        dumpFramesIfDebug(frames);
+        try {
+            Stream.of(frames)
+                  .filter(f -> KnownLocalsTester.TEST_METHODS.contains(f.getMethodName()))
+                  .forEach(LocalsAndOperands::checkFrameLocals);
+        } catch (Exception e) { dumpFramesIfNotDebug(frames); throw e; }
     }
 
     /**
-     * Basic sanity check for locals and operands
+     * Check the locals in the given StackFrame against the expected values.
      */
-    @Test(dataProvider = "provider")
-    public static void sanityCheck(StackFrame... frames) {
-        if (debug) {
-            System.out.println("Running sanityCheck");
-        }
-        try {
-            Stream<StackFrame> stream = Arrays.stream(frames);
-            if (debug) {
-                stream.forEach(LocalsAndOperands::printLocals);
+    private static void checkFrameLocals(StackFrame f) {
+        Object[] expectedArray = KnownLocalsTester.LOCAL_VALUES;
+        Object[] locals = invokeGetLocals(f);
+
+        for (int i = 0; i < locals.length; i++) {
+            Object expected = expectedArray[i];
+            Object observed = locals[i];
+
+            if (expected == null) { /* skip nulls in golden values */
+                continue;
+            } else if (expected instanceof KnownLocalsTester.TwoSlotValue) {
+                // confirm integrity of expected values
+                assertEquals(expectedArray[i+1], null,
+                        "Malformed array of expected values - slot after TwoSlotValue should be null");
+                assertLongIsInSlots(locals[i], locals[i+1],
+                        ((KnownLocalsTester.TwoSlotValue)expected).value);
+                i++; // skip following slot
+            } else if (primitiveSlotClass.isInstance(observed)) { // single slot primitive
+                assertTrue(primitiveValueEquals(observed, expected),
+                        "Local value mismatch: local " + i + " value is " +
+                          observed + ", expected " + expected);
+            } else if (expected instanceof Class) {
+                assertTrue(((Class)expected).isInstance(observed),
+                        "Local value mismatch: local " + i + " expected instancof " +
+                          expected + " but got " + observed);
+            } else if (expected instanceof String) {
+                assertEquals(expected, observed, "Local value mismatch: local " +
+                        i + " value is " + observed + ", expected " + expected);
             } else {
-                System.out.println(stream.count() + " frames");
+                throw new RuntimeException("Unrecognized expected local value " +
+                        i + ": " + expected);
             }
-        } catch (Throwable t) {
-            dumpStackWithLocals(frames);
-            throw t;
         }
     }
 
     /**
      * Sanity check for locals and operands, including testng/jtreg frames
+     * using all StackWalker options.
      */
-    @Test(dataProvider = "unfilteredProvider")
-    public static void unfilteredSanityCheck(StackFrame... frames) {
+    @Test
+    public synchronized void fullStackSanityCheck() throws Throwable {
         if (debug) {
-            System.out.println("Running unfilteredSanityCheck");
+            System.out.println("Running fullStackSanityCheck");
         }
-        try {
-            Stream<StackFrame> stream = Arrays.stream(frames);
+        StackWalker sw = (StackWalker) getExtendedWalker.invoke(null,
+                EnumSet.of(SHOW_HIDDEN_FRAMES, SHOW_REFLECT_FRAMES,
+                           RETAIN_CLASS_REFERENCE));
+        sw.forEach(f -> {
             if (debug) {
-                stream.forEach(f -> { System.out.println(f + ": " +
-                        invokeGetLocals(f).length + " locals"); } );
+                printLocals(f);
             } else {
-                System.out.println(stream.count() + " frames");
+                try {
+                    System.out.println("    " + f + ": " +
+                      ((Object[]) getLocals.invoke(f)).length + " locals, " +
+                      ((Object[]) getOperands.invoke(f)).length + " operands, " +
+                      ((Object[]) getMonitors.invoke(f)).length + " monitors");
+                } catch (IllegalAccessException|InvocationTargetException t) {
+                    throw new RuntimeException(t);
+                }
             }
-        } catch (Throwable t) {
-            dumpStackWithLocals(frames);
-            throw t;
-        }
+        });
     }
 
     /**
      * Test that LiveStackFrames are not provided with the default StackWalker
      * options.
      */
-    @Test(dataProvider = "noLocalsProvider")
-    public static void withoutLocalsAndOperands(StackFrame... frames) {
-        for (StackFrame frame : frames) {
-            if (liveStackFrameClass.isInstance(frame)) {
-                throw new RuntimeException("should not be LiveStackFrame");
-            }
-        }
+    @Test
+    public static void noLocalsSanityCheck() {
+        StackWalker sw = StackWalker.getInstance();
+        sw.forEach(f -> {
+            assertFalse(liveStackFrameClass.isInstance(f),
+                        "should not be LiveStackFrame");
+        });
     }
 
-    static class Tester {
+    /**
+     * Class stack-walking methods with a known set of methods and local variables.
+     */
+    static class KnownLocalsTester {
         private StackWalker walker;
-        private boolean filter = true; // Filter out testng/jtreg/etc frames?
 
-        Tester() {
+        KnownLocalsTester() {
             this.walker = extendedWalker;
         }
 
-        Tester(StackWalker walker, boolean filter) {
-            this.walker = walker;
-            this.filter = filter;
-        }
-
         /**
          * Perform stackwalk without keeping local variables alive and return an
          * array of the collected StackFrames
          */
-        private synchronized StackFrame[] testLocals() {
+        private synchronized StackFrame[] testLocalsUnused() {
             // Unused local variables will become dead
-            int x = 10;
-            char c = 'z';
+            int x = 0xA;
+            char c = 'z'; // 0x7A
             String hi = "himom";
-            long l = 1000000L;
-            double d =  3.1415926;
+            long l = 0x3FF00000000L + 0xFFFFL;
+            double d =  Math.PI;
 
-            if (filter) {
-                return walker.walk(s -> s.filter(f -> TEST_METHODS.contains(f
-                        .getMethodName())).collect(Collectors.toList()))
-                        .toArray(new StackFrame[0]);
-            } else {
-                return walker.walk(s -> s.collect(Collectors.toList()))
-                        .toArray(new StackFrame[0]);
-            }
+            return walker.walk(s ->
+                s.filter(f -> TEST_METHODS.contains(f.getMethodName()))
+                 .toArray(StackFrame[]::new)
+            );
         }
 
         /**
@@ -264,64 +262,153 @@
          * the collected StackFrames
          */
         private synchronized StackFrame[] testLocalsKeepAlive() {
-            int x = 10;
-            char c = 'z';
+            int x = 0xA;
+            char c = 'z'; // 0x7A
             String hi = "himom";
-            long l = 1000000L;
-            double d =  3.1415926;
+            long l = 0x3FF00000000L + 0xFFFFL;
+            double d =  Math.PI;
 
-            List<StackWalker.StackFrame> frames;
-            if (filter) {
-                frames = walker.walk(s -> s.filter(f -> TEST_METHODS.contains(f
-                        .getMethodName())).collect(Collectors.toList()));
-            } else {
-                frames = walker.walk(s -> s.collect(Collectors.toList()));
-            }
+            StackFrame[] frames = walker.walk(s ->
+                s.filter(f -> TEST_METHODS.contains(f.getMethodName()))
+                 .toArray(StackFrame[]::new)
+            );
 
             // Use local variables so they stay alive
-            System.out.println("Stayin' alive: "+x+" "+c+" "+hi+" "+l+" "+d);
-            return frames.toArray(new StackFrame[0]); // FIXME: convert to Array here
+            System.out.println("Stayin' alive: "+this+" "+x+" "+c+" "+hi+" "+l+" "+d);
+            return frames;
+        }
+
+        /**
+         * Perform stackwalk, keeping method arguments alive, and return a list of
+         * the collected StackFrames
+         */
+        private synchronized StackFrame[] testLocalsKeepAliveArgs(int x, char c,
+                                                                  String hi, long l,
+                                                                  double d) {
+            StackFrame[] frames = walker.walk(s ->
+                s.filter(f -> TEST_METHODS.contains(f.getMethodName()))
+                 .toArray(StackFrame[]::new)
+            );
+
+            // Use local variables so they stay alive
+            System.out.println("Stayin' alive: "+this+" "+x+" "+c+" "+hi+" "+l+" "+d);
+            return frames;
+        }
+
+        // An expected two-slot local (i.e. long or double)
+        static class TwoSlotValue {
+            public long value;
+            public TwoSlotValue(long value) { this.value = value; }
         }
 
-        // Expected values for locals in testLocals() & testLocalsKeepAlive()
-        // TODO: use real values instead of Strings, rebuild doubles & floats, etc
-        private final static String[] LOCAL_VALUES = new String[] {
-            null, // skip, LocalsAndOperands$Tester@XXX identity is different each run
-            "10",
-            "122",
+        // Expected values for locals in KnownLocalsTester.testLocals* methods
+        private final static Object[] LOCAL_VALUES = new Object[] {
+            LocalsAndOperands.KnownLocalsTester.class,
+            Integer.valueOf(0xA),
+            Integer.valueOf(0x7A),
             "himom",
-            "0",
-            null, // skip, fix in 8156073
-            null, // skip, fix in 8156073
-            null, // skip, fix in 8156073
-            "0"
+            new TwoSlotValue(0x3FF00000000L + 0xFFFFL),
+            null, // 2nd slot
+            new TwoSlotValue(Double.doubleToRawLongBits(Math.PI)),
+            null, // 2nd slot
+            Integer.valueOf(0)
         };
 
-        // Expected types for locals in testLocals() & testLocalsKeepAlive()
-        // TODO: use real types
-        private final static String[] LOCAL_TYPES = new String[] {
-            null, // skip
-            "I",
-            "I",
-            "java.lang.String",
-            "I",
-            "I",
-            "I",
-            "I",
-            "I"
-        };
+        private final static List<String> TEST_METHODS =
+                List.of("testLocalsUnused",
+                        "testLocalsKeepAlive",
+                        "testLocalsKeepAliveArgs");
+    }
+
+    /* Simpler tests of long & double arguments */
+
+    @Test
+    public static void testUsedLongArg() throws Exception {
+        usedLong(LOWER_LONG_VAL);
+        usedLong(UPPER_LONG_VAL);
+        usedLong(NEG_LONG_VAL);
+    }
+
+    private static void usedLong(long longArg) throws Exception {
+        StackFrame[] frames = extendedWalker.walk(s ->
+            s.filter(f -> "usedLong".equals(f.getMethodName()))
+             .toArray(StackFrame[]::new)
+        );
+        try {
+            dumpFramesIfDebug(frames);
+
+            Object[] locals = (Object[]) getLocals.invoke(frames[0]);
+            assertLongIsInSlots(locals[0], locals[1], longArg);
+            System.out.println("Stayin' alive: " + longArg);
+        } catch (Exception t) {
+            dumpFramesIfNotDebug(frames);
+            throw t;
+        }
+    }
+
+    @Test
+    public static void testUnusedLongArg() throws Exception {
+        if (testUnused) {
+            unusedLong(NEG_LONG_VAL);
+        }
+    }
 
-        final static Map NUM_LOCALS = Map.of("testLocals", 8,
-                                             "testLocalsKeepAlive",
-                                             LOCAL_VALUES.length);
-        private final static Collection<String> TEST_METHODS = NUM_LOCALS.keySet();
+    private static void unusedLong(long longArg) throws Exception {
+        StackFrame[] frames = extendedWalker.walk(s ->
+            s.filter(f -> "unusedLong".equals(f.getMethodName()))
+             .toArray(StackFrame[]::new)
+        );
+        try {
+            dumpFramesIfDebug(frames);
+
+            final Object[] locals = (Object[]) getLocals.invoke(frames[0]);
+            assertLongIsInSlots(locals[0], locals[1], NEG_LONG_VAL);
+        } catch (Exception t) {
+            dumpFramesIfNotDebug(frames);
+            throw t;
+        }
+    }
+
+    @Test
+    public static void testUsedDoubleArg() throws Exception {
+        usedDouble(LOWER_DOUBLE_VAL);
+        usedDouble(UPPER_DOUBLE_VAL);
     }
 
+    private static void usedDouble(double doubleArg) throws Exception {
+        StackFrame[] frames = extendedWalker.walk(s ->
+            s.filter(f -> "usedDouble".equals(f.getMethodName()))
+             .toArray(StackFrame[]::new)
+        );
+        try {
+            dumpFramesIfDebug(frames);
+
+            Object[] locals = (Object[]) getLocals.invoke(frames[0]);
+            assertDoubleIsInSlots(locals[0], locals[1], doubleArg);
+            System.out.println("Stayin' alive: " + doubleArg);
+        } catch (Exception t) {
+            dumpFramesIfNotDebug(frames);
+            throw t;
+        }
+    }
+
+    /*******************
+     * Utility Methods *
+     *******************/
+
     /**
      * Print stack trace with locals
      */
     public static void dumpStackWithLocals(StackFrame...frames) {
-        Arrays.stream(frames).forEach(LocalsAndOperands::printLocals);
+        Stream.of(frames).forEach(LocalsAndOperands::printLocals);
+    }
+
+    public static void dumpFramesIfDebug(StackFrame...frames) {
+        if (debug) { dumpStackWithLocals(frames); }
+    }
+
+    public static void dumpFramesIfNotDebug(StackFrame...frames) {
+        if (!debug) { dumpStackWithLocals(frames); }
     }
 
     /**
@@ -329,10 +416,21 @@
      */
     public static void printLocals(StackWalker.StackFrame frame) {
         try {
-            System.out.println(frame);
+            System.out.println("Locals for: " + frame);
             Object[] locals = (Object[]) getLocals.invoke(frame);
             for (int i = 0; i < locals.length; i++) {
-                System.out.format("  local %d: %s type %s\n", i, locals[i], type(locals[i]));
+                String localStr = null;
+
+                if (primitiveSlot64Class.isInstance(locals[i])) {
+                    localStr = String.format("0x%X",
+                            (Long)primitiveLongValue.invoke(locals[i]));
+                } else if (primitiveSlot32Class.isInstance(locals[i])) {
+                    localStr = String.format("0x%X",
+                            (Integer)primitiveIntValue.invoke(locals[i]));
+                } else if (locals[i] != null) {
+                    localStr = locals[i].toString();
+                }
+                System.out.format("  local %d: %s type %s\n", i, localStr, type(locals[i]));
             }
 
             Object[] operands = (Object[]) getOperands.invoke(frame);
@@ -352,12 +450,87 @@
         try {
             if (o == null) {
                 return "null";
-            } else if (primitiveValueClass.isInstance(o)) {
-                char c = (char)primitiveType.invoke(o);
-                return String.valueOf(c);
+            } else if (primitiveSlotClass.isInstance(o)) {
+                int s = (int)primitiveSize.invoke(o);
+                return s + "-byte primitive";
             } else {
                 return o.getClass().getName();
             }
         } catch(Exception e) { throw new RuntimeException(e); }
     }
+
+    /*
+     * Check if the PrimitiveValue "primVal" contains the specified value,
+     * either a Long or an Integer.
+     */
+    static boolean primitiveValueEquals(Object primVal, Object expectedVal) {
+        try {
+            if (expectedVal instanceof Long) {
+                assertFalse(is32bit);
+                assertTrue(primitiveSlot64Class.isInstance(primVal));
+                assertTrue(8 == (int)primitiveSize.invoke(primVal));
+                return Objects.equals(primitiveLongValue.invoke(primVal), expectedVal);
+            } else if (expectedVal instanceof Integer) {
+                int expectedInt = (Integer)expectedVal;
+                if (is32bit) {
+                    assertTrue(primitiveSlot32Class.isInstance(primVal),
+                            "expected a PrimitiveSlot32 on 32-bit VM");
+                    assertTrue(4 == (int)primitiveSize.invoke(primVal));
+                    return expectedInt == (int)primitiveIntValue.invoke(primVal);
+                } else {
+                    assertTrue(primitiveSlot64Class.isInstance(primVal),
+                            "expected a PrimitiveSlot64 on 64-bit VM");
+                    assertTrue(8 == (int)primitiveSize.invoke(primVal));
+                    // Look for int expectedVal in high- or low-order 32 bits
+                    long primValLong = (long)primitiveLongValue.invoke(primVal);
+                    return (int)(primValLong & 0x00000000FFFFFFFFL) == expectedInt ||
+                           (int)(primValLong >>> 32) == expectedInt;
+                }
+            } else {
+                throw new RuntimeException("Called with non-Integer/Long: " + expectedVal);
+            }
+        } catch (IllegalAccessException|InvocationTargetException e) {
+            throw new RuntimeException(e);
+        }
+
+    }
+
+    /*
+     * Assert that the expected 2-slot long value is stored somewhere in the
+     * pair of slots.
+     * Throw exception if long value isn't in the two slots given.
+     * Accounts for 32 vs 64 bit, but is lax on endianness (accepts either)
+     */
+    static void assertLongIsInSlots(Object primVal0, Object primVal1, long expected) {
+        try {
+            if (is32bit) {
+                int upper = (int)(expected & 0xFFFFFFFFL);
+                int lower = (int)(expected >> 32);
+
+                if (!((primitiveValueEquals(primVal0, upper) &&
+                       primitiveValueEquals(primVal1, lower)) ||
+                      (primitiveValueEquals(primVal0, lower) &&
+                       primitiveValueEquals(primVal1, upper)))) {
+                    throw new RuntimeException(String.format("0x%X and 0x%X of 0x%016X not found in 0x%X and 0x%X",
+                            upper, lower, expected,
+                            (int)primitiveIntValue.invoke(primVal0),
+                            (int)primitiveIntValue.invoke(primVal1)));
+                }
+            } else {
+                if (!(primitiveValueEquals(primVal0, expected) ||
+                      primitiveValueEquals(primVal1, expected))) {
+                    throw new RuntimeException(String.format("0x%016X not found in 0x%016X or 0x%016X",
+                            expected,
+                            (long)primitiveLongValue.invoke(primVal0),
+                            (long)primitiveLongValue.invoke(primVal1)));
+                }
+            }
+        } catch (IllegalAccessException|InvocationTargetException e) {
+            throw new RuntimeException(e);
+        }
+    }
+
+    static void assertDoubleIsInSlots(Object primVal0, Object primVal1, double expected) {
+        assertLongIsInSlots(primVal0, primVal1, Double.doubleToRawLongBits(expected));
+    }
 }
--- a/jdk/test/java/lang/StackWalker/LocalsCrash.java	Mon Feb 13 11:57:56 2017 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,75 +0,0 @@
-/*
- * Copyright (c) 2016, 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
- * @bug 8147039
- * @summary Test for -Xcomp crash that happened before 8147039 fix
- * @modules java.base/java.lang:open
- * @run testng/othervm -Xcomp LocalsCrash
- */
-
-import org.testng.annotations.*;
-import java.lang.reflect.*;
-import java.util.List;
-import java.util.stream.Collectors;
-
-public class LocalsCrash {
-    static Class<?> liveStackFrameClass;
-    static Method getStackWalker;
-
-    static {
-        try {
-            liveStackFrameClass = Class.forName("java.lang.LiveStackFrame");
-            getStackWalker = liveStackFrameClass.getMethod("getStackWalker");
-            getStackWalker.setAccessible(true);
-        } catch (Throwable t) { throw new RuntimeException(t); }
-    }
-
-    private StackWalker walker;
-
-    LocalsCrash() {
-        try {
-            walker = (StackWalker) getStackWalker.invoke(null);
-        } catch (Exception e) { throw new RuntimeException(e); }
-    }
-
-    @Test
-    public void test00() { doStackWalk(); }
-
-    @Test
-    public void test01() { doStackWalk(); }
-
-    private synchronized List<StackWalker.StackFrame> doStackWalk() {
-        try {
-            // Unused local variables will become dead
-            int x = 10;
-            char c = 'z';
-            String hi = "himom";
-            long l = 1000000L;
-            double d =  3.1415926;
-
-            return walker.walk(s -> s.collect(Collectors.toList()));
-        } catch (Exception e) { throw new RuntimeException(e); }
-    }
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/StackWalker/ReflectionFrames.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,842 @@
+/*
+ * Copyright (c) 2017, 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
+ * @bug 8173898
+ * @summary Basic test for checking filtering of reflection frames
+ * @run testng ReflectionFrames
+ */
+
+import java.lang.StackWalker.StackFrame;
+import java.lang.reflect.Constructor;
+import java.lang.reflect.Method;
+import java.lang.invoke.MethodHandle;
+import java.lang.invoke.MethodHandles;
+import java.lang.invoke.MethodHandles.Lookup;
+import java.lang.invoke.MethodType;
+import java.util.EnumSet;
+import java.util.List;
+import java.util.function.Supplier;
+import java.util.stream.Collectors;
+import java.util.stream.Stream;
+import static java.lang.StackWalker.Option.*;
+
+import org.testng.annotations.DataProvider;
+import org.testng.annotations.Test;
+import static org.testng.Assert.*;
+
+public class ReflectionFrames {
+    final static boolean verbose = false;
+
+    /**
+     * This test invokes new StackInspector() directly from
+     * the caller StackInspector.Caller.create method.
+     * It checks that the caller is StackInspector.Caller.
+     * It also checks the expected frames collected
+     * by walking the stack from the default StackInspector()
+     * constructor.
+     * This is done twice, once using a default StackWalker
+     * that hides reflection frames, once using a StackWalker
+     * configured to show reflection frames.
+     */
+    @Test
+    public static void testNewStackInspector() throws Exception {
+        // Sets the default walker which hides reflection
+        // frames.
+        StackInspector.walker.set(StackInspector.walkerHide);
+
+        // Calls the StackInspector.create method through reflection
+        // and check the frames collected in the StackInspector
+        // default constructor.
+        // The create method invokes new StackInspector() directly.
+        // No reflection frame should appear.
+        System.out.println("testNewStackInspector: create");
+
+        StackInspector obj = ((StackInspector)StackInspector.Caller.class
+                             .getMethod("create", How.class)
+                             .invoke(null, How.NEW));
+        assertEquals(obj.collectedFrames,
+                     List.of(StackInspector.class.getName()
+                                 +"::<init>",
+                             StackInspector.Caller.class.getName()
+                                 +"::create",
+                             ReflectionFrames.class.getName()
+                                 +"::testNewStackInspector"));
+        assertEquals(obj.cls, StackInspector.Caller.class);
+        assertEquals(obj.filtered, 0);
+
+        // Calls the StackInspector.reflect method through reflection
+        // and check the frames collected in the StackInspector
+        // default constructor.
+        // The reflect method invokes the create method through
+        // reflection.
+        // The create method invokes new StackInspector() directly.
+        // No reflection frame should appear.
+        System.out.println("testNewStackInspector: reflect");
+
+        obj = ((StackInspector)StackInspector.Caller.class
+                             .getMethod("reflect", How.class)
+                             .invoke(null, How.NEW));
+        assertEquals(obj.collectedFrames,
+                     List.of(StackInspector.class.getName()
+                                 +"::<init>",
+                             StackInspector.Caller.class.getName()
+                                 +"::create",
+                             StackInspector.Caller.class.getName()
+                                 +"::reflect",
+                             ReflectionFrames.class.getName()
+                                 +"::testNewStackInspector"));
+        assertEquals(obj.cls, StackInspector.Caller.class);
+        assertEquals(obj.filtered, 0);
+
+        // Calls the StackInspector.handle method through reflection
+        // and check the frames collected in the StackInspector
+        // default constructor.
+        // The handle method invokes the create method using
+        // a MethodHandle.
+        // The create method invokes new StackInspector() directly.
+        // No reflection frame should appear.
+        System.out.println("testNewStackInspector: handle");
+
+        obj = ((StackInspector)StackInspector.Caller.class
+                             .getMethod("handle", How.class)
+                             .invoke(null, How.NEW));
+        assertEquals(obj.collectedFrames,
+                     List.of(StackInspector.class.getName()
+                                 +"::<init>",
+                             StackInspector.Caller.class.getName()
+                                 +"::create",
+                             StackInspector.Caller.class.getName()
+                                 +"::handle",
+                             ReflectionFrames.class.getName()
+                                 +"::testNewStackInspector"));
+        assertEquals(obj.cls, StackInspector.Caller.class);
+        assertEquals(obj.filtered, 0);
+
+        // Sets a non-default walker configured to show
+        // reflection frames
+        StackInspector.walker.set(StackInspector.walkerShow);
+
+        // Calls the StackInspector.create method through reflection
+        // and check the frames collected in the StackInspector
+        // default constructor.
+        // The create method invokes new StackInspector() directly.
+        // We should see all reflection frames, except the
+        // jdk.internal.reflect frames which we are filtering
+        // out in StackInspector::filter.
+        System.out.println("testNewStackInspector: create: show reflect");
+
+        obj = ((StackInspector)StackInspector.Caller.class
+                             .getMethod("create", How.class)
+                             .invoke(null, How.NEW));
+        assertEquals(obj.collectedFrames,
+                     List.of(StackInspector.class.getName()
+                                 +"::<init>",
+                             StackInspector.Caller.class.getName()
+                                 +"::create",
+                             Method.class.getName()
+                                 +"::invoke",
+                             ReflectionFrames.class.getName()
+                                 +"::testNewStackInspector"));
+        assertEquals(obj.cls, StackInspector.Caller.class);
+        assertNotEquals(obj.filtered, 0);
+
+        // Calls the StackInspector.reflect method through reflection
+        // and check the frames collected in the StackInspector
+        // default constructor.
+        // The reflect method invokes the create method through
+        // reflection.
+        // The create method invokes new StackInspector() directly.
+        // We should see all reflection frames, except the
+        // jdk.internal.reflect frames which we are filtering
+        // out in StackInspector::filter.
+        System.out.println("testNewStackInspector: reflect: show reflect");
+
+        obj = ((StackInspector)StackInspector.Caller.class
+                             .getMethod("reflect", How.class)
+                             .invoke(null, How.NEW));
+        assertEquals(obj.collectedFrames,
+                     List.of(StackInspector.class.getName()
+                                 +"::<init>",
+                             StackInspector.Caller.class.getName()
+                                 +"::create",
+                             Method.class.getName()
+                                 +"::invoke",
+                             StackInspector.Caller.class.getName()
+                                 +"::reflect",
+                             Method.class.getName()
+                                 +"::invoke",
+                             ReflectionFrames.class.getName()
+                                 +"::testNewStackInspector"));
+        assertEquals(obj.cls, StackInspector.Caller.class);
+        assertNotEquals(obj.filtered, 0);
+
+        // Calls the StackInspector.handle method through reflection
+        // and check the frames collected in the StackInspector
+        // default constructor.
+        // The handle method invokes the create method using
+        // MethodHandle.
+        // The create method invokes new StackInspector() directly.
+        // We should see all reflection frames, except the
+        // jdk.internal.reflect frames which we are filtering
+        // out in StackInspector::filter.
+        System.out.println("testNewStackInspector: handle: show reflect");
+
+        obj = ((StackInspector)StackInspector.Caller.class
+                             .getMethod("handle", How.class)
+                             .invoke(null, How.NEW));
+        assertEquals(obj.collectedFrames,
+                     List.of(StackInspector.class.getName()
+                                 +"::<init>",
+                             StackInspector.Caller.class.getName()
+                                 +"::create",
+                             // MethodHandle::invoke remains hidden
+                             StackInspector.Caller.class.getName()
+                                 +"::handle",
+                             Method.class.getName()
+                                 +"::invoke",
+                             ReflectionFrames.class.getName()
+                                 +"::testNewStackInspector"));
+        assertEquals(obj.cls, StackInspector.Caller.class);
+        assertNotEquals(obj.filtered, 0);
+    }
+
+   /**
+     * This test invokes Constructor.newInstance() from
+     * the caller StackInspector.Caller.create method.
+     * It checks that the caller is StackInspector.Caller.
+     * It also checks the expected frames collected
+     * by walking the stack from the default StackInspector()
+     * constructor.
+     * This is done twice, once using a default StackWalker
+     * that hides reflection frames, once using a StackWalker
+     * configured to show reflection frames.
+     */
+    @Test
+    public static void testConstructor() throws Exception {
+        // Sets the default walker which hides reflection
+        // frames.
+        StackInspector.walker.set(StackInspector.walkerHide);
+
+        // Calls the StackInspector.create method through reflection
+        // and check the frames collected in the StackInspector
+        // default constructor.
+        // The create method invokes Constructor.newInstance().
+        // No reflection frame should appear.
+        System.out.println("testConstructor: create");
+
+        StackInspector obj = ((StackInspector)StackInspector.Caller.class
+                             .getMethod("create", How.class)
+                             .invoke(null, How.CONSTRUCTOR));
+        assertEquals(obj.collectedFrames,
+                     List.of(StackInspector.class.getName()
+                                 +"::<init>",
+                             StackInspector.Caller.class.getName()
+                                 +"::create",
+                             ReflectionFrames.class.getName()
+                                 +"::testConstructor"));
+        assertEquals(obj.cls, StackInspector.Caller.class);
+        assertEquals(obj.filtered, 0);
+
+        // Calls the StackInspector.reflect method through reflection
+        // and check the frames collected in the StackInspector
+        // default constructor.
+        // The reflect method invokes the create method through
+        // reflection.
+        // The create method invokes Constructor.newInstance().
+        // No reflection frame should appear.
+        System.out.println("testConstructor: reflect");
+
+        obj = ((StackInspector)StackInspector.Caller.class
+                             .getMethod("reflect", How.class)
+                             .invoke(null, How.CONSTRUCTOR));
+        assertEquals(obj.collectedFrames,
+                     List.of(StackInspector.class.getName()
+                                 +"::<init>",
+                             StackInspector.Caller.class.getName()
+                                 +"::create",
+                             StackInspector.Caller.class.getName()
+                                 +"::reflect",
+                             ReflectionFrames.class.getName()
+                                 +"::testConstructor"));
+        assertEquals(obj.cls, StackInspector.Caller.class);
+        assertEquals(obj.filtered, 0);
+
+        // Calls the StackInspector.handle method through reflection
+        // and check the frames collected in the StackInspector
+        // default constructor.
+        // The handle method invokes the create method using
+        // MethodHandle.
+        // The create method invokes Constructor.newInstance().
+        // No reflection frame should appear.
+        System.out.println("testConstructor: handle");
+
+        obj = ((StackInspector)StackInspector.Caller.class
+                             .getMethod("handle", How.class)
+                             .invoke(null, How.CONSTRUCTOR));
+        assertEquals(obj.collectedFrames,
+                     List.of(StackInspector.class.getName()
+                                 +"::<init>",
+                             StackInspector.Caller.class.getName()
+                                 +"::create",
+                             StackInspector.Caller.class.getName()
+                                 +"::handle",
+                             ReflectionFrames.class.getName()
+                                 +"::testConstructor"));
+        assertEquals(obj.cls, StackInspector.Caller.class);
+        assertEquals(obj.filtered, 0);
+
+        // Sets a non-default walker configured to show
+        // reflection frames
+        StackInspector.walker.set(StackInspector.walkerShow);
+
+        // Calls the StackInspector.create method through reflection
+        // and check the frames collected in the StackInspector
+        // default constructor.
+        // The create method invokes Constructor.newInstance().
+        // We should see all reflection frames, except the
+        // jdk.internal.reflect frames which we are filtering
+        // out in StackInspector::filter.
+        System.out.println("testConstructor: create: show reflect");
+
+        obj = ((StackInspector)StackInspector.Caller.class
+                             .getMethod("create", How.class)
+                             .invoke(null, How.CONSTRUCTOR));
+        assertEquals(obj.collectedFrames,
+                     List.of(StackInspector.class.getName()
+                                 +"::<init>",
+                             Constructor.class.getName()
+                                 +"::newInstance",
+                             StackInspector.Caller.class.getName()
+                                 +"::create",
+                             Method.class.getName()
+                                 +"::invoke",
+                             ReflectionFrames.class.getName()
+                                 +"::testConstructor"));
+        assertEquals(obj.cls, StackInspector.Caller.class);
+        assertNotEquals(obj.filtered, 0);
+
+        // Calls the StackInspector.reflect method through reflection
+        // and check the frames collected in the StackInspector
+        // default constructor.
+        // The reflect method invokes the create method through
+        // reflection.
+        // The create method invokes Constructor.newInstance().
+        // We should see all reflection frames, except the
+        // jdk.internal.reflect frames which we are filtering
+        // out in StackInspector::filter.
+        System.out.println("testConstructor: reflect: show reflect");
+
+        obj = ((StackInspector)StackInspector.Caller.class
+                             .getMethod("reflect", How.class)
+                             .invoke(null, How.CONSTRUCTOR));
+        assertEquals(obj.collectedFrames,
+                     List.of(StackInspector.class.getName()
+                                 +"::<init>",
+                             Constructor.class.getName()
+                                 +"::newInstance",
+                             StackInspector.Caller.class.getName()
+                                 +"::create",
+                             Method.class.getName()
+                                 +"::invoke",
+                             StackInspector.Caller.class.getName()
+                                 +"::reflect",
+                             Method.class.getName()
+                                 +"::invoke",
+                             ReflectionFrames.class.getName()
+                                 +"::testConstructor"));
+        assertEquals(obj.cls, StackInspector.Caller.class);
+        assertNotEquals(obj.filtered, 0);
+
+        // Calls the StackInspector.handle method through reflection
+        // and check the frames collected in the StackInspector
+        // default constructor.
+        // The handle method invokes the create method using
+        // MethodHandle.
+        // The create method invokes Constructor.newInstance().
+        // We should see all reflection frames, except the
+        // jdk.internal.reflect frames which we are filtering
+        // out in StackInspector::filter.
+        System.out.println("testConstructor: handle: show reflect");
+
+        obj = ((StackInspector)StackInspector.Caller.class
+                             .getMethod("handle", How.class)
+                             .invoke(null, How.CONSTRUCTOR));
+        assertEquals(obj.collectedFrames,
+                     List.of(StackInspector.class.getName()
+                                 +"::<init>",
+                             Constructor.class.getName()
+                                 +"::newInstance",
+                             StackInspector.Caller.class.getName()
+                                 +"::create",
+                             // MethodHandle::invoke remains hidden
+                             StackInspector.Caller.class.getName()
+                                 +"::handle",
+                             Method.class.getName()
+                                 +"::invoke",
+                             ReflectionFrames.class.getName()
+                                 +"::testConstructor"));
+        assertEquals(obj.cls, StackInspector.Caller.class);
+        assertNotEquals(obj.filtered, 0);
+    }
+
+   /**
+     * This test invokes StackInspector.class.newInstance() from
+     * the caller StackInspector.Caller.create method. Because
+     * Class.newInstance() is not considered as a
+     * reflection frame, the the caller returned by
+     * getCallerClass() should appear to be java.lang.Class
+     * and not StackInspector.Caller.
+     * It also checks the expected frames collected
+     * by walking the stack from the default StackInspector()
+     * constructor.
+     * This is done twice, once using a default StackWalker
+     * that hides reflection frames, once using a StackWalker
+     * configured to show reflection frames.
+     */
+    @Test
+    public static void testNewInstance() throws Exception {
+        // Sets the default walker which hides reflection
+        // frames.
+        StackInspector.walker.set(StackInspector.walkerHide);
+
+        // Calls the StackInspector.create method through reflection
+        // and check the frames collected in the StackInspector
+        // default constructor.
+        // The create method invokes StackInspector.class.newInstance().
+        // No reflection frame should appear, except
+        // Class::newInstance which is not considered as
+        // a reflection frame.
+        System.out.println("testNewInstance: create");
+
+        StackInspector obj = ((StackInspector)StackInspector.Caller.class
+                             .getMethod("create", How.class)
+                             .invoke(null, How.CLASS));
+        assertEquals(obj.collectedFrames,
+                     List.of(StackInspector.class.getName()
+                                 +"::<init>",
+                             Class.class.getName()
+                                 +"::newInstance",
+                             StackInspector.Caller.class.getName()
+                                 +"::create",
+                             ReflectionFrames.class.getName()
+                                 +"::testNewInstance"));
+        // Because Class.newInstance is not filtered, then the
+        // caller is Class.class
+        assertEquals(obj.cls, Class.class);
+        assertEquals(obj.filtered, 0);
+
+        // Calls the StackInspector.reflect method through reflection
+        // and check the frames collected in the StackInspector
+        // default constructor.
+        // The reflect method invokes the create method through
+        // reflection.
+        // The create method invokes StackInspector.class.newInstance().
+        // No reflection frame should appear, except
+        // Class::newInstance which is not considered as
+        // a reflection frame.
+        System.out.println("testNewInstance: reflect");
+
+        obj = ((StackInspector)StackInspector.Caller.class
+                             .getMethod("reflect", How.class)
+                             .invoke(null, How.CLASS));
+        assertEquals(obj.collectedFrames,
+                     List.of(StackInspector.class.getName()
+                                 +"::<init>",
+                             Class.class.getName()
+                                 +"::newInstance",
+                             StackInspector.Caller.class.getName()
+                                 +"::create",
+                             StackInspector.Caller.class.getName()
+                                 +"::reflect",
+                             ReflectionFrames.class.getName()
+                                 +"::testNewInstance"));
+
+        // Because Class.newInstance is not filtered, then the
+        // caller is Class.class
+        assertEquals(obj.cls, Class.class);
+        assertEquals(obj.filtered, 0);
+
+        // Calls the StackInspector.handle method through reflection
+        // and check the frames collected in the StackInspector
+        // default constructor.
+        // The handle method invokes the create method using
+        // reflection.
+        // The create method invokes StackInspector.class.newInstance().
+        // No reflection frame should appear, except
+        // Class::newInstance which is not considered as
+        // a reflection frame.
+        System.out.println("testNewInstance: handle");
+
+        obj = ((StackInspector)StackInspector.Caller.class
+                             .getMethod("handle", How.class)
+                             .invoke(null, How.CLASS));
+        assertEquals(obj.collectedFrames,
+                     List.of(StackInspector.class.getName()
+                                 +"::<init>",
+                             Class.class.getName()
+                                 +"::newInstance",
+                             StackInspector.Caller.class.getName()
+                                 +"::create",
+                             StackInspector.Caller.class.getName()
+                                 +"::handle",
+                             ReflectionFrames.class.getName()
+                                 +"::testNewInstance"));
+
+        // Because Class.newInstance is not filtered, then the
+        // caller is Class.class
+        assertEquals(obj.cls, Class.class);
+        assertEquals(obj.filtered, 0);
+
+        // Sets a non-default walker configured to show
+        // reflection frames
+        StackInspector.walker.set(StackInspector.walkerShow);
+
+        // Calls the StackInspector.create method through reflection
+        // and check the frames collected in the StackInspector
+        // default constructor.
+        // The create method invokes StackInspector.class.newInstance().
+        // We should see all reflection frames, except the
+        // jdk.internal.reflect frames which we are filtering
+        // out in StackInspector::filter.
+        System.out.println("testNewInstance: create: show reflect");
+
+        obj = ((StackInspector)StackInspector.Caller.class
+                             .getMethod("create", How.class)
+                             .invoke(null, How.CLASS));
+        assertEquals(obj.collectedFrames,
+                     List.of(StackInspector.class.getName()
+                                 +"::<init>",
+                             Constructor.class.getName()
+                                 +"::newInstance",
+                             Class.class.getName()
+                                 +"::newInstance",
+                             StackInspector.Caller.class.getName()
+                                 +"::create",
+                             Method.class.getName()
+                                 +"::invoke",
+                             ReflectionFrames.class.getName()
+                                 +"::testNewInstance"));
+        // Because Class.newInstance is not filtered, then the
+        // caller is Class.class
+        assertEquals(obj.cls, Class.class);
+        assertNotEquals(obj.filtered, 0);
+
+        // Calls the StackInspector.reflect method through reflection
+        // and check the frames collected in the StackInspector
+        // default constructor.
+        // The reflect method invokes the create method through
+        // reflection.
+        // The create method invokes StackInspector.class.newInstance().
+        // We should see all reflection frames, except the
+        // jdk.internal.reflect frames which we are filtering
+        // out in StackInspector::filter.
+        System.out.println("testNewInstance: reflect: show reflect");
+
+        obj = ((StackInspector)StackInspector.Caller.class
+                             .getMethod("reflect", How.class)
+                             .invoke(null, How.CLASS));
+        assertEquals(obj.collectedFrames,
+                     List.of(StackInspector.class.getName()
+                                 +"::<init>",
+                             Constructor.class.getName()
+                                 +"::newInstance",
+                             Class.class.getName()
+                                 +"::newInstance",
+                             StackInspector.Caller.class.getName()
+                                 +"::create",
+                             Method.class.getName()
+                                 +"::invoke",
+                             StackInspector.Caller.class.getName()
+                                 +"::reflect",
+                             Method.class.getName()
+                                 +"::invoke",
+                             ReflectionFrames.class.getName()
+                                 +"::testNewInstance"));
+
+        // Because Class.newInstance is not filtered, then the
+        // caller is Class.class
+        assertEquals(obj.cls, Class.class);
+        assertNotEquals(obj.filtered, 0);
+
+        // Calls the StackInspector.handle method through reflection
+        // and check the frames collected in the StackInspector
+        // default constructor.
+        // The handle method invokes the create method using
+        // MethodHandle.
+        // The create method invokes StackInspector.class.newInstance().
+        // We should see all reflection frames, except the
+        // jdk.internal.reflect frames which we are filtering
+        // out in StackInspector::filter.
+        System.out.println("testNewInstance: handle: show reflect");
+
+        obj = ((StackInspector)StackInspector.Caller.class
+                             .getMethod("handle", How.class)
+                             .invoke(null, How.CLASS));
+        assertEquals(obj.collectedFrames,
+                     List.of(StackInspector.class.getName()
+                                 +"::<init>",
+                             Constructor.class.getName()
+                                 +"::newInstance",
+                             Class.class.getName()
+                                 +"::newInstance",
+                             StackInspector.Caller.class.getName()
+                                 +"::create",
+                             // MethodHandle::invoke remains hidden
+                             StackInspector.Caller.class.getName()
+                                 +"::handle",
+                             Method.class.getName()
+                                 +"::invoke",
+                             ReflectionFrames.class.getName()
+                                 +"::testNewInstance"));
+
+        // Because Class.newInstance is not filtered, then the
+        // caller is Class.class
+        assertEquals(obj.cls, Class.class);
+        assertNotEquals(obj.filtered, 0);
+    }
+
+    @Test
+    public static void testGetCaller() throws Exception {
+        // Sets the default walker which hides reflection
+        // frames.
+        StackInspector.walker.set(StackInspector.walkerHide);
+
+        assertEquals(StackInspector.getCaller(), ReflectionFrames.class);
+        assertEquals(StackInspector.class.getMethod("getCaller").invoke(null),
+                     ReflectionFrames.class);
+
+        // Sets a non-default walker configured to show
+        // reflection frames
+        StackInspector.walker.set(StackInspector.walkerShow);
+
+        assertEquals(StackInspector.getCaller(), ReflectionFrames.class);
+        assertEquals(StackInspector.class.getMethod("getCaller").invoke(null),
+                     ReflectionFrames.class);
+    }
+
+    @Test
+    public static void testReflectCaller() throws Exception {
+        // Sets the default walker which hides reflection
+        // frames.
+        StackInspector.walker.set(StackInspector.walkerHide);
+
+        assertEquals(StackInspector.reflectCaller(), ReflectionFrames.class);
+        assertEquals(StackInspector.class.getMethod("reflectCaller").invoke(null),
+                     ReflectionFrames.class);
+
+        // Sets a non-default walker configured to show
+        // reflection frames
+        StackInspector.walker.set(StackInspector.walkerShow);
+
+        assertEquals(StackInspector.reflectCaller(), ReflectionFrames.class);
+        assertEquals(StackInspector.class.getMethod("reflectCaller").invoke(null),
+                     ReflectionFrames.class);
+    }
+
+    @Test
+    public static void testSupplyCaller() throws Exception {
+        // Sets the default walker which hides reflection
+        // frames.
+        StackInspector.walker.set(StackInspector.walkerHide);
+
+        assertEquals(StackInspector.supplyCaller(), ReflectionFrames.class);
+        assertEquals(StackInspector.class.getMethod("supplyCaller").invoke(null),
+                     ReflectionFrames.class);
+
+        // Sets a non-default walker configured to show
+        // reflection frames
+        StackInspector.walker.set(StackInspector.walkerShow);
+
+        assertEquals(StackInspector.supplyCaller(), ReflectionFrames.class);
+        assertEquals(StackInspector.class.getMethod("supplyCaller").invoke(null),
+                     ReflectionFrames.class);
+    }
+
+    @Test
+    public static void testHandleCaller() throws Exception {
+        // Sets the default walker which hides reflection
+        // frames.
+        StackInspector.walker.set(StackInspector.walkerHide);
+
+        assertEquals(StackInspector.handleCaller(), ReflectionFrames.class);
+        assertEquals(StackInspector.class.getMethod("handleCaller").invoke(null),
+                     ReflectionFrames.class);
+
+        // Sets a non-default walker configured to show
+        // reflection frames
+        StackInspector.walker.set(StackInspector.walkerShow);
+
+        assertEquals(StackInspector.handleCaller(), ReflectionFrames.class);
+        assertEquals(StackInspector.class.getMethod("handleCaller").invoke(null),
+                     ReflectionFrames.class);
+    }
+
+    static enum How { NEW, CONSTRUCTOR, CLASS};
+
+    /**
+     * An object that collect stack frames by walking the stack
+     * (and calling getCallerClass()) from within its constructor.
+     * For the purpose of this test, StackInspector objects are
+     * always created from the nested StackInspector.Caller class,
+     * which should therefore appear as the caller of the
+     * StackInspector constructor.
+     */
+    static class StackInspector {
+        static final StackWalker walkerHide =
+            StackWalker.getInstance(StackWalker.Option.RETAIN_CLASS_REFERENCE);
+        static final StackWalker walkerShow =
+            StackWalker.getInstance(EnumSet.of(
+                           StackWalker.Option.RETAIN_CLASS_REFERENCE,
+                           StackWalker.Option.SHOW_REFLECT_FRAMES));
+        final static ThreadLocal<StackWalker> walker = new ThreadLocal<>() {
+             protected StackWalker initialValue() {
+                 return walkerHide;
+             }
+        };
+
+        List<String> collectedFrames;
+        Class<?> cls = null;
+        boolean stop;
+        int filtered;
+        final boolean filterImplFrames;
+
+        public StackInspector() {
+            stop = false;
+            // if reflection frames are not hidden, we want to
+            // filter implementation frames before collecting
+            // to avoid depending on internal details.
+            filterImplFrames = walker.get() == walkerShow;
+            collectedFrames = walker.get().walk(this::parse);
+            cls = walker.get().getCallerClass();
+        }
+
+        public List<String> collectedFrames() {
+            return collectedFrames;
+        }
+
+        // The takeWhile method arrange for stopping frame collection
+        // as soon as a frame from ReflectionFrames.class is reached.
+        // The first such frame encountered is still included in the
+        // collected frames, but collection stops right after.
+        // This makes it possible to filter out anything above the
+        // the test method frame, such as frames from the test
+        // framework.
+        public boolean takeWhile(StackFrame f) {
+            if (stop) return false;
+            if (verbose) System.out.println("    " + f);
+            stop = stop || f.getDeclaringClass() == ReflectionFrames.class;
+            return true;
+        }
+
+        // filter out implementation frames to avoid depending
+        // on implementation details. If present, Class::newInstance,
+        // Method::invoke and Constructor::newInstance will
+        // still appear in the collected frames, which is
+        // sufficient for the purpose of the test.
+        // In the case where the StackWalker itself is supposed to
+        // filter the reflection frames, then this filter will always
+        // return true. This way, if such a reflection frame appears when
+        // it sjould have been filtered by StackWalker, it will make the
+        // test fail.
+        public boolean filter(StackFrame f) {
+            if (filterImplFrames &&
+                f.getClassName().startsWith("jdk.internal.reflect.")) {
+                filtered++;
+                return false;
+            }
+            if (!verbose) System.out.println("    " + f);
+            return true;
+        }
+
+        public String frame(StackFrame f) {
+            return f.getClassName() + "::" + f.getMethodName();
+        }
+
+        List<String> parse(Stream<StackFrame> s) {
+            return s.takeWhile(this::takeWhile)
+                    .filter(this::filter)
+                    .map(this::frame)
+                    .collect(Collectors.toList());
+        }
+
+        /**
+         * The Caller class is used to create instances of
+         * StackInspector, either direcltly, or throug reflection.
+         */
+        public static class Caller {
+            public static StackInspector create(How how) throws Exception {
+                switch(how) {
+                    case NEW: return new StackInspector();
+                    case CONSTRUCTOR: return StackInspector.class
+                        .getConstructor().newInstance();
+                    case CLASS: return StackInspector.class.newInstance();
+                    default: throw new AssertionError(String.valueOf(how));
+                }
+            }
+            public static StackInspector reflect(How how) throws Exception {
+                return (StackInspector) Caller.class.getMethod("create", How.class)
+                      .invoke(null, how);
+            }
+            public static StackInspector handle(How how) throws Exception {
+                Lookup lookup = MethodHandles.lookup();
+                MethodHandle mh = lookup.findStatic(Caller.class, "create",
+                        MethodType.methodType(StackInspector.class, How.class));
+                try {
+                    return (StackInspector) mh.invoke(how);
+                } catch (Error | Exception x) {
+                    throw x;
+                } catch(Throwable t) {
+                    throw new AssertionError(t);
+                }
+            }
+        }
+
+        public static Class<?> getCaller() throws Exception {
+            return walker.get().getCallerClass();
+        }
+
+        public static Class<?> reflectCaller() throws Exception {
+            return (Class<?>)StackWalker.class.getMethod("getCallerClass")
+                .invoke(walker.get());
+        }
+
+        public static Class<?> supplyCaller() throws Exception {
+            return ((Supplier<Class<?>>)StackInspector.walker.get()::getCallerClass).get();
+        }
+
+        public static Class<?> handleCaller() throws Exception {
+            Lookup lookup = MethodHandles.lookup();
+            MethodHandle mh = lookup.findVirtual(StackWalker.class, "getCallerClass",
+                    MethodType.methodType(Class.class));
+            try {
+                return (Class<?>) mh.invoke(walker.get());
+            } catch (Error | Exception x) {
+                throw x;
+            } catch(Throwable t) {
+                throw new AssertionError(t);
+            }
+        }
+    }
+}
--- a/jdk/test/java/lang/invoke/AccessControlTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/invoke/AccessControlTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012, 2017, 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
@@ -118,6 +118,8 @@
                 suffix = "/noaccess";
             else if (lookupModes == PUBLIC)
                 suffix = "/public";
+             else if (lookupModes == (PUBLIC|UNCONDITIONAL))
+                suffix = "/publicLookup";
             else if (lookupModes == (PUBLIC|MODULE))
                 suffix = "/module";
             else if (lookupModes == (PUBLIC|MODULE|PACKAGE))
@@ -140,23 +142,24 @@
          * [A2] However, the resulting {@code Lookup} object is guaranteed
          * to have no more access capabilities than the original.
          * In particular, access capabilities can be lost as follows:<ul>
-         * <li>[A3] If the new lookup class differs from the old one,
-         * protected members will not be accessible by virtue of inheritance.
+         * <li> [A3] If the old lookup class is in a named module, and the new
+         * lookup class is in a different module {@code M}, then no members, not
+         * even public members in {@code M}'s exported packages, will be accessible.
+         * The exception to this is when this lookup is publicLookup, in which case
+         * public access is not lost.
+         * <li> [A4] If the old lookup class is in an unnamed module, and the new
+         * lookup class is a different module then module access is lost.
+         * <li> [A5] If the new lookup class differs from the old one then UNCONDITIONAL
+         * is lost. If the new lookup class is not within the same package member as the
+         * old one, protected members will not be accessible by virtue of inheritance.
          * (Protected members may continue to be accessible because of package sharing.)
-         * <li>[A4] If the new lookup class is in a different package
-         * than the old one, protected and default (package) members will not be accessible.
-         * <li>[A5] If the new lookup class is not within the same package member
+         * <li> [A6] If the new lookup class is in a different package than the old one,
+         * protected and default (package) members will not be accessible.
+         * <li> [A7] If the new lookup class is not within the same package member
          * as the old one, private members will not be accessible.
-         * <li>[A6] If the new lookup class is not accessible to the old lookup class,
-         * using the original access modes,
+         * <li> [A8] If the new lookup class is not accessible to the old lookup class,
          * then no members, not even public members, will be accessible.
-         * <li>[A7] If the new lookup class for this {@code Lookup} is in the unnamed module,
-         * and the new lookup class is in a named module {@code M}, then no members in
-         * {@code M}'s non-exported packages will be accessible.
-         * <li>[A8] If the lookup for this {@code Lookup} is in a named module, and the
-         * new lookup class is in a different module, then no members, not even
-         * public members in {@code M}'s exported packages, will be accessible.
-         * [A8] (In all other cases, public members will continue to be accessible.)
+         * <li> [A9] (In all other cases, public members will continue to be accessible.)
          * </ul>
          * Other than the above cases, the new lookup will have the same
          * access capabilities as the original. [A10]
@@ -171,36 +174,35 @@
             boolean sameModule = (c1.getModule() == c2.getModule()) ||
                                  (!c1.getModule().isNamed() && !c2.getModule().isNamed());
             boolean samePackage = (c1.getClassLoader() == c2.getClassLoader() &&
-                                   packagePrefix(c1).equals(packagePrefix(c2)));
+                                   c1.getPackageName().equals(c2.getPackageName()));
             boolean sameTopLevel = (topLevelClass(c1) == topLevelClass(c2));
             boolean sameClass = (c1 == c2);
             assert(samePackage  || !sameTopLevel);
             assert(sameTopLevel || !sameClass);
-            boolean accessible = sameClass;  // [A6]
+            boolean accessible = sameClass;
             if ((m1 & PACKAGE) != 0)  accessible |= samePackage;
             if ((m1 & PUBLIC ) != 0)  accessible |= (c2.getModifiers() & PUBLIC) != 0;
             if (!sameModule) {
-                if (c1.getModule().isNamed()) {
-                    accessible = false;  // [A8]
+                if (c1.getModule().isNamed() && (m1 & UNCONDITIONAL) == 0) {
+                    accessible = false;  // [A3]
                 } else {
-                    // Different module; loose MODULE and lower access.
-                    changed |= (MODULE|PACKAGE|PRIVATE|PROTECTED);  // [A7]
+                    changed |= (MODULE|PACKAGE|PRIVATE|PROTECTED);    // [A3] [A4]
                 }
             }
             if (!accessible) {
                 // Different package and no access to c2; lose all access.
-                changed |= (PUBLIC|MODULE|PACKAGE|PRIVATE|PROTECTED);  // [A6]
+                changed |= (PUBLIC|MODULE|PACKAGE|PRIVATE|PROTECTED);  // [A8]
             }
             if (!samePackage) {
                 // Different package; loose PACKAGE and lower access.
-                changed |= (PACKAGE|PRIVATE|PROTECTED);  // [A4]
+                changed |= (PACKAGE|PRIVATE|PROTECTED);  // [A6]
             }
             if (!sameTopLevel) {
-                // Different top-level class.  Lose PRIVATE and lower access.
-                changed |= (PRIVATE|PROTECTED);  // [A5]
+                // Different top-level class.  Lose PRIVATE and PROTECTED access.
+                changed |= (PRIVATE|PROTECTED);  // [A5] [A7]
             }
             if (!sameClass) {
-                changed |= (PROTECTED);     // [A3]
+                changed |= (UNCONDITIONAL);     // [A5]
             } else {
                 assert(changed == 0);       // [A10] (no deprivation if same class)
             }
@@ -228,11 +230,10 @@
             Class<?> c1 = lookupClass();
             Class<?> c2 = m.getDeclaringClass();
 
-            // if the lookup class is in a loose module with PUBLIC access then
-            // public members of public types in all unnamed modules can be accessed
-            if (isLooseModule(c1.getModule())
+            // publicLookup has access to all public types/members of types in unnamed modules
+            if ((lookupModes & UNCONDITIONAL) != 0
                 && (lookupModes & PUBLIC) != 0
-                && (!c2.getModule().isNamed())
+                && !c2.getModule().isNamed()
                 && Modifier.isPublic(c2.getModifiers())
                 && Modifier.isPublic(m.getModifiers()))
                 return true;
@@ -261,17 +262,12 @@
             if (load && c2.getClassLoader() != null) {
                 if (c1.getClassLoader() == null) {
                     // not visible
-                return false;
-            }
-                if (c1 == publicLookup().lookupClass()) {
-                    // not visible as lookup class is defined by child of the boot loader
                     return false;
                 }
             }
 
-            // if the lookup class is in a loose module with PUBLIC access then
-            // public types in all unnamed modules can be accessed
-            if (isLooseModule(c1.getModule())
+            // publicLookup has access to all public types/members of types in unnamed modules
+            if ((lookupModes & UNCONDITIONAL) != 0
                 && (lookupModes & PUBLIC) != 0
                 && (!c2.getModule().isNamed())
                 && Modifier.isPublic(c2.getModifiers()))
@@ -295,11 +291,6 @@
             }
             return r;
         }
-
-        private boolean isLooseModule(Module m) {
-            ClassLoader cl = new ClassLoader() { };
-            return m.canRead(cl.getUnnamedModule());
-        }
     }
 
     private static Class<?> topLevelClass(Class<?> cls) {
@@ -311,14 +302,6 @@
         return c;
     }
 
-    private static String packagePrefix(Class<?> c) {
-        while (c.isArray())  c = c.getComponentType();
-        String s = c.getName();
-        assert(s.indexOf('/') < 0);
-        return s.substring(0, s.lastIndexOf('.')+1);
-    }
-
-
     private final TreeSet<LookupCase> CASES = new TreeSet<>();
     private final TreeMap<LookupCase,TreeSet<LookupCase>> CASE_EDGES = new TreeMap<>();
     private final ArrayList<ClassLoader> LOADERS = new ArrayList<>();
--- a/jdk/test/java/lang/invoke/DropLookupModeTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/invoke/DropLookupModeTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -65,6 +65,10 @@
         lookup = fullPowerLookup.dropLookupMode(PUBLIC);
         assertTrue(lookup.lookupClass() == lc);
         assertTrue(lookup.lookupModes() == 0);
+
+        lookup = fullPowerLookup.dropLookupMode(UNCONDITIONAL);
+        assertTrue(lookup.lookupClass() == lc);
+        assertTrue(lookup.lookupModes() == (PUBLIC|MODULE|PACKAGE|PRIVATE));
     }
 
     /**
@@ -108,7 +112,7 @@
     public void testPublicLookup() {
         final Lookup publicLookup = MethodHandles.publicLookup();
         final Class<?> lc = publicLookup.lookupClass();
-        assertTrue(publicLookup.lookupModes() == PUBLIC);
+        assertTrue(publicLookup.lookupModes() == (PUBLIC|UNCONDITIONAL));
 
         Lookup lookup = publicLookup.dropLookupMode(PRIVATE);
         assertTrue(lookup.lookupClass() == lc);
@@ -129,6 +133,10 @@
         lookup = publicLookup.dropLookupMode(PUBLIC);
         assertTrue(lookup.lookupClass() == lc);
         assertTrue(lookup.lookupModes() == 0);
+
+        lookup = publicLookup.dropLookupMode(UNCONDITIONAL);
+        assertTrue(lookup.lookupClass() == lc);
+        assertTrue(lookup.lookupModes() == PUBLIC);
     }
 
     @DataProvider(name = "badInput")
--- a/jdk/test/java/lang/invoke/LFCaching/LFMultiThreadCachingTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/invoke/LFCaching/LFMultiThreadCachingTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2014, 2017, 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
@@ -30,7 +30,7 @@
  * @library /lib/testlibrary/jsr292 /lib/testlibrary
  * @modules java.base/java.lang.invoke:open
  *          java.base/java.lang.ref:open
- *          jdk.management
+ *          java.management
  * @build TestMethods
  * @build LambdaFormTestCase
  * @build LFCachingTestCase
--- a/jdk/test/java/lang/invoke/LFCaching/LFSingleThreadCachingTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/invoke/LFCaching/LFSingleThreadCachingTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2014, 2017, 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
@@ -30,6 +30,7 @@
  * @library /lib/testlibrary/jsr292 /lib/testlibrary
  * @modules java.base/java.lang.ref:open
  *          java.base/java.lang.invoke:open
+ *          java.management
  * @build TestMethods
  * @build LambdaFormTestCase
  * @build LFCachingTestCase
--- a/jdk/test/java/lang/invoke/MethodHandles/privateLookupIn/Driver.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/invoke/MethodHandles/privateLookupIn/Driver.java	Wed Jul 05 22:52:01 2017 +0200
@@ -23,7 +23,7 @@
 
 /**
  * @test
- * @build test/* m1/* m2/* m3/*
+ * @build test/* m1/* m2/* m3/* Unnamed
  * @run testng/othervm test/p.PrivateLookupInTests
  * @summary Unit tests for MethodHandles.privateLookupIn
  */
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/invoke/MethodHandles/privateLookupIn/Unnamed.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,24 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+
+public class Unnamed { }
--- a/jdk/test/java/lang/invoke/MethodHandles/privateLookupIn/test/p/PrivateLookupInTests.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/invoke/MethodHandles/privateLookupIn/test/p/PrivateLookupInTests.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -126,6 +126,26 @@
         Object obj = mh.invokeExact();
     }
 
+    // test target class in unnamed module
+    public void testTargetClassInUnnamedModule() throws Throwable {
+        Class<?> clazz = Class.forName("Unnamed");
+        assertFalse(clazz.getModule().isNamed());
+
+        // thisModule does not read the unnamed module
+        Module thisModule = getClass().getModule();
+        assertFalse(thisModule.canRead(clazz.getModule()));
+        try {
+            MethodHandles.privateLookupIn(clazz, MethodHandles.lookup());
+            assertTrue(false);
+        } catch (IllegalAccessException expected) { }
+
+        // thisModule reads the unnamed module
+        thisModule.addReads(clazz.getModule());
+        Lookup lookup = MethodHandles.privateLookupIn(clazz, MethodHandles.lookup());
+        assertTrue(lookup.lookupClass() == clazz);
+        assertTrue(lookup.hasPrivateAccess());
+    }
+
     // test does not read m2, m2 opens p2 to test
     @Test(expectedExceptions = {IllegalAccessException.class})
     public void testCallerDoesNotRead() throws Throwable {
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/invoke/lambda/MetafactoryDescriptorTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,269 @@
+/*
+ * Copyright (c) 2017, 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
+ * @bug 8035776 8173587
+ * @summary metafactory should fail if instantiatedMethodType does not match sam/bridge descriptors
+ */
+import java.lang.invoke.*;
+import java.util.*;
+
+public class MetafactoryDescriptorTest {
+
+    static final MethodHandles.Lookup lookup = MethodHandles.lookup();
+
+    static MethodType mt(Class<?> ret, Class<?>... params) {
+        return MethodType.methodType(ret, params);
+    }
+
+    public interface I {}
+
+    public static class C {
+        public static void m_void(String arg) {}
+        public static boolean m_boolean(String arg) { return true; }
+        public static char m_char(String arg) { return 'x'; }
+        public static byte m_byte(String arg) { return 12; }
+        public static short m_short(String arg) { return 12; }
+        public static int m_int(String arg) { return 12; }
+        public static long m_long(String arg) { return 12; }
+        public static float m_float(String arg) { return 12; }
+        public static double m_double(String arg) { return 12; }
+        public static String m_String(String arg) { return ""; }
+        public static Integer m_Integer(String arg) { return 23; }
+        public static Object m_Object(String arg) { return new Object(); }
+
+        public static String n_boolean(boolean arg) { return ""; }
+        public static String n_char(char arg) { return ""; }
+        public static String n_byte(byte arg) { return ""; }
+        public static String n_short(short arg) { return ""; }
+        public static String n_int(int arg) { return ""; }
+        public static String n_long(long arg) { return ""; }
+        public static String n_float(float arg) { return ""; }
+        public static String n_double(double arg) { return ""; }
+        public static String n_String(String arg) { return ""; }
+        public static String n_Integer(Integer arg) { return ""; }
+        public static String n_Object(Object arg) { return ""; }
+
+        public static MethodHandle getM(Class<?> c) {
+            try {
+                return lookup.findStatic(C.class, "m_" + c.getSimpleName(), mt(c, String.class));
+            }
+            catch (NoSuchMethodException | IllegalAccessException e) {
+                throw new RuntimeException(e);
+            }
+        }
+
+        public static MethodHandle getN(Class<?> c) {
+            if (c == void.class) return null;
+            try {
+                return lookup.findStatic(C.class, "n_" + c.getSimpleName(), mt(String.class, c));
+            }
+            catch (NoSuchMethodException | IllegalAccessException e) {
+                throw new RuntimeException(e);
+            }
+        }
+
+    }
+
+    public static void main(String... args) {
+        Class<?>[] t = { void.class, boolean.class, char.class,
+                         byte.class, short.class, int.class, long.class, float.class, double.class,
+                         String.class, Integer.class, Object.class };
+
+        for (int i = 0; i < t.length; i++) {
+            MethodHandle m = C.getM(t[i]);
+            MethodHandle n = C.getN(t[i]); // null for void.class
+            for (int j = 0; j < t.length; j++) {
+                boolean correctRet = t[j].isAssignableFrom(t[i]) || conversions.contains(t[i], t[j]);
+                test(correctRet, m, mt(t[i], String.class), mt(t[j], String.class));
+                testBridge(correctRet, m, mt(t[i], String.class), mt(t[i], String.class),
+                           mt(t[j], Object.class));
+                testBridge(correctRet, m, mt(t[i], String.class), mt(t[i], String.class),
+                           mt(t[i], CharSequence.class), mt(t[j], Object.class));
+
+                if (t[i] != void.class && t[j] != void.class) {
+                    boolean correctParam = t[j].isAssignableFrom(t[i]);
+                    test(correctParam, n, mt(String.class, t[i]), mt(String.class, t[j]));
+                    testBridge(correctParam, n, mt(String.class, t[i]), mt(String.class, t[i]),
+                            mt(Object.class, t[j]));
+                    testBridge(correctParam, n, mt(String.class, t[i]), mt(String.class, t[i]),
+                            mt(CharSequence.class, t[i]), mt(Object.class, t[j]));
+                }
+
+            }
+        }
+    }
+
+    static void test(boolean correct, MethodHandle mh, MethodType instMT, MethodType samMT) {
+        tryMetafactory(correct, mh, instMT, samMT);
+        tryAltMetafactory(correct, mh, instMT, samMT);
+    }
+
+    static void testBridge(boolean correct, MethodHandle mh, MethodType instMT, MethodType samMT, MethodType... bridgeMTs) {
+        tryAltMetafactory(correct, mh, instMT, samMT, bridgeMTs);
+    }
+
+    static void tryMetafactory(boolean correct, MethodHandle mh, MethodType instMT, MethodType samMT) {
+        try {
+            LambdaMetafactory.metafactory(lookup, "run", mt(I.class),
+                                          samMT, mh, instMT);
+            if (!correct) {
+                throw new AssertionError("Unexpected linkage without error:" +
+                                         " impl=" + mh +
+                                         ", inst=" + instMT +
+                                         ", sam=" + samMT);
+            }
+        }
+        catch (LambdaConversionException e) {
+            if (correct) {
+                throw new AssertionError("Unexpected linkage error:" +
+                                         " e=" + e +
+                                         ", impl=" + mh +
+                                         ", inst=" + instMT +
+                                         ", sam=" + samMT);
+            }
+        }
+    }
+
+    static void tryAltMetafactory(boolean correct, MethodHandle mh, MethodType instMT, MethodType samMT,
+                                  MethodType... bridgeMTs) {
+        boolean bridge = bridgeMTs.length > 0;
+        Object[] args = new Object[bridge ? 5+bridgeMTs.length : 4];
+        args[0] = samMT;
+        args[1] = mh;
+        args[2] = instMT;
+        args[3] = bridge ? LambdaMetafactory.FLAG_BRIDGES : 0;
+        if (bridge) {
+            args[4] = bridgeMTs.length;
+            for (int i = 0; i < bridgeMTs.length; i++) args[5+i] = bridgeMTs[i];
+        }
+        try {
+            LambdaMetafactory.altMetafactory(lookup, "run", mt(I.class), args);
+            if (!correct) {
+                throw new AssertionError("Unexpected linkage without error:" +
+                                         " impl=" + mh +
+                                         ", inst=" + instMT +
+                                         ", sam=" + samMT +
+                                         ", bridges=" + Arrays.toString(bridgeMTs));
+            }
+        }
+        catch (LambdaConversionException e) {
+            if (correct) {
+                throw new AssertionError("Unexpected linkage error:" +
+                                         " e=" + e +
+                                         ", impl=" + mh +
+                                         ", inst=" + instMT +
+                                         ", sam=" + samMT +
+                                         ", bridges=" + Arrays.toString(bridgeMTs));
+            }
+        }
+    }
+
+    private static class ConversionTable {
+        private final Map<Class<?>, Set<Class<?>>> pairs = new HashMap<>();
+
+        public void put(Class<?> from, Class<?> to) {
+            Set<Class<?>> set = pairs.computeIfAbsent(from, f -> new HashSet<>());
+            set.add(to);
+        }
+
+        public boolean contains(Class<?> from, Class<?> to) {
+            return pairs.containsKey(from) && pairs.get(from).contains(to);
+        }
+    }
+
+    private static ConversionTable conversions = new ConversionTable();
+    static {
+        conversions.put(char.class, int.class);
+        conversions.put(char.class, long.class);
+        conversions.put(char.class, float.class);
+        conversions.put(char.class, double.class);
+        conversions.put(char.class, Character.class);
+        conversions.put(char.class, Object.class);
+        conversions.put(Character.class, char.class);
+        conversions.put(Character.class, int.class);
+        conversions.put(Character.class, long.class);
+        conversions.put(Character.class, float.class);
+        conversions.put(Character.class, double.class);
+
+        conversions.put(byte.class, short.class);
+        conversions.put(byte.class, int.class);
+        conversions.put(byte.class, long.class);
+        conversions.put(byte.class, float.class);
+        conversions.put(byte.class, double.class);
+        conversions.put(byte.class, Byte.class);
+        conversions.put(byte.class, Object.class);
+        conversions.put(Byte.class, byte.class);
+        conversions.put(Byte.class, short.class);
+        conversions.put(Byte.class, int.class);
+        conversions.put(Byte.class, long.class);
+        conversions.put(Byte.class, float.class);
+        conversions.put(Byte.class, double.class);
+
+        conversions.put(short.class, int.class);
+        conversions.put(short.class, long.class);
+        conversions.put(short.class, float.class);
+        conversions.put(short.class, double.class);
+        conversions.put(short.class, Short.class);
+        conversions.put(short.class, Object.class);
+        conversions.put(Short.class, short.class);
+        conversions.put(Short.class, int.class);
+        conversions.put(Short.class, long.class);
+        conversions.put(Short.class, float.class);
+        conversions.put(Short.class, double.class);
+
+        conversions.put(int.class, long.class);
+        conversions.put(int.class, float.class);
+        conversions.put(int.class, double.class);
+        conversions.put(int.class, Integer.class);
+        conversions.put(int.class, Object.class);
+        conversions.put(Integer.class, int.class);
+        conversions.put(Integer.class, long.class);
+        conversions.put(Integer.class, float.class);
+        conversions.put(Integer.class, double.class);
+
+        conversions.put(long.class, float.class);
+        conversions.put(long.class, double.class);
+        conversions.put(long.class, Long.class);
+        conversions.put(long.class, Object.class);
+        conversions.put(Long.class, long.class);
+        conversions.put(Long.class, float.class);
+        conversions.put(Long.class, double.class);
+
+        conversions.put(float.class, double.class);
+        conversions.put(float.class, Float.class);
+        conversions.put(float.class, Object.class);
+        conversions.put(Float.class, float.class);
+        conversions.put(Float.class, double.class);
+
+        conversions.put(double.class, Double.class);
+        conversions.put(double.class, Object.class);
+        conversions.put(Double.class, double.class);
+
+        conversions.put(boolean.class, Boolean.class);
+        conversions.put(boolean.class, Object.class);
+        conversions.put(Boolean.class, boolean.class);
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/invoke/lambda/MetafactoryMethodNameTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,197 @@
+/*
+ * Copyright (c) 2017, 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
+ * @bug 8173587
+ * @summary metafactory should fail if the method name is not legal
+ */
+import java.lang.invoke.*;
+import java.util.*;
+
+public class MetafactoryMethodNameTest {
+
+    public static void main(String... args) {
+        goodName("x");
+        goodName("xy");
+
+        goodName("]");
+        goodName("x]");
+        goodName("]y");
+        goodName("x]y");
+
+        goodName("&");
+        goodName("x&");
+        goodName("&y");
+        goodName("x&y");
+
+        badName(".");
+        badName("x.");
+        badName(".y");
+        badName("x.y");
+
+        badName(";");
+        badName("x;");
+        badName(";y");
+        badName("x;y");
+
+        badName("[");
+        badName("x[");
+        badName("[y");
+        badName("x[y");
+
+        badName("/");
+        badName("x/");
+        badName("/y");
+        badName("x/y");
+
+        badName("<");
+        badName("x<");
+        badName("<y");
+        badName("x<y");
+
+        badName(">");
+        badName("x>");
+        badName(">y");
+        badName("x>y");
+
+        badName("");
+        badName("<init>");
+        badName("<clinit>");
+    }
+
+    static MethodType mt(Class<?> ret, Class<?>... params) {
+        return MethodType.methodType(ret, params);
+    }
+
+    static MethodHandle smh(Class<?> c, String name, MethodType desc) {
+        try {
+            return MethodHandles.lookup().findStatic(c, name, desc);
+        } catch (ReflectiveOperationException e) {
+            throw new RuntimeException(e);
+        }
+    }
+
+    static Object[] arr(Object... args) {
+        return args;
+    }
+
+    public static class C {
+        public static void m() {}
+    }
+
+    public interface I {}
+
+    private static MethodHandles.Lookup lookup = MethodHandles.lookup();
+    private static MethodType toI = mt(I.class);
+    private static MethodType toVoid = mt(void.class);
+    private static MethodHandle mh = smh(C.class, "m", toVoid);
+    private static Class<?> lce = LambdaConversionException.class;
+
+    static void goodName(String name) {
+        succeedMFLinkage(lookup, name, toI, toVoid, mh, toVoid);
+        succeedAltMFLinkage(lookup, name, toI, arr(toVoid, mh, toVoid, LambdaMetafactory.FLAG_SERIALIZABLE));
+    }
+
+    static void badName(String name) {
+        failMFLinkage(lookup, name, toI, toVoid, mh, toVoid, lce);
+        failAltMFLinkage(lookup, name, toI, arr(toVoid, mh, toVoid, LambdaMetafactory.FLAG_SERIALIZABLE), lce);
+    }
+
+    static CallSite succeedMFLinkage(MethodHandles.Lookup lookup,
+                                    String name,
+                                    MethodType capType,
+                                    MethodType desc,
+                                    MethodHandle impl,
+                                    MethodType checked) {
+        try {
+            return LambdaMetafactory.metafactory(lookup, name, capType, desc, impl, checked);
+        } catch (Throwable t) {
+            String msg = String.format("Unexpected exception during linkage for metafactory(%s, %s, %s, %s, %s, %s)",
+                    lookup, name, capType, desc, impl, checked);
+            throw new AssertionError(msg, t);
+        }
+    }
+
+    static void failMFLinkage(MethodHandles.Lookup lookup,
+                              String name,
+                              MethodType capType,
+                              MethodType desc,
+                              MethodHandle impl,
+                              MethodType checked,
+                              Class<?> expectedExceptionType) {
+        try {
+            LambdaMetafactory.metafactory(lookup, name, capType, desc, impl, checked);
+        } catch (Throwable t) {
+            if (expectedExceptionType.isInstance(t)) {
+                return;
+            } else {
+                String msg = String.format("Unexpected exception: expected %s during linkage for metafactory(%s, %s, %s, %s, %s, %s)",
+                        expectedExceptionType.getName(),
+                        lookup, name, capType, desc, impl, checked);
+                throw new AssertionError(msg, t);
+            }
+        }
+        String msg = String.format("Unexpected success: expected %s during linkage for metafactory(%s, %s, %s, %s, %s, %s)",
+                expectedExceptionType.getName(),
+                lookup, name, capType, desc, impl, checked);
+        throw new AssertionError(msg);
+    }
+
+    static CallSite succeedAltMFLinkage(MethodHandles.Lookup lookup,
+                                        String name,
+                                        MethodType capType,
+                                        Object[] args) {
+        try {
+            return LambdaMetafactory.altMetafactory(lookup, name, capType, args);
+        } catch (Throwable t) {
+            String msg = String.format("Unexpected exception during linkage for metafactory(%s, %s, %s, %s)",
+                    lookup, name, capType, Arrays.asList(args));
+            throw new AssertionError(msg, t);
+        }
+    }
+
+    static void failAltMFLinkage(MethodHandles.Lookup lookup,
+                                 String name,
+                                 MethodType capType,
+                                 Object[] args,
+                                 Class<?> expectedExceptionType) {
+        try {
+            LambdaMetafactory.altMetafactory(lookup, name, capType, args);
+        } catch (Throwable t) {
+            if (expectedExceptionType.isInstance(t)) {
+                return;
+            } else {
+                String msg = String.format("Unexpected exception: expected %s during linkage for metafactory(%s, %s, %s, %s)",
+                        expectedExceptionType.getName(),
+                        lookup, name, capType, Arrays.asList(args));
+                throw new AssertionError(msg, t);
+            }
+        }
+        String msg = String.format("Unexpected success: expected %s during linkage for metafactory(%s, %s, %s, %s)",
+                expectedExceptionType.getName(),
+                lookup, name, capType, Arrays.asList(args));
+        throw new AssertionError(msg);
+    }
+
+}
--- a/jdk/test/java/lang/invoke/lambda/MetafactorySamReturnTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,167 +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.
- *
- * 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
- * @bug 8035776
- * @summary metafactory should fail if impl return does not match sam/bridge returns
- */
-import java.lang.invoke.*;
-import java.util.Arrays;
-import static java.lang.invoke.MethodType.methodType;
-
-public class MetafactorySamReturnTest {
-
-    static final MethodHandles.Lookup lookup = MethodHandles.lookup();
-
-    public interface I {}
-
-    public static class C {
-        public static void m_void(String arg) {}
-        public static boolean m_boolean(String arg) { return true; }
-        public static char m_char(String arg) { return 'x'; }
-        public static byte m_byte(String arg) { return 12; }
-        public static short m_short(String arg) { return 12; }
-        public static int m_int(String arg) { return 12; }
-        public static long m_long(String arg) { return 12; }
-        public static float m_float(String arg) { return 12; }
-        public static double m_double(String arg) { return 12; }
-        public static String m_String(String arg) { return ""; }
-        public static Integer m_Integer(String arg) { return 23; }
-        public static Object m_Object(String arg) { return new Object(); }
-
-        public static MethodHandle getMH(Class<?> c) {
-            try {
-                return lookup.findStatic(C.class, "m_" + c.getSimpleName(), methodType(c, String.class));
-            }
-            catch (NoSuchMethodException | IllegalAccessException e) {
-                throw new RuntimeException(e);
-            }
-        }
-    }
-
-    public static void main(String... args) {
-        Class<?>[] t = { void.class, boolean.class, char.class,
-                         byte.class, short.class, int.class, long.class, float.class, double.class,
-                         String.class, Integer.class, Object.class };
-
-        for (int i = 0; i < t.length; i++) {
-            MethodHandle mh = C.getMH(t[i]);
-            for (int j = 0; j < t.length; j++) {
-                // TEMPORARY EXCEPTIONS
-                if (t[j] == void.class) continue;
-                if (t[i].isPrimitive() && t[j] == Object.class) continue;
-                if (t[i] == char.class && (t[j] == int.class || t[j] == long.class || t[j] == float.class || t[j] == double.class)) continue;
-                if (t[i] == byte.class && (t[j] == short.class || t[j] == int.class || t[j] == long.class || t[j] == float.class || t[j] == double.class)) continue;
-                if (t[i] == short.class && (t[j] == int.class || t[j] == long.class || t[j] == float.class || t[j] == double.class)) continue;
-                if (t[i] == int.class && (t[j] == long.class || t[j] == float.class || t[j] == double.class)) continue;
-                if (t[i] == long.class && (t[j] == float.class || t[j] == double.class)) continue;
-                if (t[i] == float.class && t[j] == double.class) continue;
-                if (t[i] == int.class && t[j] == Integer.class) continue;
-                if (t[i] == Integer.class && (t[j] == int.class || t[j] == long.class || t[j] == float.class || t[j] == double.class)) continue;
-                // END TEMPORARY EXCEPTIONS
-                boolean correct = (t[i].isPrimitive() || t[j].isPrimitive())
-                                  ? t[i] == t[j]
-                                  : t[j].isAssignableFrom(t[i]);
-                MethodType mti = methodType(t[i], String.class);
-                MethodType mtiCS = methodType(t[i], CharSequence.class);
-                MethodType mtj = methodType(t[j], String.class);
-                MethodType mtjObj = methodType(t[j], Object.class);
-                test(correct, mh, mti, mtj);
-                testBridge(correct, mh, mti, mti, mtjObj);
-                testBridge(correct, mh, mti, mti, mtiCS, mtjObj);
-            }
-        }
-    }
-
-    static void test(boolean correct, MethodHandle mh, MethodType instMT, MethodType samMT) {
-        tryMetafactory(correct, mh, new Class<?>[]{}, instMT, samMT);
-        tryAltMetafactory(correct, mh, new Class<?>[]{}, instMT, samMT);
-    }
-
-    static void testBridge(boolean correct, MethodHandle mh, MethodType instMT, MethodType samMT, MethodType... bridgeMTs) {
-        tryAltMetafactory(correct, mh, new Class<?>[]{}, instMT, samMT, bridgeMTs);
-    }
-
-    static void tryMetafactory(boolean correct, MethodHandle mh, Class<?>[] captured,
-                               MethodType instMT, MethodType samMT) {
-        try {
-            LambdaMetafactory.metafactory(lookup, "run", methodType(I.class, captured),
-                                          samMT, mh, instMT);
-            if (!correct) {
-                throw new AssertionError("Uncaught linkage error:" +
-                                         " impl=" + mh +
-                                         ", captured=" + Arrays.toString(captured) +
-                                         ", inst=" + instMT +
-                                         ", sam=" + samMT);
-            }
-        }
-        catch (LambdaConversionException e) {
-            if (correct) {
-                throw new AssertionError("Unexpected linkage error:" +
-                                         " e=" + e +
-                                         ", impl=" + mh +
-                                         ", captured=" + Arrays.toString(captured) +
-                                         ", inst=" + instMT +
-                                         ", sam=" + samMT);
-            }
-        }
-    }
-
-    static void tryAltMetafactory(boolean correct, MethodHandle mh, Class<?>[] captured,
-                                  MethodType instMT, MethodType samMT, MethodType... bridgeMTs) {
-        boolean bridge = bridgeMTs.length > 0;
-        Object[] args = new Object[bridge ? 5+bridgeMTs.length : 4];
-        args[0] = samMT;
-        args[1] = mh;
-        args[2] = instMT;
-        args[3] = bridge ? LambdaMetafactory.FLAG_BRIDGES : 0;
-        if (bridge) {
-            args[4] = bridgeMTs.length;
-            for (int i = 0; i < bridgeMTs.length; i++) args[5+i] = bridgeMTs[i];
-        }
-        try {
-            LambdaMetafactory.altMetafactory(lookup, "run", methodType(I.class, captured), args);
-            if (!correct) {
-                throw new AssertionError("Uncaught linkage error:" +
-                                         " impl=" + mh +
-                                         ", captured=" + Arrays.toString(captured) +
-                                         ", inst=" + instMT +
-                                         ", sam=" + samMT +
-                                         ", bridges=" + Arrays.toString(bridgeMTs));
-            }
-        }
-        catch (LambdaConversionException e) {
-            if (correct) {
-                throw new AssertionError("Unexpected linkage error:" +
-                                         " e=" + e +
-                                         ", impl=" + mh +
-                                         ", captured=" + Arrays.toString(captured) +
-                                         ", inst=" + instMT +
-                                         ", sam=" + samMT +
-                                         ", bridges=" + Arrays.toString(bridgeMTs));
-            }
-        }
-    }
-
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/invoke/modules/Driver.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,29 @@
+/*
+ * Copyright (c) 2017, 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
+ * @build m1/* m2/* Unnamed
+ * @run testng/othervm m1/p1.Main
+ * @summary Basic test case for module access checks and Lookup.in.
+ */
--- a/jdk/test/java/lang/invoke/modules/ModuleAccessControlTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,81 +0,0 @@
-/*
- * Copyright (c) 2015, 2016, 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.
- */
-
-import java.nio.file.Path;
-import java.nio.file.Paths;
-import java.util.Arrays;
-import java.util.List;
-
-import static jdk.testlibrary.ProcessTools.executeTestJava;
-
-import org.testng.annotations.BeforeTest;
-import org.testng.annotations.Test;
-import static org.testng.Assert.*;
-
-/**
- * @test
- * @library /lib/testlibrary
- * @modules jdk.compiler
- * @build CompilerUtils jdk.testlibrary.*
- * @run testng ModuleAccessControlTest
- * @summary Driver for testing module access checking by MethodHandles.Lookup
- */
-
-public class ModuleAccessControlTest {
-
-    private static final String TEST_SRC = System.getProperty("test.src");
-
-    private static final Path SRC_DIR = Paths.get(TEST_SRC, "src");
-    private static final Path MODS_DIR = Paths.get("mods");
-
-    // the names of the modules in this test
-    private static List<String> modules = Arrays.asList("m1", "m2");
-
-
-    /**
-     * Compiles all modules used by the test
-     */
-    @BeforeTest
-    public void compileAll() throws Exception {
-        for (String mn : modules) {
-            Path msrc = SRC_DIR.resolve(mn);
-            assertTrue(CompilerUtils
-                .compile(msrc, MODS_DIR, "--module-source-path", SRC_DIR.toString()));
-        }
-    }
-
-    /**
-     * Launch the test
-     */
-    @Test
-    public void runTest() throws Exception {
-        int exitValue = executeTestJava("--module-path", MODS_DIR.toString(),
-                                        "-m", "m1/p1.Main")
-                .outputTo(System.out)
-                .errorTo(System.out)
-                .getExitValue();
-
-        assertTrue(exitValue == 0);
-    }
-
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/invoke/modules/Unnamed.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,24 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+
+public class Unnamed { }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/invoke/modules/m1/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,27 @@
+/*
+ * 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.
+ *
+ * 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.
+ */
+module m1 {
+    requires m2;
+    requires testng;
+    exports p1;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/invoke/modules/m1/p1/Main.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,367 @@
+/*
+ * Copyright (c) 2015, 2017, 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.
+ */
+
+package p1;
+
+import java.lang.invoke.MethodHandle;
+import java.lang.invoke.MethodHandles;
+import java.lang.invoke.MethodHandles.Lookup;
+import java.lang.invoke.MethodType;
+import java.lang.reflect.Layer;
+import java.lang.reflect.Module;
+
+import static java.lang.invoke.MethodHandles.Lookup.*;
+
+import org.testng.annotations.BeforeTest;
+import org.testng.annotations.Test;
+import static org.testng.Assert.*;
+
+/**
+ * Basic test case for module access checks and Lookup.in.
+ */
+
+@Test
+public class Main {
+
+    private Class<?> p1_Type1;        // m1, exported
+    private Class<?> p2_Type2;        // m1, not exported
+    private Class<?> q1_Type1;        // m2, exported
+    private Class<?> q2_Type2;        // m2, not exported
+    private Class<?> x500NameClass;   // java.base, not exported
+    private Class<?> unnamedClass;    // class in unnamed module
+
+    @BeforeTest
+    public void setup() throws Exception {
+        try {
+            p1_Type1 = Class.forName("p1.Type1");
+            p2_Type2 = Class.forName("p2.Type2");
+            q1_Type1 = Class.forName("q1.Type1");
+            q2_Type2 = Class.forName("q2.Type2");
+            x500NameClass = Class.forName("sun.security.x509.X500Name");
+            unnamedClass = Class.forName("Unnamed");
+        } catch (ClassNotFoundException e) {
+            throw new AssertionError(e);
+        }
+
+        // check setup
+        Module m1 = Layer.boot().findModule("m1").orElse(null);
+        assertNotNull(m1);
+        assertTrue(p1_Type1.getModule() == m1);
+        assertTrue(p2_Type2.getModule() == m1);
+        assertTrue(m1.isExported("p1"));
+        assertFalse(m1.isExported("p2"));
+
+        Module m2 = Layer.boot().findModule("m2").orElse(null);
+        assertNotNull(m2);
+        assertTrue(q1_Type1.getModule() == m2);
+        assertTrue(q2_Type2.getModule() == m2);
+        assertTrue(m2.isExported("q1"));
+        assertFalse(m2.isExported("q2"));
+
+        Module unnamedModule = unnamedClass.getModule();
+        assertFalse(unnamedModule.isNamed());
+
+        // m1 needs to read unnamed module
+        Main.class.getModule().addReads(unnamedModule);
+    }
+
+    /**
+     * MethodHandles.lookup()
+     *
+     * [A0] has module access
+     * [A1] can access all public types in m1
+     * [A2] can access public types in packages exported by modules that m1 reads
+     * [A3] cannot access public types in non-exported modules of modules that m1 reads
+     */
+    public void testLookup() throws Exception {
+        Lookup lookup = MethodHandles.lookup();
+        assertTrue((lookup.lookupModes() & MODULE) == MODULE); // [A0]
+
+        // m1
+        findConstructor(lookup, p1_Type1, void.class); // [A1]
+        findConstructor(lookup, p2_Type2, void.class); // [A1]
+
+        // m2
+        findConstructor(lookup, q1_Type1, void.class); // [A2]
+        findConstructorExpectingIAE(lookup, q2_Type2, void.class); // [A3]
+
+        // java.base
+        findConstructor(lookup, Object.class, void.class); // [A2]
+        findConstructorExpectingIAE(lookup, x500NameClass, void.class, String.class); // [A3]
+
+        // unnamed
+        findConstructor(lookup, unnamedClass, void.class);  // [A3]
+    }
+
+    /**
+     * Hop to lookup class in the same module
+     *
+     * [A0] module and public access is not lost
+     */
+    public void testToSameModule() throws Exception {
+        Lookup lookup = MethodHandles.lookup().in(p2_Type2);
+        assertTrue(lookup.lookupModes() == (MODULE|PUBLIC)); // [A0]
+
+        // m1
+        findConstructor(lookup, p1_Type1, void.class);
+        findConstructor(lookup, p2_Type2, void.class);
+
+        // m2
+        findConstructor(lookup, q1_Type1, void.class);
+        findConstructorExpectingIAE(lookup, q2_Type2, void.class);
+
+        // java.base
+        findConstructor(lookup, Object.class, void.class);
+        findConstructorExpectingIAE(lookup, x500NameClass, void.class, String.class);
+
+        // unnamed
+        findConstructor(lookup, unnamedClass, void.class);
+    }
+
+    /**
+     * Hop to lookup class in another named module
+     *
+     * [A0] has no access
+     */
+    public void testFromNamedToNamedModule() throws Exception {
+        Lookup lookup = MethodHandles.lookup().in(q1_Type1);
+        assertTrue(lookup.lookupModes() == 0); // [A0]
+
+        // m1
+        findConstructorExpectingIAE(lookup, p1_Type1, void.class);
+        findConstructorExpectingIAE(lookup, p2_Type2, void.class);
+
+        // m2
+        findConstructorExpectingIAE(lookup, q1_Type1, void.class);
+        findConstructorExpectingIAE(lookup, q2_Type2, void.class);
+
+        // java.base
+        findConstructorExpectingIAE(lookup, Object.class, void.class);
+        findConstructorExpectingIAE(lookup, x500NameClass, void.class, String.class);
+
+        // unnamed
+        findConstructorExpectingIAE(lookup, unnamedClass, void.class);
+    }
+
+    /**
+     * Hop to lookup class in an unnamed module
+     *
+     * [A0] has no access
+     */
+    public void testFromNamedToUnnamedModule() throws Exception {
+        Lookup lookup = MethodHandles.lookup().in(unnamedClass);
+        assertTrue(lookup.lookupModes() == 0); // [A0]
+
+        // m1
+        findConstructorExpectingIAE(lookup, p1_Type1, void.class);
+        findConstructorExpectingIAE(lookup, p2_Type2, void.class);
+
+        // m2
+        findConstructorExpectingIAE(lookup, q1_Type1, void.class);
+        findConstructorExpectingIAE(lookup, q2_Type2, void.class);
+
+        // java.base
+        findConstructorExpectingIAE(lookup, Object.class, void.class);
+        findConstructorExpectingIAE(lookup, x500NameClass, void.class, String.class);
+
+        // unnamed
+        findConstructorExpectingIAE(lookup, unnamedClass, void.class);
+    }
+
+    /**
+     * Hop from unnamed to named module.
+     *
+     * [A0] retains PUBLIC access
+     */
+    public void testFromUnnamedToNamedModule() throws Exception {
+        Lookup lookup = MethodHandles.lookup();
+        lookup = MethodHandles.privateLookupIn(unnamedClass, lookup).in(p1_Type1);
+        assertTrue(lookup.lookupModes() == PUBLIC); // A0
+
+        // m1
+        findConstructor(lookup, p1_Type1, void.class);
+        findConstructorExpectingIAE(lookup, p2_Type2, void.class);
+
+        // m2
+        findConstructor(lookup, q1_Type1, void.class);
+        findConstructorExpectingIAE(lookup, q2_Type2, void.class);
+
+        // java.base
+        findConstructor(lookup, Object.class, void.class);
+        findConstructorExpectingIAE(lookup, x500NameClass, void.class, String.class);
+
+        // unnamed
+        findConstructor(lookup, unnamedClass, void.class);
+    }
+
+    /**
+     * MethodHandles.publicLookup()
+     *
+     * [A0] has PUBLIC|UNCONDITIONAL access
+     */
+    public void testPublicLookup() throws Exception {
+        Lookup lookup = MethodHandles.publicLookup();
+        assertTrue(lookup.lookupModes() == (PUBLIC|UNCONDITIONAL)); // A0
+
+        // m1
+        findConstructor(lookup, p1_Type1, void.class);
+        findConstructorExpectingIAE(lookup, p2_Type2, void.class);
+
+        // m2
+        findConstructor(lookup, q1_Type1, void.class);
+        findConstructorExpectingIAE(lookup, q2_Type2, void.class);
+
+        // java.base
+        findConstructor(lookup, Object.class, void.class);
+        findConstructorExpectingIAE(lookup, x500NameClass, void.class, String.class);
+
+        // unnamed
+        findConstructor(lookup, unnamedClass, void.class);
+    }
+
+    /**
+     * Hop from publicLookup to accessible type in java.base
+     */
+    public void testPublicLookupToBaseModule() throws Exception {
+        Lookup lookup = MethodHandles.publicLookup().in(String.class);
+        assertTrue(lookup.lookupModes() == PUBLIC); // A0
+
+        // m1
+        findConstructorExpectingIAE(lookup, p1_Type1, void.class);
+        findConstructorExpectingIAE(lookup, p2_Type2, void.class);
+
+        // m2
+        findConstructorExpectingIAE(lookup, q1_Type1, void.class);
+        findConstructorExpectingIAE(lookup, q2_Type2, void.class);
+
+        // java.base
+        findConstructor(lookup, Object.class, void.class);
+        findConstructorExpectingIAE(lookup, x500NameClass, void.class, String.class);
+
+        // unnamed
+        findConstructorExpectingIAE(lookup, unnamedClass, void.class);
+    }
+
+
+    /**
+     * Hop from publicLookup to accessible type in named module.
+     *
+     * [A0] has PUBLIC access
+     */
+    public void testPublicLookupToAccessibleTypeInNamedModule() throws Exception {
+        Lookup lookup = MethodHandles.publicLookup().in(p1_Type1);
+        assertTrue(lookup.lookupModes() == PUBLIC); // A0
+
+        // m1
+        findConstructor(lookup, p1_Type1, void.class);
+        findConstructorExpectingIAE(lookup, p2_Type2, void.class);
+
+        // m2
+        findConstructor(lookup, q1_Type1, void.class);
+        findConstructorExpectingIAE(lookup, q2_Type2, void.class);
+
+        // java.base
+        findConstructor(lookup, Object.class, void.class);
+        findConstructorExpectingIAE(lookup, x500NameClass, void.class, String.class);
+
+        // unnamed
+        findConstructor(lookup, unnamedClass, void.class);
+    }
+
+    /**
+     * Teleport from publicLookup to inaccessible type in named module.
+     *
+     * [A0] has no access
+     */
+    public void testPublicLookupToInaccessibleTypeInNamedModule() throws Exception {
+        Lookup lookup = MethodHandles.publicLookup().in(p2_Type2);
+        assertTrue(lookup.lookupModes() == 0); // A0
+
+        // m1
+        findConstructorExpectingIAE(lookup, p1_Type1, void.class);
+        findConstructorExpectingIAE(lookup, p2_Type2, void.class);
+
+        // m2
+        findConstructorExpectingIAE(lookup, q1_Type1, void.class);
+        findConstructorExpectingIAE(lookup, q2_Type2, void.class);
+
+        // java.base
+        findConstructorExpectingIAE(lookup, Object.class, void.class);
+        findConstructorExpectingIAE(lookup, x500NameClass, void.class, String.class);
+
+        // unnamed
+        findConstructorExpectingIAE(lookup, unnamedClass, void.class);
+    }
+
+    /**
+     * Teleport from publicLookup to public type in unnamed module
+     *
+     * [A0] has PUBLIC access
+     */
+    public void testPublicLookupToUnnamedModule() throws Exception {
+        Lookup lookup = MethodHandles.publicLookup().in(unnamedClass);
+        assertTrue(lookup.lookupModes() == PUBLIC); // A0
+
+        // m1
+        findConstructor(lookup, p1_Type1, void.class);
+        findConstructorExpectingIAE(lookup, p2_Type2, void.class);
+
+        // m2
+        findConstructor(lookup, q1_Type1, void.class);
+        findConstructorExpectingIAE(lookup, q2_Type2, void.class);
+
+        // java.base
+        findConstructor(lookup, Object.class, void.class);
+        findConstructorExpectingIAE(lookup, x500NameClass, void.class, String.class);
+
+        // unnamed
+        findConstructor(lookup, unnamedClass, void.class);
+    }
+
+    /**
+     * Invokes Lookup findConstructor with a method type constructored from the
+     * given return and parameter types, expecting IllegalAccessException to be
+     * thrown.
+     */
+    static void findConstructorExpectingIAE(Lookup lookup,
+                                            Class<?> clazz,
+                                            Class<?> rtype,
+                                            Class<?>... ptypes) throws Exception {
+        try {
+            findConstructor(lookup, clazz, rtype, ptypes);
+            assertTrue(false);
+        } catch (IllegalAccessException expected) { }
+    }
+
+    /**
+     * Invokes Lookup findConstructor with a method type constructored from the
+     * given return and parameter types.
+     */
+    static MethodHandle findConstructor(Lookup lookup,
+                                        Class<?> clazz,
+                                        Class<?> rtype,
+                                        Class<?>... ptypes) throws Exception {
+        MethodType mt = MethodType.methodType(rtype, ptypes);
+        return lookup.findConstructor(clazz, mt);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/invoke/modules/m1/p1/Type1.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,27 @@
+/*
+ * 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.
+ *
+ * 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 p1;
+
+public class Type1 {
+    public Type1() { }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/invoke/modules/m1/p2/Type2.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,27 @@
+/*
+ * 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.
+ *
+ * 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 p2;
+
+public class Type2 {
+    public Type2() { }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/invoke/modules/m2/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,25 @@
+/*
+ * 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.
+ *
+ * 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.
+ */
+module m2 {
+    exports q1;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/invoke/modules/m2/q1/Type1.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,27 @@
+/*
+ * 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.
+ *
+ * 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 q1;
+
+public class Type1 {
+    public Type1() { }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/invoke/modules/m2/q2/Type2.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,27 @@
+/*
+ * 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.
+ *
+ * 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 q2;
+
+public class Type2 {
+    public Type2() { }
+}
--- a/jdk/test/java/lang/invoke/modules/src/m1/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,26 +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.
- *
- * 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.
- */
-module m1 {
-    requires m2;
-    exports p1;
-}
--- a/jdk/test/java/lang/invoke/modules/src/m1/p1/Main.java	Mon Feb 13 11:57:56 2017 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,225 +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.
- *
- * 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 p1;
-
-import java.lang.invoke.MethodHandle;
-import java.lang.invoke.MethodHandles;
-import java.lang.invoke.MethodHandles.Lookup;
-import java.lang.invoke.MethodType;
-
-/**
- * Basic test case for module access check, supplements AccessControlTest.
- *
- * The tests consists of two modules:
- *
- * module m1 { requires m2; exports p1; }
- * module m2 { exports q1; }
- *
- * Both modules read java.base (as every module reads java.base)
- *
- * module m1 has public types in packages p1 and p2, p2 is not exported.
- * module m2 has public types in packages q1 and q2, q2 is not exported.
- */
-
-public class Main {
-
-    static final int MODULE = Lookup.MODULE;
-
-    // Use Class.forName to get classes for test because some
-    // are not accessible at compile-time
-
-    static final Class<?> p1_Type1;        // m1, exported
-    static final Class<?> p2_Type2;        // m1, not exported
-    static final Class<?> q1_Type1;        // m2, exported, m1 reads m2
-    static final Class<?> q2_Type2;        // m2, not exported, m1 reads m2
-    static final Class<?> x500NameClass;   // java.base, not exported
-
-    static {
-        try {
-            p1_Type1 = Class.forName("p1.Type1");
-            p2_Type2 = Class.forName("p2.Type2");
-            q1_Type1 = Class.forName("q1.Type1");
-            q2_Type2 = Class.forName("q2.Type2");
-            x500NameClass = Class.forName("sun.security.x509.X500Name");
-        } catch (ClassNotFoundException e) {
-            throw new AssertionError(e);
-        }
-    }
-
-    public static void main(String[] args) throws Exception {
-        Lookup lookup, lookup2;
-
-        /**
-         * MethodHandles.lookup()
-         * has module access [A0]
-         * can access all public types in m1 [A1]
-         * can access public types in packages exported by modules that m1 reads [A2]
-         * cannot access public types in non-exported modules of modules that m1 reads [A3]
-         */
-        lookup = MethodHandles.lookup();
-        assertTrue((lookup.lookupModes() & MODULE) == MODULE); // [A0]
-        findConstructor(lookup, p1_Type1, void.class); // [A1]
-        findConstructor(lookup, p2_Type2, void.class); // [A1]
-        findConstructor(lookup, q1_Type1, void.class); // [A2]
-        findConstructorExpectingIAE(lookup, q2_Type2, void.class); // [A3]
-        findConstructor(lookup, Object.class, void.class); // [A2]
-        findConstructorExpectingIAE(lookup, x500NameClass, void.class, String.class); // [A3]
-
-        /**
-         * Teleport from MethodHandles.lookup() to lookup class in the same module
-         * module access is retained [A0]
-         * can access all public types in m1 [A1]
-         * can access public types in packages exported by modules that m1 reads [A2]
-         * cannot access public types in non-exported modules of modules that m1 reads [A3]
-         */
-        lookup2 = lookup.in(p2_Type2);
-        assertTrue((lookup2.lookupModes() & MODULE) == MODULE); // [A0]
-        findConstructor(lookup2, p1_Type1, void.class); // [A1]
-        findConstructor(lookup2, p2_Type2, void.class); // [A1]
-        findConstructor(lookup2, q1_Type1, void.class); // [A2]
-        findConstructorExpectingIAE(lookup2, q2_Type2, void.class); // [A3]
-        findConstructor(lookup2, Object.class, void.class); // [A2]
-        findConstructorExpectingIAE(lookup2, x500NameClass, void.class, String.class); // [A3]
-
-        /**
-         * Teleport from MethodHandles.lookup() to lookup class in another named module
-         * has no access [A0]
-         */
-        lookup2 = lookup.in(Object.class);
-        assertTrue(lookup2.lookupModes() == 0); // [A0]
-        findConstructorExpectingIAE(lookup2, Object.class, void.class);  // [A0]
-
-        /**
-         * Teleport from MethodHandles.lookup() to lookup class in an unnamed module
-         * has no access [A0]
-         */
-        Class<?> c = MethodHandles.publicLookup().lookupClass();
-        assertTrue(!c.getModule().isNamed());
-        lookup2 = lookup.in(c);
-        assertTrue(lookup2.lookupModes() == 0); // [A0]
-        findConstructorExpectingIAE(lookup2, Object.class, void.class);
-
-        /**
-         * MethodHandles.publicLookup()
-         * has no module access [A0]
-         * can access public types in exported packages [A1]
-         * cannot access public types in non-exported packages [A2]
-         */
-        lookup = MethodHandles.publicLookup();
-        assertTrue((lookup.lookupModes() & MODULE) == 0); // [A0]
-        findConstructor(lookup, p1_Type1, void.class); // [A1]
-        findConstructorExpectingIAE(lookup, p2_Type2, void.class); // [A1]
-        findConstructor(lookup, q1_Type1, void.class); // [A1]
-        findConstructorExpectingIAE(lookup, q2_Type2, void.class); // [A2]
-        findConstructor(lookup, Object.class, void.class); // [A1]
-        findConstructorExpectingIAE(lookup, x500NameClass, void.class); // [A2]
-
-        /**
-         * Teleport from MethodHandles.publicLookup() to lookup class in java.base
-         * has no module access [A0]
-         * can access public types in packages exported by java.base [A1]
-         * cannot access public types in non-exported packages [A2]
-         * no access to types in other named modules [A3]
-         */
-        lookup2 = lookup.in(Object.class);
-        assertTrue((lookup2.lookupModes() & MODULE) == 0); // [A0]
-        findConstructor(lookup2, String.class, void.class); // [A1]
-        findConstructorExpectingIAE(lookup2, x500NameClass, void.class, String.class); // [A2]
-        findConstructorExpectingIAE(lookup2, p1_Type1, void.class); // [A3]
-        findConstructorExpectingIAE(lookup2, q1_Type1, void.class); // [A3]
-
-        /**
-         * Teleport from MethodHandles.publicLookup() to lookup class in m1
-         * has no module access [A0]
-         * can access public types in packages exported by m1, m2 and java.base [A1]
-         * cannot access public types is non-exported packages [A2]
-         */
-        lookup2 = lookup.in(p1_Type1);
-        assertTrue((lookup2.lookupModes() & MODULE) == 0); // [A0]
-        findConstructor(lookup2, p1_Type1, void.class);  // [A1]
-        findConstructor(lookup2, q1_Type1, void.class);  // [A1]
-        findConstructor(lookup2, Object.class, void.class);  // [A1]
-        findConstructorExpectingIAE(lookup, p2_Type2, void.class); // [A2]
-        findConstructorExpectingIAE(lookup, q2_Type2, void.class); // [A2]
-        findConstructorExpectingIAE(lookup2, x500NameClass, void.class, String.class); // [A2]
-
-        /**
-         * Teleport from MethodHandles.publicLookup() to lookup class in m2
-         * has no module access [A0]
-         * can access public types in packages exported by m2 and java.base [A1]
-         * cannot access public types is non-exported packages or modules that m2 does
-         *   not read [A2]
-         */
-        lookup2 = lookup.in(q1_Type1);
-        assertTrue((lookup2.lookupModes() & MODULE) == 0); // [A0]
-        findConstructor(lookup2, q1_Type1, void.class); // [A1]
-        findConstructor(lookup2, Object.class, void.class); // [A1]
-        findConstructorExpectingIAE(lookup2, p1_Type1, void.class); // [A2]
-        findConstructorExpectingIAE(lookup, q2_Type2, void.class); // [A2]
-        findConstructorExpectingIAE(lookup2, x500NameClass, void.class, String.class);  // [A2]
-
-        /**
-         * Teleport from MethodHandles.publicLookup() to lookup class that is not
-         * in an exported package, should get no access [A0]
-         */
-        lookup2 = lookup.in(p2_Type2);
-        assertTrue(lookup2.lookupModes()  == 0); // [A0]
-        findConstructorExpectingIAE(lookup, q2_Type2, void.class); // [A0]
-    }
-
-    /**
-     * Invokes Lookup findConstructor with a method type constructored from the
-     * given return and parameter types, expecting IllegalAccessException to be
-     * thrown.
-     */
-    static MethodHandle findConstructorExpectingIAE(Lookup lookup,
-                                                    Class<?> clazz,
-                                                    Class<?> rtype,
-                                                    Class<?>... ptypes) throws Exception {
-        try {
-            findConstructor(lookup, clazz, rtype, ptypes);
-            throw new RuntimeException("IllegalAccessError expected");
-        } catch (IllegalAccessException expected) {
-            return null;
-        }
-    }
-
-    /**
-     * Invokes Lookup findConstructor with a method type constructored from the
-     * given return and parameter types.
-     */
-    static MethodHandle findConstructor(Lookup lookup,
-                                        Class<?> clazz,
-                                        Class<?> rtype,
-                                        Class<?>... ptypes) throws Exception {
-        MethodType mt = MethodType.methodType(rtype, ptypes);
-        return lookup.findConstructor(clazz, mt);
-    }
-
-    static void assertTrue(boolean condition) {
-        if (!condition)
-            throw new RuntimeException();
-    }
-
-}
--- a/jdk/test/java/lang/invoke/modules/src/m1/p1/Type1.java	Mon Feb 13 11:57:56 2017 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,27 +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.
- *
- * 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 p1;
-
-public class Type1 {
-    public Type1() { }
-}
--- a/jdk/test/java/lang/invoke/modules/src/m1/p2/Type2.java	Mon Feb 13 11:57:56 2017 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,27 +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.
- *
- * 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 p2;
-
-public class Type2 {
-    public Type2() { }
-}
--- a/jdk/test/java/lang/invoke/modules/src/m2/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,25 +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.
- *
- * 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.
- */
-module m2 {
-    exports q1;
-}
--- a/jdk/test/java/lang/invoke/modules/src/m2/q1/Type1.java	Mon Feb 13 11:57:56 2017 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,27 +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.
- *
- * 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 q1;
-
-public class Type1 {
-    public Type1() { }
-}
--- a/jdk/test/java/lang/invoke/modules/src/m2/q2/Type2.java	Mon Feb 13 11:57:56 2017 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,27 +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.
- *
- * 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 q2;
-
-public class Type2 {
-    public Type2() { }
-}
--- a/jdk/test/java/lang/management/ManagementFactory/DefaultManagementProviderTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/management/ManagementFactory/DefaultManagementProviderTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -26,6 +26,7 @@
  * @bug 8151099
  * @summary Verify platform MXBeans initialized properly with java.management
  *          module only. No other management provider
+ * @modules java.management
  * @run main/othervm --limit-modules=java.management DefaultManagementProviderTest
  */
 import java.lang.management.ManagementFactory;
--- a/jdk/test/java/lang/module/AutomaticModulesTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/module/AutomaticModulesTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2017, 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
@@ -33,10 +33,10 @@
 import java.lang.module.Configuration;
 import java.lang.module.FindException;
 import java.lang.module.ModuleDescriptor;
-import java.lang.module.ModuleDescriptor.Exports;
 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.module.ResolvedModule;
 import java.lang.reflect.Layer;
 import java.lang.reflect.Module;
@@ -137,6 +137,7 @@
         assertTrue(mref.isPresent(), mn + " not found");
 
         ModuleDescriptor descriptor = mref.get().descriptor();
+        assertTrue(descriptor.isAutomatic());
         assertEquals(descriptor.name(), mn);
         if (vs == null) {
             assertFalse(descriptor.version().isPresent());
@@ -175,17 +176,14 @@
         assertTrue(mref.isPresent(), "m not found");
 
         ModuleDescriptor descriptor = mref.get().descriptor();
+        assertTrue(descriptor.isAutomatic());
 
         assertTrue(descriptor.packages().size() == 2);
         assertTrue(descriptor.packages().contains("p"));
         assertTrue(descriptor.packages().contains("q"));
 
-        Set<String> exports = descriptor.exports().stream()
-                .map(Exports::source)
-                .collect(Collectors.toSet());
-        assertTrue(exports.size() == 2);
-        assertTrue(exports.contains("p"));
-        assertTrue(exports.contains("q"));
+        assertTrue(descriptor.exports().isEmpty());
+        assertTrue(descriptor.opens().isEmpty());
     }
 
     /**
@@ -201,15 +199,13 @@
         assertTrue(mref.isPresent(), "m not found");
 
         ModuleDescriptor descriptor = mref.get().descriptor();
+        assertTrue(descriptor.isAutomatic());
 
         assertTrue(descriptor.packages().size() == 1);
         assertTrue(descriptor.packages().contains("p"));
 
-        Set<String> exports = descriptor.exports().stream()
-                .map(Exports::source)
-                .collect(Collectors.toSet());
-        assertTrue(exports.size() == 1);
-        assertTrue(exports.contains("p"));
+        assertTrue(descriptor.exports().isEmpty());
+        assertTrue(descriptor.opens().isEmpty());
     }
 
     /**
@@ -229,10 +225,10 @@
         assertTrue(mref.isPresent(), "m not found");
 
         ModuleDescriptor descriptor = mref.get().descriptor();
+        assertTrue(descriptor.isAutomatic());
 
-        assertTrue(descriptor.packages().size() == 2);
+        assertTrue(descriptor.packages().size() == 1);
         assertTrue(descriptor.packages().contains("p"));
-        assertTrue(descriptor.packages().contains("p.resources"));
     }
 
     /**
@@ -254,9 +250,17 @@
         String provider = "p.S1";
 
         Path tmpdir = Files.createTempDirectory(USER_DIR, "tmp");
+
+        // provider class
+        Path providerClass = tmpdir.resolve(provider.replace('.', '/') + ".class");
+        Files.createDirectories(providerClass.getParent());
+        Files.createFile(providerClass);
+
+        // services configuration file
         Path services = tmpdir.resolve("META-INF").resolve("services");
         Files.createDirectories(services);
         Files.write(services.resolve(service), Set.of(provider));
+
         Path dir = Files.createTempDirectory(USER_DIR, "mods");
         JarUtils.createJarFile(dir.resolve("m.jar"), tmpdir);
 
@@ -314,7 +318,7 @@
 
                 // service type         provider type
                 { "p.S",                "-" },
-                { "p.S",                ".S1" },
+                { "p.S",                "p..S1" },
                 { "p.S",                "S1." },
         };
     }
@@ -324,13 +328,41 @@
      * values or names.
      */
     @Test(dataProvider = "badproviders", expectedExceptions = FindException.class)
-    public void testBadProvideNames(String service, String provider)
+    public void testBadProviderNames(String service, String provider)
         throws IOException
     {
         Path tmpdir = Files.createTempDirectory(USER_DIR, "tmp");
+
+        // provider class
+        Path providerClass = tmpdir.resolve(provider.replace('.', '/') + ".class");
+        Files.createDirectories(providerClass.getParent());
+        Files.createFile(providerClass);
+
+        // services configuration file
         Path services = tmpdir.resolve("META-INF").resolve("services");
         Files.createDirectories(services);
         Files.write(services.resolve(service), Set.of(provider));
+
+        Path dir = Files.createTempDirectory(USER_DIR, "mods");
+        JarUtils.createJarFile(dir.resolve("m.jar"), tmpdir);
+
+        // should throw FindException
+        ModuleFinder.of(dir).findAll();
+    }
+
+    /**
+     * Test JAR file with META-INF/services configuration file listing a
+     * provider that is not in the module.
+     */
+    @Test(expectedExceptions = FindException.class)
+    public void testMissingProviderPackage() throws IOException {
+        Path tmpdir = Files.createTempDirectory(USER_DIR, "tmp");
+
+        // services configuration file
+        Path services = tmpdir.resolve("META-INF").resolve("services");
+        Files.createDirectories(services);
+        Files.write(services.resolve("p.S"), Set.of("q.P"));
+
         Path dir = Files.createTempDirectory(USER_DIR, "mods");
         JarUtils.createJarFile(dir.resolve("m.jar"), tmpdir);
 
@@ -352,7 +384,8 @@
         attrs.put(Attributes.Name.MAIN_CLASS, mainClass);
 
         Path dir = Files.createTempDirectory(USER_DIR, "mods");
-        createDummyJarFile(dir.resolve("m.jar"), man);
+        String entry = mainClass.replace('.', '/') + ".class";
+        createDummyJarFile(dir.resolve("m.jar"), man, entry);
 
         ModuleFinder finder = ModuleFinder.of(dir);
 
@@ -366,20 +399,21 @@
     }
 
 
-    // Main-Class files that do not map to a legal Java identifier
+    // Main-Class files that do not map to a legal qualified type name
     @DataProvider(name = "badmainclass")
     public Object[][] createBadMainClass() {
         return new Object[][]{
 
+            { "Main",        null },
+            { "p..Main",     null },
             { "p-.Main",     null },
-            { ".Main",       null }
 
         };
     }
 
     /**
-     * Test that a JAR file with a Main-Class attribute that is not a valid
-     * Java identifier
+     * Test that a JAR file with a Main-Class attribute that is not a qualified
+     * type name.
      */
     @Test(dataProvider = "badmainclass", expectedExceptions = FindException.class)
     public void testBadMainClass(String mainClass, String ignore) throws IOException {
@@ -389,6 +423,24 @@
         attrs.put(Attributes.Name.MAIN_CLASS, mainClass);
 
         Path dir = Files.createTempDirectory(USER_DIR, "mods");
+        String entry = mainClass.replace('.', '/') + ".class";
+        createDummyJarFile(dir.resolve("m.jar"), man, entry);
+
+        // should throw FindException
+        ModuleFinder.of(dir).findAll();
+    }
+
+    /**
+     * Test that a JAR file with a Main-Class attribute that is not in the module
+     */
+    @Test(expectedExceptions = FindException.class)
+    public void testMissingMainClassPackage() throws IOException {
+        Manifest man = new Manifest();
+        Attributes attrs = man.getMainAttributes();
+        attrs.put(Attributes.Name.MANIFEST_VERSION, "1.0.0");
+        attrs.put(Attributes.Name.MAIN_CLASS, "p.Main");
+
+        Path dir = Files.createTempDirectory(USER_DIR, "mods");
         createDummyJarFile(dir.resolve("m.jar"), man);
 
         // should throw FindException
@@ -405,7 +457,7 @@
      */
     public void testConfiguration1() throws Exception {
         ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("a")
+            = ModuleDescriptor.newModule("a")
                 .requires("b")
                 .requires("c")
                 .requires("java.base")
@@ -465,13 +517,13 @@
      */
     public void testInConfiguration2() throws IOException {
         ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("a")
+            = ModuleDescriptor.newModule("a")
                 .requires("b")
                 .requires("java.base")
                 .build();
 
         ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("b")
+            = ModuleDescriptor.newModule("b")
                 .requires("c")
                 .requires("java.base")
                 .build();
@@ -538,13 +590,13 @@
      */
     public void testInConfiguration3() throws IOException {
         ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("a")
+            = ModuleDescriptor.newModule("a")
                 .requires("b")
                 .requires("java.base")
                 .build();
 
         ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("b")
+            = ModuleDescriptor.newModule("b")
                 .requires(Set.of(Modifier.TRANSITIVE), "c")
                 .requires("java.base")
                 .build();
@@ -609,11 +661,67 @@
 
 
     /**
+     * Basic test of a configuration created with automatic modules
+     *   a requires b* and c*
+     *   b* contains p
+     *   c* contains p
+     */
+    @Test(expectedExceptions = { ResolutionException.class })
+    public void testDuplicateSuppliers1() throws IOException {
+        ModuleDescriptor descriptor
+            = ModuleDescriptor.newModule("a")
+                .requires("b")
+                .requires("c")
+                .build();
+
+        // c and d are automatic modules with the same package
+        Path dir = Files.createTempDirectory(USER_DIR, "mods");
+        createDummyJarFile(dir.resolve("b.jar"), "p/T.class");
+        createDummyJarFile(dir.resolve("c.jar"), "p/T.class");
+
+        // module finder locates 'a' and the modules in the directory
+        ModuleFinder finder
+            = ModuleFinder.compose(ModuleUtils.finderOf(descriptor),
+                                   ModuleFinder.of(dir));
+
+        Configuration parent = Layer.boot().configuration();
+        resolve(parent, finder, "a");
+    }
+
+
+    /**
+     * Basic test of a configuration created with automatic modules
+     *   a contains p, requires b*
+     *   b* contains p
+     */
+    @Test(expectedExceptions = { ResolutionException.class })
+    public void testDuplicateSuppliers2() throws IOException {
+        ModuleDescriptor descriptor
+            = ModuleDescriptor.newModule("a")
+                .packages(Set.of("p"))
+                .requires("b")
+                .build();
+
+        // c and d are automatic modules with the same package
+        Path dir = Files.createTempDirectory(USER_DIR, "mods");
+        createDummyJarFile(dir.resolve("b.jar"), "p/T.class");
+
+        // module finder locates 'a' and the modules in the directory
+        ModuleFinder finder
+            = ModuleFinder.compose(ModuleUtils.finderOf(descriptor),
+                                   ModuleFinder.of(dir));
+
+        Configuration parent = Layer.boot().configuration();
+        resolve(parent, finder, "a");
+    }
+
+
+    /**
      * Basic test of Layer containing automatic modules
      */
     public void testInLayer() throws IOException {
         ModuleDescriptor descriptor
-            = ModuleDescriptor.module("a")
+            = ModuleDescriptor.newModule("a")
                 .requires("b")
                 .requires("c")
                 .build();
@@ -664,7 +772,7 @@
 
         // test miscellaneous methods
         assertTrue(m.isAutomatic());
-        assertFalse(m.isSynthetic());
+        assertFalse(m.modifiers().contains(ModuleDescriptor.Modifier.SYNTHETIC));
         assertFalse(m.osName().isPresent());
         assertFalse(m.osArch().isPresent());
         assertFalse(m.osVersion().isPresent());
@@ -672,12 +780,12 @@
 
 
     /**
-     * Invokes parent.resolveRequires to resolve the given root modules.
+     * Invokes parent.resolve to resolve the given root modules.
      */
     static Configuration resolve(Configuration parent,
                                  ModuleFinder finder,
                                  String... roots) {
-        return parent.resolveRequires(finder, ModuleFinder.of(), Set.of(roots));
+        return parent.resolve(finder, ModuleFinder.of(), Set.of(roots));
     }
 
     /**
--- a/jdk/test/java/lang/module/ConfigurationTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/module/ConfigurationTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2014, 2017, 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
@@ -24,23 +24,26 @@
 /**
  * @test
  * @library /lib/testlibrary
+ * @modules java.base/jdk.internal.misc
  * @build ConfigurationTest ModuleUtils
  * @run testng ConfigurationTest
  * @summary Basic tests for java.lang.module.Configuration
  */
 
 import java.lang.module.Configuration;
+import java.lang.module.FindException;
 import java.lang.module.ModuleDescriptor;
+import java.lang.module.ModuleDescriptor.Builder;
 import java.lang.module.ModuleDescriptor.Requires;
 import java.lang.module.ModuleFinder;
 import java.lang.module.ResolutionException;
 import java.lang.module.ResolvedModule;
 import java.lang.reflect.Layer;
-import java.util.HashSet;
 import java.util.List;
 import java.util.Optional;
 import java.util.Set;
 
+import jdk.internal.misc.SharedSecrets;
 import org.testng.annotations.DataProvider;
 import org.testng.annotations.Test;
 import static org.testng.Assert.*;
@@ -48,30 +51,35 @@
 @Test
 public class ConfigurationTest {
 
+    /**
+     * Creates a "non-strict" builder for building a module. This allows the
+     * test the create ModuleDescriptor objects that do not require java.base.
+     */
+    private static ModuleDescriptor.Builder newBuilder(String mn) {
+        return SharedSecrets.getJavaLangModuleAccess()
+                .newModuleBuilder(mn, false, Set.of());
+    }
 
     /**
      * Basic test of resolver
      *     m1 requires m2, m2 requires m3
      */
     public void testBasic() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .requires("m2")
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires("m3")
                 .build();
 
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .build();
 
         ModuleFinder finder
             = ModuleUtils.finderOf(descriptor1, descriptor2, descriptor3);
 
-        Configuration cf = resolveRequires(finder, "m1");
+        Configuration cf = resolve(finder, "m1");
 
         assertTrue(cf.modules().size() == 3);
 
@@ -110,24 +118,21 @@
      */
     public void testRequiresTransitive1() {
         // m1 requires m2, m2 requires transitive m3
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .requires("m2")
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires(Set.of(Requires.Modifier.TRANSITIVE), "m3")
                 .build();
 
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .build();
 
         ModuleFinder finder
             = ModuleUtils.finderOf(descriptor1, descriptor2, descriptor3);
 
-        Configuration cf = resolveRequires(finder, "m1");
+        Configuration cf = resolve(finder, "m1");
 
         assertTrue(cf.modules().size() == 3);
 
@@ -167,18 +172,16 @@
 
         // cf1: m1 and m2, m2 requires transitive m1
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires(Set.of(Requires.Modifier.TRANSITIVE), "m1")
                 .build();
 
         ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1, descriptor2);
 
-        Configuration cf1 = resolveRequires(finder1, "m2");
+        Configuration cf1 = resolve(finder1, "m2");
 
         assertTrue(cf1.modules().size() == 2);
         assertTrue(cf1.findModule("m1").isPresent());
@@ -196,14 +199,13 @@
 
         // cf2: m3, m3 requires m2
 
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .requires("m2")
                 .build();
 
         ModuleFinder finder2 = ModuleUtils.finderOf(descriptor3);
 
-        Configuration cf2 = resolveRequires(cf1, finder2, "m3");
+        Configuration cf2 = resolve(cf1, finder2, "m3");
 
         assertTrue(cf2.modules().size() == 1);
         assertTrue(cf2.findModule("m1").isPresent());  // in parent
@@ -231,13 +233,11 @@
 
         // cf1: m1
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
-                .build();
+        ModuleDescriptor descriptor1 = newBuilder("m1").build();
 
         ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1);
 
-        Configuration cf1 = resolveRequires(finder1, "m1");
+        Configuration cf1 = resolve(finder1, "m1");
 
         assertTrue(cf1.modules().size() == 1);
         assertTrue(cf1.findModule("m1").isPresent());
@@ -250,19 +250,17 @@
 
         // cf2: m2, m3: m2 requires transitive m1, m3 requires m2
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires(Set.of(Requires.Modifier.TRANSITIVE), "m1")
                 .build();
 
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .requires("m2")
                 .build();
 
         ModuleFinder finder2 = ModuleUtils.finderOf(descriptor2, descriptor3);
 
-        Configuration cf2 = resolveRequires(cf1, finder2, "m3");
+        Configuration cf2 = resolve(cf1, finder2, "m3");
 
         assertTrue(cf2.modules().size() == 2);
         assertTrue(cf2.findModule("m1").isPresent());   // in parent
@@ -297,13 +295,11 @@
 
         // cf1: m1
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
-                .build();
+        ModuleDescriptor descriptor1 = newBuilder("m1").build();
 
         ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1);
 
-        Configuration cf1 = resolveRequires(finder1, "m1");
+        Configuration cf1 = resolve(finder1, "m1");
 
         assertTrue(cf1.modules().size() == 1);
         assertTrue(cf1.findModule("m1").isPresent());
@@ -316,14 +312,13 @@
 
         // cf2: m2 requires transitive m1
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires(Set.of(Requires.Modifier.TRANSITIVE), "m1")
                 .build();
 
         ModuleFinder finder2 = ModuleUtils.finderOf(descriptor2);
 
-        Configuration cf2 = resolveRequires(cf1, finder2, "m2");
+        Configuration cf2 = resolve(cf1, finder2, "m2");
 
         assertTrue(cf2.modules().size() == 1);
         assertTrue(cf2.findModule("m1").isPresent());  // in parent
@@ -340,14 +335,13 @@
 
         // cf3: m3 requires m2
 
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .requires("m2")
                 .build();
 
         ModuleFinder finder3 = ModuleUtils.finderOf(descriptor3);
 
-        Configuration cf3 = resolveRequires(cf2, finder3, "m3");
+        Configuration cf3 = resolve(cf2, finder3, "m3");
 
         assertTrue(cf3.modules().size() == 1);
         assertTrue(cf3.findModule("m1").isPresent());  // in parent
@@ -376,18 +370,16 @@
 
         // cf1: m1, m2 requires transitive m1
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires(Set.of(Requires.Modifier.TRANSITIVE), "m1")
                 .build();
 
         ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1, descriptor2);
 
-        Configuration cf1 = resolveRequires(finder1, "m2");
+        Configuration cf1 = resolve(finder1, "m2");
 
         assertTrue(cf1.modules().size() == 2);
         assertTrue(cf1.findModule("m1").isPresent());
@@ -408,20 +400,18 @@
 
         // cf2: m3 requires transitive m2, m4 requires m3
 
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .requires(Set.of(Requires.Modifier.TRANSITIVE), "m2")
                 .build();
 
-        ModuleDescriptor descriptor4
-            = ModuleDescriptor.module("m4")
+        ModuleDescriptor descriptor4 = newBuilder("m4")
                 .requires("m3")
                 .build();
 
 
         ModuleFinder finder2 = ModuleUtils.finderOf(descriptor3, descriptor4);
 
-        Configuration cf2 = resolveRequires(cf1, finder2, "m3", "m4");
+        Configuration cf2 = resolve(cf1, finder2, "m3", "m4");
 
         assertTrue(cf2.modules().size() == 2);
         assertTrue(cf2.findModule("m1").isPresent());   // in parent
@@ -456,28 +446,24 @@
      * - Configuration cf3(cf1,cf2): m4 requires m2, m3
      */
     public void testRequiresTransitive6() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires(Set.of(Requires.Modifier.TRANSITIVE), "m1")
                 .build();
 
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .requires(Set.of(Requires.Modifier.TRANSITIVE), "m1")
                 .build();
 
-        ModuleDescriptor descriptor4
-            = ModuleDescriptor.module("m4")
+        ModuleDescriptor descriptor4 = newBuilder("m4")
                 .requires("m2")
                 .requires("m3")
                 .build();
 
         ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1, descriptor2);
-        Configuration cf1 = resolveRequires(finder1, "m2");
+        Configuration cf1 = resolve(finder1, "m2");
         assertTrue(cf1.modules().size() == 2);
         assertTrue(cf1.findModule("m1").isPresent());
         assertTrue(cf1.findModule("m2").isPresent());
@@ -485,7 +471,7 @@
         assertTrue(cf1.parents().get(0) == Configuration.empty());
 
         ModuleFinder finder2 = ModuleUtils.finderOf(descriptor1, descriptor3);
-        Configuration cf2 = resolveRequires(finder2, "m3");
+        Configuration cf2 = resolve(finder2, "m3");
         assertTrue(cf2.modules().size() == 2);
         assertTrue(cf2.findModule("m3").isPresent());
         assertTrue(cf2.findModule("m1").isPresent());
@@ -493,7 +479,7 @@
         assertTrue(cf2.parents().get(0) == Configuration.empty());
 
         ModuleFinder finder3 = ModuleUtils.finderOf(descriptor4);
-        Configuration cf3 = Configuration.resolveRequires(finder3,
+        Configuration cf3 = Configuration.resolve(finder3,
                 List.of(cf1, cf2),
                 ModuleFinder.of(),
                 Set.of("m4"));
@@ -522,14 +508,13 @@
      *     resolve m1
      */
     public void testRequiresStatic1() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .requires(Set.of(Requires.Modifier.STATIC), "m2")
                 .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1);
 
-        Configuration cf = resolveRequires(finder, "m1");
+        Configuration cf = resolve(finder, "m1");
 
         assertTrue(cf.modules().size() == 1);
 
@@ -545,18 +530,16 @@
      *     resolve m1
      */
     public void testRequiresStatic2() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .requires(Set.of(Requires.Modifier.STATIC), "m2")
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1, descriptor2);
 
-        Configuration cf = resolveRequires(finder, "m1");
+        Configuration cf = resolve(finder, "m1");
 
         assertTrue(cf.modules().size() == 1);
 
@@ -572,18 +555,16 @@
      *     resolve m1, m2
      */
     public void testRequiresStatic3() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .requires(Set.of(Requires.Modifier.STATIC), "m2")
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1, descriptor2);
 
-        Configuration cf = resolveRequires(finder, "m1", "m2");
+        Configuration cf = resolve(finder, "m1", "m2");
 
         assertTrue(cf.modules().size() == 2);
 
@@ -604,25 +585,22 @@
      *     m3
      */
     public void testRequiresStatic4() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .requires("m2")
                 .requires("m3")
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires(Set.of(Requires.Modifier.STATIC), "m3")
                 .build();
 
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .build();
 
         ModuleFinder finder
-                = ModuleUtils.finderOf(descriptor1, descriptor2, descriptor3);
-
-        Configuration cf = resolveRequires(finder, "m1");
+            = ModuleUtils.finderOf(descriptor1, descriptor2, descriptor3);
+
+        Configuration cf = resolve(finder, "m1");
 
         assertTrue(cf.modules().size() == 3);
 
@@ -648,31 +626,28 @@
      * - Configuration cf2: m3 requires m1, requires static m2
      */
     public void testRequiresStatic5() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .build();
 
         ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1, descriptor2);
 
-        Configuration cf1 = resolveRequires(finder1, "m1", "m2");
+        Configuration cf1 = resolve(finder1, "m1", "m2");
 
         assertTrue(cf1.modules().size() == 2);
         assertTrue(cf1.findModule("m1").isPresent());
         assertTrue(cf1.findModule("m2").isPresent());
 
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .requires("m1")
                 .requires(Set.of(Requires.Modifier.STATIC), "m2")
                 .build();
 
         ModuleFinder finder2 = ModuleUtils.finderOf(descriptor3);
 
-        Configuration cf2 = resolveRequires(cf1, finder2, "m3");
+        Configuration cf2 = resolve(cf1, finder2, "m3");
 
         assertTrue(cf2.modules().size() == 1);
         assertTrue(cf2.findModule("m3").isPresent());
@@ -694,26 +669,24 @@
      * - Configuration cf2: m3 requires m1, requires static m2
      */
     public void testRequiresStatic6() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .build();
 
         ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1);
 
-        Configuration cf1 = resolveRequires(finder1, "m1");
+        Configuration cf1 = resolve(finder1, "m1");
 
         assertTrue(cf1.modules().size() == 1);
         assertTrue(cf1.findModule("m1").isPresent());
 
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .requires("m1")
                 .requires(Set.of(Requires.Modifier.STATIC), "m2")
                 .build();
 
         ModuleFinder finder2 = ModuleUtils.finderOf(descriptor3);
 
-        Configuration cf2 = resolveRequires(cf1, finder2, "m3");
+        Configuration cf2 = resolve(cf1, finder2, "m3");
 
         assertTrue(cf2.modules().size() == 1);
         assertTrue(cf2.findModule("m3").isPresent());
@@ -735,21 +708,19 @@
     public void testRequiresStatic7() {
         ModuleDescriptor descriptor1 = null;  // not observable
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires(Set.of(Requires.Modifier.TRANSITIVE,
                                 Requires.Modifier.STATIC),
                          "m1")
                 .build();
 
-        ModuleDescriptor descriptor3
-                = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .requires("m2")
                 .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor2, descriptor3);
 
-        Configuration cf = resolveRequires(finder, "m3");
+        Configuration cf = resolve(finder, "m3");
 
         assertTrue(cf.modules().size() == 2);
         assertTrue(cf.findModule("m2").isPresent());
@@ -770,8 +741,7 @@
     public void testRequiresStatic8() {
         ModuleDescriptor descriptor1 = null;  // not observable
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires(Set.of(Requires.Modifier.TRANSITIVE,
                                 Requires.Modifier.STATIC),
                         "m1")
@@ -779,21 +749,20 @@
 
         ModuleFinder finder1 = ModuleUtils.finderOf(descriptor2);
 
-        Configuration cf1 = resolveRequires(finder1, "m2");
+        Configuration cf1 = resolve(finder1, "m2");
 
         assertTrue(cf1.modules().size() == 1);
         assertTrue(cf1.findModule("m2").isPresent());
         ResolvedModule m2 = cf1.findModule("m2").get();
         assertTrue(m2.reads().isEmpty());
 
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .requires("m2")
                 .build();
 
         ModuleFinder finder2 = ModuleUtils.finderOf(descriptor3);
 
-        Configuration cf2 = resolveRequires(cf1, finder2, "m3");
+        Configuration cf2 = resolve(cf1, finder2, "m3");
 
         assertTrue(cf2.modules().size() == 1);
         assertTrue(cf2.findModule("m3").isPresent());
@@ -810,22 +779,19 @@
      */
     public void testServiceBinding1() {
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .exports("p")
                 .uses("p.S")
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires("m1")
-                .contains("q")
-                .provides("p.S", "q.T")
+                .provides("p.S", List.of("q.T"))
                 .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1, descriptor2);
 
-        Configuration cf = resolveRequiresAndUses(finder, "m1");
+        Configuration cf = resolveAndBind(finder, "m1");
 
         assertTrue(cf.modules().size() == 2);
         assertTrue(cf.findModule("m1").isPresent());
@@ -853,31 +819,26 @@
      */
     public void testServiceBinding2() {
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .exports("p")
                 .uses("p.S1")
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires("m1")
                 .uses("p.S2")
-                .contains("q")
-                .provides("p.S1", "q.Service1Impl")
+                .provides("p.S1", List.of("q.Service1Impl"))
                 .build();
 
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .requires("m1")
-                .contains("q")
-                .provides("p.S2", "q.Service2Impl")
+                .provides("p.S2", List.of("q.Service2Impl"))
                 .build();
 
         ModuleFinder finder
             = ModuleUtils.finderOf(descriptor1, descriptor2, descriptor3);
 
-        Configuration cf = resolveRequiresAndUses(finder, "m1");
+        Configuration cf = resolveAndBind(finder, "m1");
 
         assertTrue(cf.modules().size() == 3);
         assertTrue(cf.findModule("m1").isPresent());
@@ -912,29 +873,26 @@
      */
     public void testServiceBindingWithConfigurations1() {
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .exports("p")
                 .uses("p.S")
                 .build();
 
         ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1);
 
-        Configuration cf1 = resolveRequires(finder1, "m1");
+        Configuration cf1 = resolve(finder1, "m1");
 
         assertTrue(cf1.modules().size() == 1);
         assertTrue(cf1.findModule("m1").isPresent());
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires("m1")
-                .contains("q")
-                .provides("p.S", "q.T")
+                .provides("p.S", List.of("q.T"))
                 .build();
 
         ModuleFinder finder2 = ModuleUtils.finderOf(descriptor2);
 
-        Configuration cf2 = resolveRequiresAndUses(cf1, finder2); // no roots
+        Configuration cf2 = resolveAndBind(cf1, finder2); // no roots
 
         assertTrue(cf2.parents().size() == 1);
         assertTrue(cf2.parents().get(0) == cf1);
@@ -961,47 +919,39 @@
      */
     public void testServiceBindingWithConfigurations2() {
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .exports("p")
                 .uses("p.S")
-                .contains("p1")
-                .provides("p.S", "p1.ServiceImpl")
+                .provides("p.S", List.of("p1.ServiceImpl"))
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires("m1")
-                .contains("p2")
-                .provides("p.S", "p2.ServiceImpl")
+                .provides("p.S", List.of("p2.ServiceImpl"))
                 .build();
 
         ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1, descriptor2);
 
-        Configuration cf1 = resolveRequiresAndUses(finder1, "m1");
+        Configuration cf1 = resolveAndBind(finder1, "m1");
 
         assertTrue(cf1.modules().size() == 2);
         assertTrue(cf1.findModule("m1").isPresent());
         assertTrue(cf1.findModule("m2").isPresent());
 
 
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .requires("m1")
-                .contains("p3")
-                .provides("p.S", "p3.ServiceImpl")
+                .provides("p.S", List.of("p3.ServiceImpl"))
                 .build();
 
-        ModuleDescriptor descriptor4
-            = ModuleDescriptor.module("m4")
+        ModuleDescriptor descriptor4 = newBuilder("m4")
                 .requires("m1")
-                .contains("p4")
-                .provides("p.S", "p4.ServiceImpl")
+                .provides("p.S", List.of("p4.ServiceImpl"))
                 .build();
 
         ModuleFinder finder2 = ModuleUtils.finderOf(descriptor3, descriptor4);
 
-        Configuration cf2 = resolveRequiresAndUses(cf1, finder2); // no roots
+        Configuration cf2 = resolveAndBind(cf1, finder2); // no roots
 
         assertTrue(cf2.parents().size() == 1);
         assertTrue(cf2.parents().get(0) == cf1);
@@ -1037,22 +987,19 @@
      */
     public void testServiceBindingWithConfigurations3() {
 
-        ModuleDescriptor service
-            = ModuleDescriptor.module("s")
+        ModuleDescriptor service = newBuilder("s")
                 .exports("p")
                 .build();
 
-        ModuleDescriptor provider_v1
-            = ModuleDescriptor.module("p")
+        ModuleDescriptor provider_v1 = newBuilder("p")
                 .version("1.0")
                 .requires("s")
-                .contains("q")
-                .provides("p.S", "q.T")
+                .provides("p.S", List.of("q.T"))
                 .build();
 
         ModuleFinder finder1 = ModuleUtils.finderOf(service, provider_v1);
 
-        Configuration cf1 = resolveRequires(finder1, "p");
+        Configuration cf1 = resolve(finder1, "p");
 
         assertTrue(cf1.modules().size() == 2);
         assertTrue(cf1.findModule("s").isPresent());
@@ -1063,18 +1010,15 @@
         assertEquals(p.reference().descriptor(), provider_v1);
 
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .requires("s")
                 .uses("p.S")
                 .build();
 
-        ModuleDescriptor provider_v2
-            = ModuleDescriptor.module("p")
+        ModuleDescriptor provider_v2 = newBuilder("p")
                 .version("2.0")
                 .requires("s")
-                .contains("q")
-                .provides("p.S", "q.T")
+                .provides("p.S", List.of("q.T"))
                 .build();
 
         ModuleFinder finder2 = ModuleUtils.finderOf(descriptor1, provider_v2);
@@ -1082,7 +1026,7 @@
 
         // finder2 is the before ModuleFinder and so p@2.0 should be located
 
-        Configuration cf2 = resolveRequiresAndUses(cf1, finder2, "m1");
+        Configuration cf2 = resolveAndBind(cf1, finder2, "m1");
 
         assertTrue(cf2.parents().size() == 1);
         assertTrue(cf2.parents().get(0) == cf1);
@@ -1097,7 +1041,7 @@
         // finder2 is the after ModuleFinder and so p@2.0 should not be located
         // as module p is in parent configuration.
 
-        cf2 = resolveRequiresAndUses(cf1, ModuleFinder.of(), finder2, "m1");
+        cf2 = resolveAndBind(cf1, ModuleFinder.of(), finder2, "m1");
 
         assertTrue(cf2.parents().size() == 1);
         assertTrue(cf2.parents().get(0) == cf1);
@@ -1117,25 +1061,22 @@
      */
     public void testWithTwoFinders1() {
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .requires("m2")
                 .build();
 
-        ModuleDescriptor descriptor2_v1
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2_v1 = newBuilder("m2")
                 .version("1.0")
                 .build();
 
-        ModuleDescriptor descriptor2_v2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2_v2 = newBuilder("m2")
                 .version("2.0")
                 .build();
 
         ModuleFinder finder1 = ModuleUtils.finderOf(descriptor2_v1);
         ModuleFinder finder2 = ModuleUtils.finderOf(descriptor1, descriptor2_v2);
 
-        Configuration cf = resolveRequires(finder1, finder2, "m1");
+        Configuration cf = resolve(finder1, finder2, "m1");
 
         assertTrue(cf.modules().size() == 2);
         assertTrue(cf.findModule("m1").isPresent());
@@ -1157,30 +1098,25 @@
      */
     public void testWithTwoFinders2() {
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .exports("p")
                 .uses("p.S")
                 .build();
 
-        ModuleDescriptor descriptor2_v1
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2_v1 = newBuilder("m2")
                 .requires("m1")
-                .contains("q")
-                .provides("p.S", "q.T")
+                .provides("p.S", List.of("q.T"))
                 .build();
 
-        ModuleDescriptor descriptor2_v2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2_v2 = newBuilder("m2")
                 .requires("m1")
-                .contains("q")
-                .provides("p.S", "q.T")
+                .provides("p.S", List.of("q.T"))
                 .build();
 
         ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1, descriptor2_v1);
         ModuleFinder finder2 = ModuleUtils.finderOf(descriptor2_v2);
 
-        Configuration cf = resolveRequiresAndUses(finder1, finder2, "m1");
+        Configuration cf = resolveAndBind(finder1, finder2, "m1");
 
         assertTrue(cf.modules().size() == 2);
         assertTrue(cf.findModule("m1").isPresent());
@@ -1200,18 +1136,17 @@
      */
     public void testResolvedInParent1() {
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1);
 
-        Configuration cf1 = resolveRequires(finder, "m1");
+        Configuration cf1 = resolve(finder, "m1");
 
         assertTrue(cf1.modules().size() == 1);
         assertTrue(cf1.findModule("m1").isPresent());
 
-        Configuration cf2 = resolveRequires(cf1, finder, "m1");
+        Configuration cf2 = resolve(cf1, finder, "m1");
 
         assertTrue(cf2.modules().size() == 1);
     }
@@ -1223,26 +1158,23 @@
      */
     public void testResolvedInParent2() {
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
-                .build();
+        ModuleDescriptor descriptor1 = newBuilder("m1").build();
 
         ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1);
 
-        Configuration cf1 = resolveRequires(finder1, "m1");
+        Configuration cf1 = resolve(finder1, "m1");
 
         assertTrue(cf1.modules().size() == 1);
         assertTrue(cf1.findModule("m1").isPresent());
 
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires("m1")
                 .build();
 
         ModuleFinder finder2 = ModuleUtils.finderOf(descriptor2);
 
-        Configuration cf2 = resolveRequires(cf1, ModuleFinder.of(), finder2, "m2");
+        Configuration cf2 = resolve(cf1, ModuleFinder.of(), finder2, "m2");
 
         assertTrue(cf2.modules().size() == 1);
         assertTrue(cf2.findModule("m2").isPresent());
@@ -1268,29 +1200,28 @@
     public void testResolvedInMultipleParents1() {
 
         // Configuration cf1: m1
-        ModuleDescriptor descriptor1 = ModuleDescriptor.module("m1").build();
-        Configuration cf1 = resolveRequires(ModuleUtils.finderOf(descriptor1), "m1");
+        ModuleDescriptor descriptor1 = newBuilder("m1").build();
+        Configuration cf1 = resolve(ModuleUtils.finderOf(descriptor1), "m1");
         assertEquals(cf1.parents(), List.of(Configuration.empty()));
         assertTrue(cf1.findModule("m1").isPresent());
         ResolvedModule m1 = cf1.findModule("m1").get();
         assertTrue(m1.configuration() == cf1);
 
         // Configuration cf2: m2
-        ModuleDescriptor descriptor2 = ModuleDescriptor.module("m2").build();
-        Configuration cf2 = resolveRequires(ModuleUtils.finderOf(descriptor2), "m2");
+        ModuleDescriptor descriptor2 = newBuilder("m2").build();
+        Configuration cf2 = resolve(ModuleUtils.finderOf(descriptor2), "m2");
         assertEquals(cf2.parents(), List.of(Configuration.empty()));
         assertTrue(cf2.findModule("m2").isPresent());
         ResolvedModule m2 = cf2.findModule("m2").get();
         assertTrue(m2.configuration() == cf2);
 
         // Configuration cf3(cf1,cf2): m3 requires m1 and m2
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .requires("m1")
                 .requires("m2")
                 .build();
         ModuleFinder finder = ModuleUtils.finderOf(descriptor3);
-        Configuration cf3 = Configuration.resolveRequires(
+        Configuration cf3 = Configuration.resolve(
                 finder,
                 List.of(cf1, cf2),  // parents
                 ModuleFinder.of(),
@@ -1319,19 +1250,18 @@
      */
     public void testResolvedInMultipleParents2() {
         // Configuration cf1: m1
-        ModuleDescriptor descriptor1 = ModuleDescriptor.module("m1").build();
-        Configuration cf1 = resolveRequires(ModuleUtils.finderOf(descriptor1), "m1");
+        ModuleDescriptor descriptor1 = newBuilder("m1").build();
+        Configuration cf1 = resolve(ModuleUtils.finderOf(descriptor1), "m1");
         assertEquals(cf1.parents(), List.of(Configuration.empty()));
         assertTrue(cf1.findModule("m1").isPresent());
         ResolvedModule m1 = cf1.findModule("m1").get();
         assertTrue(m1.configuration() == cf1);
 
         // Configuration cf2(cf1): m2 requires m1
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires("m1")
                 .build();
-        Configuration cf2 = Configuration.resolveRequires(
+        Configuration cf2 = Configuration.resolve(
                 ModuleUtils.finderOf(descriptor2),
                 List.of(cf1),  // parents
                 ModuleFinder.of(),
@@ -1342,11 +1272,10 @@
         assertTrue(m2.configuration() == cf2);
 
         // Configuration cf3(cf1): m3 requires m1
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .requires("m1")
                 .build();
-        Configuration cf3 = Configuration.resolveRequires(
+        Configuration cf3 = Configuration.resolve(
                 ModuleUtils.finderOf(descriptor3),
                 List.of(cf1),  // parents
                 ModuleFinder.of(),
@@ -1357,13 +1286,12 @@
         assertTrue(m3.configuration() == cf3);
 
         // Configuration cf4(cf2,cf3): m4 requires m1,m2,m3
-        ModuleDescriptor descriptor4
-            = ModuleDescriptor.module("m4")
+        ModuleDescriptor descriptor4 = newBuilder("m4")
                 .requires("m1")
                 .requires("m2")
                 .requires("m3")
                 .build();
-        Configuration cf4 = Configuration.resolveRequires(
+        Configuration cf4 = Configuration.resolve(
                 ModuleUtils.finderOf(descriptor4),
                 List.of(cf2, cf3),  // parents
                 ModuleFinder.of(),
@@ -1395,35 +1323,34 @@
         ModuleDescriptor descriptor1, descriptor2, descriptor3;
 
         // Configuration cf1: m1@1
-        descriptor1 = ModuleDescriptor.module("m1").version("1").build();
-        Configuration cf1 = resolveRequires(ModuleUtils.finderOf(descriptor1), "m1");
+        descriptor1 = newBuilder("m1").version("1").build();
+        Configuration cf1 = resolve(ModuleUtils.finderOf(descriptor1), "m1");
         assertEquals(cf1.parents(), List.of(Configuration.empty()));
 
         // Configuration cf2: m1@2, m2@2
-        descriptor1 = ModuleDescriptor.module("m1").version("2").build();
-        descriptor2 = ModuleDescriptor.module("m2").version("2").build();
-        Configuration cf2 = resolveRequires(
+        descriptor1 = newBuilder("m1").version("2").build();
+        descriptor2 = newBuilder("m2").version("2").build();
+        Configuration cf2 = resolve(
                 ModuleUtils.finderOf(descriptor1, descriptor2),
                 "m1", "m2");
         assertEquals(cf2.parents(), List.of(Configuration.empty()));
 
         // Configuration cf3: m1@3, m2@3, m3@3
-        descriptor1 = ModuleDescriptor.module("m1").version("3").build();
-        descriptor2 = ModuleDescriptor.module("m2").version("3").build();
-        descriptor3 = ModuleDescriptor.module("m3").version("3").build();
-        Configuration cf3 = resolveRequires(
+        descriptor1 = newBuilder("m1").version("3").build();
+        descriptor2 = newBuilder("m2").version("3").build();
+        descriptor3 = newBuilder("m3").version("3").build();
+        Configuration cf3 = resolve(
                 ModuleUtils.finderOf(descriptor1, descriptor2, descriptor3),
                 "m1", "m2", "m3");
         assertEquals(cf3.parents(), List.of(Configuration.empty()));
 
         // Configuration cf4(cf1,cf2,cf3): m4 requires m1,m2,m3
-        ModuleDescriptor descriptor4
-                = ModuleDescriptor.module("m4")
+        ModuleDescriptor descriptor4 = newBuilder("m4")
                 .requires("m1")
                 .requires("m2")
                 .requires("m3")
                 .build();
-        Configuration cf4 = Configuration.resolveRequires(
+        Configuration cf4 = Configuration.resolve(
                 ModuleUtils.finderOf(descriptor4),
                 List.of(cf1, cf2, cf3),  // parents
                 ModuleFinder.of(),
@@ -1470,17 +1397,15 @@
      * configuration.
      */
     public void testOverriding1() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
-                .build();
+        ModuleDescriptor descriptor1 = newBuilder("m1").build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1);
 
-        Configuration cf1 = resolveRequires(finder, "m1");
+        Configuration cf1 = resolve(finder, "m1");
         assertTrue(cf1.modules().size() == 1);
         assertTrue(cf1.findModule("m1").isPresent());
 
-        Configuration cf2 = resolveRequires(cf1, finder, "m1");
+        Configuration cf2 = resolve(cf1, finder, "m1");
         assertTrue(cf2.modules().size() == 1);
         assertTrue(cf2.findModule("m1").isPresent());
     }
@@ -1490,24 +1415,24 @@
      * configuration.
      */
     public void testOverriding2() {
-        ModuleDescriptor descriptor1 = ModuleDescriptor.module("m1").build();
-        Configuration cf1 = resolveRequires(ModuleUtils.finderOf(descriptor1), "m1");
+        ModuleDescriptor descriptor1 = newBuilder("m1").build();
+        Configuration cf1 = resolve(ModuleUtils.finderOf(descriptor1), "m1");
         assertTrue(cf1.modules().size() == 1);
         assertTrue(cf1.findModule("m1").isPresent());
 
-        ModuleDescriptor descriptor2 = ModuleDescriptor.module("m2").build();
-        Configuration cf2 = resolveRequires(ModuleUtils.finderOf(descriptor2), "m2");
+        ModuleDescriptor descriptor2 = newBuilder("m2").build();
+        Configuration cf2 = resolve(ModuleUtils.finderOf(descriptor2), "m2");
         assertTrue(cf2.modules().size() == 1);
         assertTrue(cf2.findModule("m2").isPresent());
 
-        ModuleDescriptor descriptor3 = ModuleDescriptor.module("m3").build();
-        Configuration cf3 = resolveRequires(ModuleUtils.finderOf(descriptor3), "m3");
+        ModuleDescriptor descriptor3 = newBuilder("m3").build();
+        Configuration cf3 = resolve(ModuleUtils.finderOf(descriptor3), "m3");
         assertTrue(cf3.modules().size() == 1);
         assertTrue(cf3.findModule("m3").isPresent());
 
         // override m2, m1 and m3 should be found in parent configurations
         ModuleFinder finder = ModuleUtils.finderOf(descriptor2);
-        Configuration cf4 = Configuration.resolveRequires(
+        Configuration cf4 = Configuration.resolve(
                 finder,
                 List.of(cf1, cf2, cf3),
                 ModuleFinder.of(),
@@ -1530,18 +1455,16 @@
      */
     public void testOverriding3() {
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires(Set.of(Requires.Modifier.TRANSITIVE), "m1")
                 .build();
 
         ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1, descriptor2);
 
-        Configuration cf1 = resolveRequires(finder1, "m2");
+        Configuration cf1 = resolve(finder1, "m2");
 
         assertTrue(cf1.modules().size() == 2);
         assertTrue(cf1.findModule("m1").isPresent());
@@ -1549,14 +1472,13 @@
 
         // cf2: m3 requires m2, m1
 
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .requires("m2")
                 .build();
 
         ModuleFinder finder2 = ModuleUtils.finderOf(descriptor1, descriptor3);
 
-        Configuration cf2 = resolveRequires(cf1, finder2, "m1", "m3");
+        Configuration cf2 = resolve(cf1, finder2, "m1", "m3");
 
         assertTrue(cf2.parents().size() == 1);
         assertTrue(cf2.parents().get(0) == cf1);
@@ -1585,64 +1507,58 @@
     /**
      * Root module not found
      */
-    @Test(expectedExceptions = { ResolutionException.class })
+    @Test(expectedExceptions = { FindException.class })
     public void testRootNotFound() {
-        resolveRequires(ModuleFinder.of(), "m1");
+        resolve(ModuleFinder.of(), "m1");
     }
 
 
     /**
      * Direct dependency not found
      */
-    @Test(expectedExceptions = { ResolutionException.class })
+    @Test(expectedExceptions = { FindException.class })
     public void testDirectDependencyNotFound() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1").requires("m2").build();
+        ModuleDescriptor descriptor1 = newBuilder("m1").requires("m2").build();
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1);
-        resolveRequires(finder, "m1");
+        resolve(finder, "m1");
     }
 
 
     /**
      * Transitive dependency not found
      */
-    @Test(expectedExceptions = { ResolutionException.class })
+    @Test(expectedExceptions = { FindException.class })
     public void testTransitiveDependencyNotFound() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1").requires("m2").build();
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2").requires("m3").build();
+        ModuleDescriptor descriptor1 = newBuilder("m1").requires("m2").build();
+        ModuleDescriptor descriptor2 = newBuilder("m2").requires("m3").build();
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1, descriptor2);
-        resolveRequires(finder, "m1");
+        resolve(finder, "m1");
     }
 
 
     /**
      * Service provider dependency not found
      */
-    @Test(expectedExceptions = { ResolutionException.class })
+    @Test(expectedExceptions = { FindException.class })
     public void testServiceProviderDependencyNotFound() {
 
         // service provider dependency (on m3) not found
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .exports("p")
                 .uses("p.S")
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires("m1")
                 .requires("m3")
-                .contains("q")
-                .provides("p.S", "q.T")
+                .provides("p.S", List.of("q.T"))
                 .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1, descriptor2);
 
         // should throw ResolutionException because m3 is not found
-        Configuration cf = resolveRequiresAndUses(finder, "m1");
+        Configuration cf = resolveAndBind(finder, "m1");
     }
 
 
@@ -1651,15 +1567,12 @@
      */
     @Test(expectedExceptions = { ResolutionException.class })
     public void testSimpleCycle() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1").requires("m2").build();
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2").requires("m3").build();
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3").requires("m1").build();
+        ModuleDescriptor descriptor1 = newBuilder("m1").requires("m2").build();
+        ModuleDescriptor descriptor2 = newBuilder("m2").requires("m3").build();
+        ModuleDescriptor descriptor3 = newBuilder("m3").requires("m1").build();
         ModuleFinder finder
             = ModuleUtils.finderOf(descriptor1, descriptor2, descriptor3);
-        resolveRequires(finder, "m1");
+        resolve(finder, "m1");
     }
 
     /**
@@ -1668,20 +1581,16 @@
     @Test(expectedExceptions = { ResolutionException.class })
     public void testCycleInProvider() {
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .exports("p")
                 .uses("p.S")
                 .build();
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires("m1")
                 .requires("m3")
-                .contains("q")
-                .provides("p.S", "q.T")
+                .provides("p.S", List.of("q.T"))
                 .build();
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .requires("m2")
                 .build();
 
@@ -1689,7 +1598,7 @@
             = ModuleUtils.finderOf(descriptor1, descriptor2, descriptor3);
 
         // should throw ResolutionException because of the m2 <--> m3 cycle
-        resolveRequiresAndUses(finder, "m1");
+        resolveAndBind(finder, "m1");
     }
 
 
@@ -1699,19 +1608,16 @@
     @Test(expectedExceptions = { ResolutionException.class })
     public void testPackageSuppliedByTwoOthers() {
 
-        ModuleDescriptor descriptor1
-            =  ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .requires("m2")
                 .requires("m3")
                 .build();
 
-        ModuleDescriptor descriptor2
-            =  ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .exports("p")
                 .build();
 
-        ModuleDescriptor descriptor3
-            =  ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .exports("p", Set.of("m1"))
                 .build();
 
@@ -1719,7 +1625,7 @@
             = ModuleUtils.finderOf(descriptor1, descriptor2, descriptor3);
 
         // m2 and m3 export package p to module m1
-        resolveRequires(finder, "m1");
+        resolve(finder, "m1");
     }
 
 
@@ -1730,21 +1636,19 @@
     @Test(expectedExceptions = { ResolutionException.class })
     public void testPackageSuppliedBySelfAndOther() {
 
-        ModuleDescriptor descriptor1
-            =  ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .requires("m2")
-                .contains("p")
+                .packages(Set.of("p"))
                 .build();
 
-        ModuleDescriptor descriptor2
-            =  ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .exports("p")
                 .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1, descriptor2);
 
         // m1 contains package p, module m2 exports package p to m1
-        resolveRequires(finder, "m1");
+        resolve(finder, "m1");
     }
 
 
@@ -1753,20 +1657,18 @@
      * a module that also contains a package p.
      */
     public void testContainsPackageInSelfAndOther() {
-        ModuleDescriptor descriptor1
-            =  ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .requires("m2")
-                .contains("p")
+                .packages(Set.of("p"))
                 .build();
 
-        ModuleDescriptor descriptor2
-            =  ModuleDescriptor.module("m2")
-                .contains("p")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
+                .packages(Set.of("p"))
                 .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1, descriptor2);
 
-        Configuration cf = resolveRequires(finder, "m1");
+        Configuration cf = resolve(finder, "m1");
 
         assertTrue(cf.modules().size() == 2);
         assertTrue(cf.findModule("m1").isPresent());
@@ -1787,8 +1689,7 @@
      */
     @Test(expectedExceptions = { ResolutionException.class })
     public void testExportSamePackageAsBootLayer() {
-        ModuleDescriptor descriptor
-            =  ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor = newBuilder("m1")
                 .requires("java.base")
                 .exports("java.lang")
                 .build();
@@ -1798,7 +1699,7 @@
         Configuration bootConfiguration = Layer.boot().configuration();
 
         // m1 contains package java.lang, java.base exports package java.lang to m1
-        resolveRequires(bootConfiguration, finder, "m1");
+        resolve(bootConfiguration, finder, "m1");
     }
 
 
@@ -1806,15 +1707,14 @@
      * Test "uses p.S" where p is contained in the same module.
      */
     public void testContainsService1() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
-                .contains("p")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
+                .packages(Set.of("p"))
                 .uses("p.S")
                 .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1);
 
-        Configuration cf = resolveRequires(finder, "m1");
+        Configuration cf = resolve(finder, "m1");
 
         assertTrue(cf.modules().size() == 1);
         assertTrue(cf.findModule("m1").isPresent());
@@ -1826,13 +1726,11 @@
      */
     @Test(expectedExceptions = { ResolutionException.class })
     public void testContainsService2() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
-                .contains("p")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
+                .packages(Set.of("p"))
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires("m1")
                 .uses("p.S")
                 .build();
@@ -1840,7 +1738,7 @@
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1, descriptor2);
 
         // m2 does not read a module that exports p
-        resolveRequires(finder, "m2");
+        resolve(finder, "m2");
     }
 
 
@@ -1848,16 +1746,14 @@
      * Test "provides p.S" where p is contained in the same module.
      */
     public void testContainsService3() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
-                .contains("p")
-                .contains("q")
-                .provides("p.S", "q.S1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
+                .packages(Set.of("p", "q"))
+                .provides("p.S", List.of("q.S1"))
                 .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1);
 
-        Configuration cf = resolveRequires(finder, "m1");
+        Configuration cf = resolve(finder, "m1");
 
         assertTrue(cf.modules().size() == 1);
         assertTrue(cf.findModule("m1").isPresent());
@@ -1869,22 +1765,19 @@
      */
     @Test(expectedExceptions = { ResolutionException.class })
     public void testContainsService4() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
-                .contains("p")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
+                .packages(Set.of("p"))
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires("m1")
-                .contains("q")
-                .provides("p.S", "q.S1")
+                .provides("p.S", List.of("q.S1"))
                 .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1, descriptor2);
 
         // m2 does not read a module that exports p
-        resolveRequires(finder, "m2");
+        resolve(finder, "m2");
     }
 
 
@@ -1893,15 +1786,14 @@
      */
     @Test(expectedExceptions = { ResolutionException.class })
     public void testServiceTypePackageNotExported1() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .uses("p.S")
                 .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1);
 
         // m1 does not read a module that exports p
-        resolveRequires(finder, "m1");
+        resolve(finder, "m1");
     }
 
 
@@ -1910,40 +1802,14 @@
      */
     @Test(expectedExceptions = { ResolutionException.class })
     public void testServiceTypePackageNotExported2() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
-                .contains("q")
-                .provides("p.S", "q.T")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
+                .provides("p.S", List.of("q.T"))
                 .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1);
 
         // m1 does not read a module that exports p
-        resolveRequires(finder, "m1");
-    }
-
-
-    /**
-     * Test "provides p.S with q.T" where q.T is not local
-     */
-    @Test(expectedExceptions = { ResolutionException.class })
-    public void testProviderPackageNotLocal() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
-                .exports("p")
-                .exports("q")
-                .build();
-
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
-                .requires("m1")
-                .provides("p.S", "q.T")
-                .build();
-
-        ModuleFinder finder = ModuleUtils.finderOf(descriptor1, descriptor2);
-
-        // q.T not in module m2
-        resolveRequires(finder, "m2");
+        resolve(finder, "m1");
     }
 
 
@@ -2007,34 +1873,17 @@
     @Test(dataProvider = "platformmatch")
     public void testPlatformMatch(String s1, String s2) {
 
-        ModuleDescriptor.Builder builder
-            = ModuleDescriptor.module("m1").requires("m2");
-
-        String[] s = s1.split("-");
-        if (!s[0].equals("*"))
-            builder.osName(s[0]);
-        if (!s[1].equals("*"))
-            builder.osArch(s[1]);
-        if (!s[2].equals("*"))
-            builder.osVersion(s[2]);
-
+        Builder builder = newBuilder("m1").requires("m2");
+        addPlatformConstraints(builder, s1);
         ModuleDescriptor descriptor1 = builder.build();
 
-        builder = ModuleDescriptor.module("m2");
-
-        s = s2.split("-");
-        if (!s[0].equals("*"))
-            builder.osName(s[0]);
-        if (!s[1].equals("*"))
-            builder.osArch(s[1]);
-        if (!s[2].equals("*"))
-            builder.osVersion(s[2]);
-
+        builder = newBuilder("m2");
+        addPlatformConstraints(builder, s2);
         ModuleDescriptor descriptor2 = builder.build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1, descriptor2);
 
-        Configuration cf = resolveRequires(finder, "m1");
+        Configuration cf = resolve(finder, "m1");
 
         assertTrue(cf.modules().size() == 2);
         assertTrue(cf.findModule("m1").isPresent());
@@ -2046,7 +1895,7 @@
      * platforms.
      */
     @Test(dataProvider = "platformmismatch",
-          expectedExceptions = ResolutionException.class )
+          expectedExceptions = FindException.class )
     public void testPlatformMisMatch(String s1, String s2) {
         testPlatformMatch(s1, s2);
     }
@@ -2057,16 +1906,67 @@
     @Test(expectedExceptions = { IllegalArgumentException.class })
     public void testResolveRequiresWithNoParents() {
         ModuleFinder empty = ModuleFinder.of();
-        Configuration.resolveRequires(empty, List.of(), empty, Set.of());
+        Configuration.resolve(empty, List.of(), empty, Set.of());
     }
 
     @Test(expectedExceptions = { IllegalArgumentException.class })
     public void testResolveRequiresAndUsesWithNoParents() {
         ModuleFinder empty = ModuleFinder.of();
-        Configuration.resolveRequiresAndUses(empty, List.of(), empty, Set.of());
+        Configuration.resolveAndBind(empty, List.of(), empty, Set.of());
     }
 
 
+    // parents with modules for specific platforms
+
+    @Test(dataProvider = "platformmatch")
+    public void testResolveRequiresWithCompatibleParents(String s1, String s2) {
+        Builder builder = newBuilder("m1");
+        addPlatformConstraints(builder, s1);
+        ModuleDescriptor descriptor1 = builder.build();
+
+        builder = newBuilder("m2");
+        addPlatformConstraints(builder, s2);
+        ModuleDescriptor descriptor2 = builder.build();
+
+        ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1);
+        Configuration cf1 = resolve(finder1, "m1");
+
+        ModuleFinder finder2 = ModuleUtils.finderOf(descriptor2);
+        Configuration cf2 = resolve(finder2, "m2");
+
+        Configuration cf3 = Configuration.resolve(ModuleFinder.of(),
+                                                  List.of(cf1, cf2),
+                                                  ModuleFinder.of(),
+                                                  Set.of());
+        assertTrue(cf3.parents().size() == 2);
+    }
+
+    @Test(dataProvider = "platformmismatch",
+          expectedExceptions = IllegalArgumentException.class )
+    public void testResolveRequiresWithConflictingParents(String s1, String s2) {
+        Builder builder = newBuilder("m1");
+        addPlatformConstraints(builder, s1);
+        ModuleDescriptor descriptor1 = builder.build();
+
+        builder = newBuilder("m2");
+        addPlatformConstraints(builder, s2);
+        ModuleDescriptor descriptor2 = builder.build();
+
+        ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1);
+        Configuration cf1 = resolve(finder1, "m1");
+
+        ModuleFinder finder2 = ModuleUtils.finderOf(descriptor2);
+        Configuration cf2 = resolve(finder2, "m2");
+
+        // should throw IAE
+        Configuration.resolve(ModuleFinder.of(),
+                              List.of(cf1, cf2),
+                              ModuleFinder.of(),
+                              Set.of());
+    }
+
+
+
     // null handling
 
     // finder1, finder2, roots
@@ -2074,72 +1974,72 @@
 
     @Test(expectedExceptions = { NullPointerException.class })
     public void testResolveRequiresWithNull1() {
-        resolveRequires((ModuleFinder)null, ModuleFinder.of());
+        resolve((ModuleFinder)null, ModuleFinder.of());
     }
 
     @Test(expectedExceptions = { NullPointerException.class })
     public void testResolveRequiresWithNull2() {
-        resolveRequires(ModuleFinder.of(), (ModuleFinder)null);
+        resolve(ModuleFinder.of(), (ModuleFinder)null);
     }
 
     @Test(expectedExceptions = { NullPointerException.class })
     public void testResolveRequiresWithNull3() {
         Configuration empty = Configuration.empty();
-        Configuration.resolveRequires(null, List.of(empty),  ModuleFinder.of(), Set.of());
+        Configuration.resolve(null, List.of(empty),  ModuleFinder.of(), Set.of());
     }
 
     @Test(expectedExceptions = { NullPointerException.class })
     public void testResolveRequiresWithNull4() {
         ModuleFinder empty = ModuleFinder.of();
-        Configuration.resolveRequires(empty, null, empty, Set.of());
+        Configuration.resolve(empty, null, empty, Set.of());
     }
 
     @Test(expectedExceptions = { NullPointerException.class })
     public void testResolveRequiresWithNull5() {
         Configuration cf = Layer.boot().configuration();
-        Configuration.resolveRequires(ModuleFinder.of(), List.of(cf), null, Set.of());
+        Configuration.resolve(ModuleFinder.of(), List.of(cf), null, Set.of());
     }
 
     @Test(expectedExceptions = { NullPointerException.class })
     public void testResolveRequiresWithNull6() {
         ModuleFinder empty = ModuleFinder.of();
         Configuration cf = Layer.boot().configuration();
-        Configuration.resolveRequires(empty, List.of(cf), empty, null);
+        Configuration.resolve(empty, List.of(cf), empty, null);
     }
 
     @Test(expectedExceptions = { NullPointerException.class })
     public void testResolveRequiresAndUsesWithNull1() {
-        resolveRequiresAndUses((ModuleFinder) null, ModuleFinder.of());
+        resolveAndBind((ModuleFinder) null, ModuleFinder.of());
     }
 
     @Test(expectedExceptions = { NullPointerException.class })
     public void testResolveRequiresAndUsesWithNull2() {
-        resolveRequiresAndUses(ModuleFinder.of(), (ModuleFinder) null);
+        resolveAndBind(ModuleFinder.of(), (ModuleFinder) null);
     }
 
     @Test(expectedExceptions = { NullPointerException.class })
     public void testResolveRequiresAndUsesWithNull3() {
         Configuration empty = Configuration.empty();
-        Configuration.resolveRequiresAndUses(null, List.of(empty), ModuleFinder.of(), Set.of());
+        Configuration.resolveAndBind(null, List.of(empty), ModuleFinder.of(), Set.of());
     }
 
     @Test(expectedExceptions = { NullPointerException.class })
     public void testResolveRequiresAndUsesWithNull4() {
         ModuleFinder empty = ModuleFinder.of();
-        Configuration.resolveRequiresAndUses(empty, null, empty, Set.of());
+        Configuration.resolveAndBind(empty, null, empty, Set.of());
     }
 
     @Test(expectedExceptions = { NullPointerException.class })
     public void testResolveRequiresAndUsesWithNull5() {
         Configuration cf = Layer.boot().configuration();
-        Configuration.resolveRequiresAndUses(ModuleFinder.of(), List.of(cf), null, Set.of());
+        Configuration.resolveAndBind(ModuleFinder.of(), List.of(cf), null, Set.of());
     }
 
     @Test(expectedExceptions = { NullPointerException.class })
     public void testResolveRequiresAndUsesWithNull6() {
         ModuleFinder empty = ModuleFinder.of();
         Configuration cf = Layer.boot().configuration();
-        Configuration.resolveRequiresAndUses(empty, List.of(cf), empty, null);
+        Configuration.resolveAndBind(empty, List.of(cf), empty, null);
     }
 
     @Test(expectedExceptions = { NullPointerException.class })
@@ -2165,58 +2065,58 @@
 
 
     /**
-     * Invokes parent.resolveRequires(...)
+     * Invokes parent.resolve(...)
      */
-    private Configuration resolveRequires(Configuration parent,
-                                          ModuleFinder before,
-                                          ModuleFinder after,
-                                          String... roots) {
-        return parent.resolveRequires(before, after, Set.of(roots));
+    private Configuration resolve(Configuration parent,
+                                  ModuleFinder before,
+                                  ModuleFinder after,
+                                  String... roots) {
+        return parent.resolve(before, after, Set.of(roots));
     }
 
-    private Configuration resolveRequires(Configuration parent,
-                                          ModuleFinder before,
-                                          String... roots) {
-        return resolveRequires(parent, before, ModuleFinder.of(), roots);
+    private Configuration resolve(Configuration parent,
+                                  ModuleFinder before,
+                                  String... roots) {
+        return resolve(parent, before, ModuleFinder.of(), roots);
     }
 
-    private Configuration resolveRequires(ModuleFinder before,
-                                          ModuleFinder after,
-                                          String... roots) {
-        return resolveRequires(Configuration.empty(), before, after, roots);
+    private Configuration resolve(ModuleFinder before,
+                                  ModuleFinder after,
+                                  String... roots) {
+        return resolve(Configuration.empty(), before, after, roots);
     }
 
-    private Configuration resolveRequires(ModuleFinder before,
-                                          String... roots) {
-        return resolveRequires(Configuration.empty(), before, roots);
+    private Configuration resolve(ModuleFinder before,
+                                  String... roots) {
+        return resolve(Configuration.empty(), before, roots);
     }
 
 
     /**
-     * Invokes parent.resolveRequiresAndUses(...)
+     * Invokes parent.resolveAndBind(...)
      */
-    private Configuration resolveRequiresAndUses(Configuration parent,
-                                                 ModuleFinder before,
-                                                 ModuleFinder after,
-                                                 String... roots) {
-        return parent.resolveRequiresAndUses(before, after, Set.of(roots));
+    private Configuration resolveAndBind(Configuration parent,
+                                         ModuleFinder before,
+                                         ModuleFinder after,
+                                         String... roots) {
+        return parent.resolveAndBind(before, after, Set.of(roots));
     }
 
-    private Configuration resolveRequiresAndUses(Configuration parent,
-                                                 ModuleFinder before,
-                                                 String... roots) {
-        return resolveRequiresAndUses(parent, before, ModuleFinder.of(), roots);
+    private Configuration resolveAndBind(Configuration parent,
+                                         ModuleFinder before,
+                                         String... roots) {
+        return resolveAndBind(parent, before, ModuleFinder.of(), roots);
     }
 
-    private Configuration resolveRequiresAndUses(ModuleFinder before,
-                                                 ModuleFinder after,
-                                                 String... roots) {
-        return resolveRequiresAndUses(Configuration.empty(), before, after, roots);
+    private Configuration resolveAndBind(ModuleFinder before,
+                                         ModuleFinder after,
+                                         String... roots) {
+        return resolveAndBind(Configuration.empty(), before, after, roots);
     }
 
-    private Configuration resolveRequiresAndUses(ModuleFinder before,
-                                                 String... roots) {
-        return resolveRequiresAndUses(Configuration.empty(), before, roots);
+    private Configuration resolveAndBind(ModuleFinder before,
+                                         String... roots) {
+        return resolveAndBind(Configuration.empty(), before, roots);
     }
 
 
@@ -2234,5 +2134,17 @@
                 .anyMatch(mn2::equals);
     }
 
-
+    /**
+     * Decodes the platform string and calls the builder osName/osArch/osVersion
+     * methods to set the platform constraints.
+     */
+    static void addPlatformConstraints(Builder builder, String platformString) {
+        String[] s = platformString.split("-");
+        if (!s[0].equals("*"))
+            builder.osName(s[0]);
+        if (!s[1].equals("*"))
+            builder.osArch(s[1]);
+        if (!s[2].equals("*"))
+            builder.osVersion(s[2]);
+    }
 }
--- a/jdk/test/java/lang/module/ModuleDescriptorTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/module/ModuleDescriptorTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013, 2017, 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
@@ -24,6 +24,7 @@
 /**
  * @test
  * @modules java.base/jdk.internal.module
+ *          java.base/jdk.internal.misc
  * @run testng ModuleDescriptorTest
  * @summary Basic test for java.lang.module.ModuleDescriptor and its builder
  */
@@ -42,14 +43,19 @@
 import java.lang.module.ModuleDescriptor.Version;
 import java.lang.reflect.Module;
 import java.nio.ByteBuffer;
+import java.util.ArrayList;
 import java.util.Collections;
 import java.util.EnumSet;
 import java.util.HashSet;
+import java.util.Iterator;
 import java.util.List;
+import java.util.Objects;
 import java.util.Set;
+import java.util.stream.Collectors;
 
 import static java.lang.module.ModuleDescriptor.Requires.Modifier.*;
 
+import jdk.internal.misc.SharedSecrets;
 import jdk.internal.module.ModuleInfoWriter;
 import org.testng.annotations.DataProvider;
 import org.testng.annotations.Test;
@@ -84,21 +90,27 @@
     // requires
 
     private Requires requires(Set<Modifier> mods, String mn) {
-        return ModuleDescriptor.module("m")
-            .requires(mods, mn)
-            .build()
-            .requires()
-            .iterator()
-            .next();
+        return requires(mods, mn, null);
     }
 
     private Requires requires(Set<Modifier> mods, String mn, Version v) {
-        return ModuleDescriptor.module("m")
-            .requires(mods, mn, v)
-            .build()
-            .requires()
-            .iterator()
-            .next();
+        Builder builder = ModuleDescriptor.newModule("m");
+        if (v == null) {
+            builder.requires(mods, mn);
+        } else {
+            builder.requires(mods, mn, v);
+        }
+        Set<Requires> requires = builder.build().requires();
+        assertTrue(requires.size() == 2);
+        Iterator<Requires> iterator = requires.iterator();
+        Requires r = iterator.next();
+        if (r.name().equals("java.base")) {
+            r = iterator.next();
+        } else {
+            Requires other = iterator.next();
+            assertEquals(other.name(), "java.base");
+        }
+        return r;
     }
 
     private Requires requires(String mn) {
@@ -107,7 +119,7 @@
 
     public void testRequiresWithRequires() {
         Requires r1 = requires("foo");
-        ModuleDescriptor descriptor = ModuleDescriptor.module("m").requires(r1).build();
+        ModuleDescriptor descriptor = ModuleDescriptor.newModule("m").requires(r1).build();
         Requires r2 = descriptor.requires().iterator().next();
         assertEquals(r1, r2);
     }
@@ -162,28 +174,28 @@
     @Test(expectedExceptions = IllegalStateException.class)
     public void testRequiresWithDuplicatesRequires() {
         Requires r = requires("foo");
-        ModuleDescriptor.module("m").requires(r).requires(r);
+        ModuleDescriptor.newModule("m").requires(r).requires(r);
     }
 
     @Test(expectedExceptions = IllegalArgumentException.class)
     public void testRequiresSelfWithRequires() {
         Requires r = requires("foo");
-        ModuleDescriptor.module("foo").requires(r);
+        ModuleDescriptor.newModule("foo").requires(r);
     }
 
     @Test(expectedExceptions = IllegalArgumentException.class)
     public void testRequiresSelfWithNoModifier() {
-        ModuleDescriptor.module("m").requires("m");
+        ModuleDescriptor.newModule("m").requires("m");
     }
 
     @Test(expectedExceptions = IllegalArgumentException.class)
     public void testRequiresSelfWithOneModifier() {
-        ModuleDescriptor.module("m").requires(Set.of(TRANSITIVE), "m");
+        ModuleDescriptor.newModule("m").requires(Set.of(TRANSITIVE), "m");
     }
 
     @Test(expectedExceptions = IllegalArgumentException.class)
     public void testRequiresSelfWithAllModifiers() {
-        ModuleDescriptor.module("m").requires(EnumSet.allOf(Modifier.class), "m");
+        ModuleDescriptor.newModule("m").requires(EnumSet.allOf(Modifier.class), "m");
     }
 
     @Test(dataProvider = "invalidjavaidentifiers",
@@ -194,17 +206,17 @@
 
     @Test(expectedExceptions = NullPointerException.class)
     public void testRequiresWithNullRequires() {
-        ModuleDescriptor.module("m").requires((Requires) null);
+        ModuleDescriptor.newModule("m").requires((Requires) null);
     }
 
     @Test(expectedExceptions = NullPointerException.class)
     public void testRequiresWithNullModifiers() {
-        ModuleDescriptor.module("m").requires(null, "foo");
+        ModuleDescriptor.newModule("m").requires(null, "foo");
     }
 
     @Test(expectedExceptions = NullPointerException.class)
     public void testRequiresWithNullVersion() {
-        ModuleDescriptor.module("m").requires(Set.of(), "foo", null);
+        ModuleDescriptor.newModule("m").requires(Set.of(), "foo", null);
     }
 
     public void testRequiresCompare() {
@@ -284,7 +296,7 @@
     // exports
 
     private Exports exports(Set<Exports.Modifier> mods, String pn) {
-        return ModuleDescriptor.module("foo")
+        return ModuleDescriptor.newModule("foo")
             .exports(mods, pn)
             .build()
             .exports()
@@ -297,7 +309,7 @@
     }
 
     private Exports exports(Set<Exports.Modifier> mods, String pn, String target) {
-        return ModuleDescriptor.module("foo")
+        return ModuleDescriptor.newModule("foo")
             .exports(mods, pn, Set.of(target))
             .build()
             .exports()
@@ -312,7 +324,7 @@
 
     public void testExportsExports() {
         Exports e1 = exports("p");
-        ModuleDescriptor descriptor = ModuleDescriptor.module("m").exports(e1).build();
+        ModuleDescriptor descriptor = ModuleDescriptor.newModule("m").exports(e1).build();
         Exports e2 = descriptor.exports().iterator().next();
         assertEquals(e1, e2);
     }
@@ -341,7 +353,7 @@
         targets.add("bar");
         targets.add("gus");
         Exports e
-            = ModuleDescriptor.module("foo")
+            = ModuleDescriptor.newModule("foo")
                 .exports("p", targets)
                 .build()
                 .exports()
@@ -380,69 +392,80 @@
     @Test(expectedExceptions = IllegalStateException.class)
     public void testExportsWithDuplicate1() {
         Exports e = exports("p");
-        ModuleDescriptor.module("foo").exports(e).exports(e);
+        ModuleDescriptor.newModule("foo").exports(e).exports(e);
     }
 
     @Test(expectedExceptions = IllegalStateException.class)
     public void testExportsWithDuplicate2() {
-        ModuleDescriptor.module("foo").exports("p").exports("p");
-    }
-
-    @Test(expectedExceptions = IllegalStateException.class)
-    public void testExportsOnContainedPackage() {
-        ModuleDescriptor.module("foo").contains("p").exports("p");
-    }
-
-    @Test(expectedExceptions = IllegalStateException.class)
-    public void testExportsToTargetOnContainedPackage() {
-        ModuleDescriptor.module("foo").contains("p").exports("p", Set.of("bar"));
+        ModuleDescriptor.newModule("foo").exports("p").exports("p");
     }
 
     @Test(expectedExceptions = IllegalArgumentException.class )
     public void testExportsWithEmptySet() {
-        ModuleDescriptor.module("foo").exports("p", Collections.emptySet());
+        ModuleDescriptor.newModule("foo").exports("p", Collections.emptySet());
     }
 
     @Test(dataProvider = "invalidjavaidentifiers",
           expectedExceptions = IllegalArgumentException.class )
     public void testExportsWithBadName(String pn, String ignore) {
-        ModuleDescriptor.module("foo").exports(pn);
+        ModuleDescriptor.newModule("foo").exports(pn);
     }
 
     @Test(expectedExceptions = NullPointerException.class )
     public void testExportsWithNullExports() {
-        ModuleDescriptor.module("foo").exports((Exports) null);
+        ModuleDescriptor.newModule("foo").exports((Exports) null);
     }
 
     @Test(expectedExceptions = NullPointerException.class )
     public void testExportsWithNullTargets() {
-        ModuleDescriptor.module("foo").exports("p", (Set<String>) null);
+        ModuleDescriptor.newModule("foo").exports("p", (Set<String>) null);
     }
 
-    public void testExportsEqualsAndHashCode() {
-        Exports e1, e2;
+    public void testExportsCompare() {
+        Exports e1 = exports("p");
+        Exports e2 = exports("p");
+        assertEquals(e1, e2);
+        assertTrue(e1.hashCode() == e2.hashCode());
+        assertTrue(e1.compareTo(e2) == 0);
+        assertTrue(e2.compareTo(e1) == 0);
+    }
 
-        e1 = exports("p");
-        e2 = exports("p");
+    public void testExportsCompareWithSameModifiers() {
+        Exports e1 = exports(Set.of(Exports.Modifier.SYNTHETIC), "p");
+        Exports e2 = exports(Set.of(Exports.Modifier.SYNTHETIC), "p");
         assertEquals(e1, e2);
         assertTrue(e1.hashCode() == e2.hashCode());
+        assertTrue(e1.compareTo(e2) == 0);
+        assertTrue(e2.compareTo(e1) == 0);
+    }
 
-        e1 = exports(Set.of(Exports.Modifier.SYNTHETIC), "p");
-        e2 = exports(Set.of(Exports.Modifier.SYNTHETIC), "p");
+    public void testExportsCompareWithDifferentModifiers() {
+        Exports e1 = exports(Set.of(Exports.Modifier.SYNTHETIC), "p");
+        Exports e2 = exports("p");
+        assertNotEquals(e1, e2);
+        assertTrue(e1.compareTo(e2) == 1);
+        assertTrue(e2.compareTo(e1) == -1);
+    }
+
+    public void testExportsCompareWithSameTargets() {
+        Exports e1 = exports("p", "x");
+        Exports e2 = exports("p", "x");
         assertEquals(e1, e2);
         assertTrue(e1.hashCode() == e2.hashCode());
+        assertTrue(e1.compareTo(e2) == 0);
+        assertTrue(e2.compareTo(e1) == 0);
+    }
 
-        e1 = exports("p");
-        e2 = exports("q");
+    public void testExportsCompareWithDifferentTargets() {
+        Exports e1 = exports("p", "y");
+        Exports e2 = exports("p", "x");
         assertNotEquals(e1, e2);
-
-        e1 = exports(Set.of(Exports.Modifier.SYNTHETIC), "p");
-        e2 = exports(Set.of(), "p");
-        assertNotEquals(e1, e2);
+        assertTrue(e1.compareTo(e2) == 1);
+        assertTrue(e2.compareTo(e1) == -1);
     }
 
     public void testExportsToString() {
-        String s = ModuleDescriptor.module("foo")
+        String s = ModuleDescriptor.newModule("foo")
             .exports("p1", Set.of("bar"))
             .build()
             .exports()
@@ -457,7 +480,7 @@
     // opens
 
     private Opens opens(Set<Opens.Modifier> mods, String pn) {
-        return ModuleDescriptor.module("foo")
+        return ModuleDescriptor.newModule("foo")
                 .opens(mods, pn)
                 .build()
                 .opens()
@@ -470,7 +493,7 @@
     }
 
     private Opens opens(Set<Opens.Modifier> mods, String pn, String target) {
-        return ModuleDescriptor.module("foo")
+        return ModuleDescriptor.newModule("foo")
                 .opens(mods, pn, Set.of(target))
                 .build()
                 .opens()
@@ -484,7 +507,7 @@
 
     public void testOpensOpens() {
         Opens o1 = opens("p");
-        ModuleDescriptor descriptor = ModuleDescriptor.module("m").opens(o1).build();
+        ModuleDescriptor descriptor = ModuleDescriptor.newModule("m").opens(o1).build();
         Opens o2 = descriptor.opens().iterator().next();
         assertEquals(o1, o2);
     }
@@ -513,7 +536,7 @@
         Set<String> targets = new HashSet<>();
         targets.add("bar");
         targets.add("gus");
-        Opens o = ModuleDescriptor.module("foo")
+        Opens o = ModuleDescriptor.newModule("foo")
                 .opens("p", targets)
                 .build()
                 .opens()
@@ -528,98 +551,83 @@
         assertTrue(o.targets().contains("gus"));
     }
 
-    /*
-
-    public void testOpensToAllWithModifier() {
-        Exports e = exports(Set.of(Exports.Modifier.SYNTHETIC), "p");
-        assertEquals(e, e);
-        assertTrue(e.modifiers().size() == 1);
-        assertTrue(e.modifiers().contains(Exports.Modifier.SYNTHETIC));
-        assertEquals(e.source(), "p");
-        assertFalse(e.isQualified());
-        assertTrue(e.targets().isEmpty());
-    }
-
-    public void testOpensToTargetWithModifier() {
-        Exports e = exports(Set.of(Exports.Modifier.SYNTHETIC), "p", Set.of("bar"));
-        assertEquals(e, e);
-        assertTrue(e.modifiers().size() == 1);
-        assertTrue(e.modifiers().contains(Exports.Modifier.SYNTHETIC));
-        assertEquals(e.source(), "p");
-        assertTrue(e.isQualified());
-        assertTrue(e.targets().size() == 1);
-        assertTrue(e.targets().contains("bar"));
-    }
-
-
-    */
-
     @Test(expectedExceptions = IllegalStateException.class)
     public void testOpensWithDuplicate1() {
         Opens o = opens("p");
-        ModuleDescriptor.module("foo").opens(o).opens(o);
+        ModuleDescriptor.newModule("foo").opens(o).opens(o);
     }
 
     @Test(expectedExceptions = IllegalStateException.class)
     public void testOpensWithDuplicate2() {
-        ModuleDescriptor.module("foo").opens("p").opens("p");
-    }
-
-    @Test(expectedExceptions = IllegalStateException.class)
-    public void testOpensOnContainedPackage() {
-        ModuleDescriptor.module("foo").contains("p").opens("p");
-    }
-
-    @Test(expectedExceptions = IllegalStateException.class)
-    public void testOpensToTargetOnContainedPackage() {
-        ModuleDescriptor.module("foo").contains("p").opens("p", Set.of("bar"));
+        ModuleDescriptor.newModule("foo").opens("p").opens("p");
     }
 
     @Test(expectedExceptions = IllegalArgumentException.class )
     public void testOpensWithEmptySet() {
-        ModuleDescriptor.module("foo").opens("p", Collections.emptySet());
+        ModuleDescriptor.newModule("foo").opens("p", Collections.emptySet());
     }
 
     @Test(dataProvider = "invalidjavaidentifiers",
             expectedExceptions = IllegalArgumentException.class )
     public void testOpensWithBadName(String pn, String ignore) {
-        ModuleDescriptor.module("foo").opens(pn);
+        ModuleDescriptor.newModule("foo").opens(pn);
     }
 
     @Test(expectedExceptions = NullPointerException.class )
     public void testOpensWithNullExports() {
-        ModuleDescriptor.module("foo").opens((Opens) null);
+        ModuleDescriptor.newModule("foo").opens((Opens) null);
     }
 
     @Test(expectedExceptions = NullPointerException.class )
     public void testOpensWithNullTargets() {
-        ModuleDescriptor.module("foo").opens("p", (Set<String>) null);
+        ModuleDescriptor.newModule("foo").opens("p", (Set<String>) null);
+    }
+
+    public void testOpensCompare() {
+        Opens o1 = opens("p");
+        Opens o2 = opens("p");
+        assertEquals(o1, o2);
+        assertTrue(o1.hashCode() == o2.hashCode());
+        assertTrue(o1.compareTo(o2) == 0);
+        assertTrue(o2.compareTo(o1) == 0);
+    }
+
+    public void testOpensCompareWithSameModifiers() {
+        Opens o1 = opens(Set.of(Opens.Modifier.SYNTHETIC), "p");
+        Opens o2 = opens(Set.of(Opens.Modifier.SYNTHETIC), "p");
+        assertEquals(o1, o2);
+        assertTrue(o1.hashCode() == o2.hashCode());
+        assertTrue(o1.compareTo(o2) == 0);
+        assertTrue(o2.compareTo(o1) == 0);
     }
 
-    public void testOpensEqualsAndHashCode() {
-        Opens o1, o2;
+    public void testOpensCompareWithDifferentModifiers() {
+        Opens o1 = opens(Set.of(Opens.Modifier.SYNTHETIC), "p");
+        Opens o2 = opens("p");
+        assertNotEquals(o1, o2);
+        assertTrue(o1.compareTo(o2) == 1);
+        assertTrue(o2.compareTo(o1) == -1);
+    }
 
-        o1 = opens("p");
-        o2 = opens("p");
-        assertEquals(o1, o2);
-        assertTrue(o1.hashCode() == o1.hashCode());
-
-        o1 = opens(Set.of(Opens.Modifier.SYNTHETIC), "p");
-        o2 = opens(Set.of(Opens.Modifier.SYNTHETIC), "p");
+    public void testOpensCompareWithSameTargets() {
+        Opens o1 = opens("p", "x");
+        Opens o2 = opens("p", "x");
         assertEquals(o1, o2);
         assertTrue(o1.hashCode() == o2.hashCode());
+        assertTrue(o1.compareTo(o2) == 0);
+        assertTrue(o2.compareTo(o1) == 0);
+    }
 
-        o1 = opens("p");
-        o2 = opens("q");
+    public void testOpensCompareWithDifferentTargets() {
+        Opens o1 = opens("p", "y");
+        Opens o2 = opens("p", "x");
         assertNotEquals(o1, o2);
-
-        o1 = opens(Set.of(Opens.Modifier.SYNTHETIC), "p");
-        o2 = opens(Set.of(), "p");
-        assertNotEquals(o1, o2);
+        assertTrue(o1.compareTo(o2) == 1);
+        assertTrue(o2.compareTo(o1) == -1);
     }
 
     public void testOpensToString() {
-        String s = ModuleDescriptor.module("foo")
+        String s = ModuleDescriptor.newModule("foo")
                 .opens("p1", Set.of("bar"))
                 .build()
                 .opens()
@@ -635,7 +643,7 @@
 
     public void testUses() {
         Set<String> uses
-            = ModuleDescriptor.module("foo")
+            = ModuleDescriptor.newModule("foo")
                 .uses("p.S")
                 .uses("q.S")
                 .build()
@@ -647,30 +655,44 @@
 
     @Test(expectedExceptions = IllegalStateException.class)
     public void testUsesWithDuplicate() {
-        ModuleDescriptor.module("foo").uses("p.S").uses("p.S");
+        ModuleDescriptor.newModule("foo").uses("p.S").uses("p.S");
+    }
+
+    @Test(expectedExceptions = IllegalArgumentException.class)
+    public void testUsesWithSimpleIdentifier() {
+        ModuleDescriptor.newModule("foo").uses("S");
     }
 
     @Test(dataProvider = "invalidjavaidentifiers",
           expectedExceptions = IllegalArgumentException.class )
     public void testUsesWithBadName(String service, String ignore) {
-        ModuleDescriptor.module("foo").uses(service);
+        ModuleDescriptor.newModule("foo").uses(service);
     }
 
 
     // provides
 
     private Provides provides(String st, String pc) {
-        return ModuleDescriptor.module("foo")
-            .provides(st, pc)
+        return ModuleDescriptor.newModule("foo")
+            .provides(st, List.of(pc))
             .build()
             .provides()
             .iterator()
             .next();
     }
 
+    private Provides provides(String st, List<String> pns) {
+        return ModuleDescriptor.newModule("foo")
+                .provides(st, pns)
+                .build()
+                .provides()
+                .iterator()
+                .next();
+    }
+
     public void testProvidesWithProvides() {
         Provides p1 = provides("p.S", "q.S1");
-        ModuleDescriptor descriptor = ModuleDescriptor.module("m")
+        ModuleDescriptor descriptor = ModuleDescriptor.newModule("m")
                 .provides(p1)
                 .build();
         Provides p2 = descriptor.provides().iterator().next();
@@ -679,7 +701,7 @@
 
 
     public void testProvides() {
-        Set<Provides> set = ModuleDescriptor.module("foo")
+        Set<Provides> set = ModuleDescriptor.newModule("foo")
                 .provides("p.S", List.of("q.P1", "q.P2"))
                 .build()
                 .provides();
@@ -696,59 +718,86 @@
     @Test(expectedExceptions = IllegalStateException.class )
     public void testProvidesWithDuplicateProvides() {
         Provides p = provides("p.S", "q.S2");
-        ModuleDescriptor.module("m").provides("p.S", "q.S1").provides(p);
+        ModuleDescriptor.newModule("m").provides("p.S", List.of("q.S1")).provides(p);
     }
 
     @Test(expectedExceptions = IllegalArgumentException.class )
     public void testProvidesWithEmptySet() {
-        ModuleDescriptor.module("foo").provides("p.Service", Collections.emptyList());
+        ModuleDescriptor.newModule("foo").provides("p.Service", Collections.emptyList());
+    }
+
+    @Test(expectedExceptions = IllegalArgumentException.class )
+    public void testProvidesWithSimpleIdentifier1() {
+        ModuleDescriptor.newModule("foo").provides("S", List.of("q.P"));
+    }
+
+    @Test(expectedExceptions = IllegalArgumentException.class )
+    public void testProvidesWithSimpleIdentifier2() {
+        ModuleDescriptor.newModule("foo").provides("p.S", List.of("P"));
     }
 
     @Test(dataProvider = "invalidjavaidentifiers",
           expectedExceptions = IllegalArgumentException.class )
     public void testProvidesWithBadService(String service, String ignore) {
-        ModuleDescriptor.module("foo").provides(service, "p.Provider");
+        ModuleDescriptor.newModule("foo").provides(service, List.of("p.Provider"));
     }
 
     @Test(dataProvider = "invalidjavaidentifiers",
           expectedExceptions = IllegalArgumentException.class )
     public void testProvidesWithBadProvider(String provider, String ignore) {
-        ModuleDescriptor.module("foo").provides("p.Service", provider);
+        List<String> names = new ArrayList<>(); // allows nulls
+        names.add(provider);
+        ModuleDescriptor.newModule("foo").provides("p.Service", names);
     }
 
     @Test(expectedExceptions = NullPointerException.class )
     public void testProvidesWithNullProvides() {
-        ModuleDescriptor.module("foo").provides((Provides) null);
+        ModuleDescriptor.newModule("foo").provides((Provides) null);
     }
 
     @Test(expectedExceptions = NullPointerException.class )
     public void testProvidesWithNullProviders() {
-        ModuleDescriptor.module("foo").provides("p.S", (List<String>) null);
+        ModuleDescriptor.newModule("foo").provides("p.S", (List<String>) null);
     }
 
-    public void testProvidesEqualsAndHashCode() {
-        Provides p1, p2;
-
-        p1 = provides("p.S", "q.S1");
-        p2 = provides("p.S", "q.S1");
+    public void testProvidesCompare() {
+        Provides p1 = provides("p.S", "q.S1");
+        Provides p2 = provides("p.S", "q.S1");
         assertEquals(p1, p2);
         assertTrue(p1.hashCode() == p2.hashCode());
+        assertTrue(p1.compareTo(p2) == 0);
+        assertTrue(p2.compareTo(p1) == 0);
+    }
 
-        p1 = provides("p.S", "q.S1");
-        p2 = provides("p.S", "q.S2");
+    public void testProvidesCompareWithDifferentService() {
+        Provides p1 = provides("p.S2", "q.S1");
+        Provides p2 = provides("p.S1", "q.S1");
         assertNotEquals(p1, p2);
-
-        p1 = provides("p.S", "q.S1");
-        p2 = provides("p.S2", "q.S1");
-        assertNotEquals(p1, p2);
+        assertTrue(p1.compareTo(p2) == 1);
+        assertTrue(p2.compareTo(p1) == -1);
     }
 
-    // contains
+    public void testProvidesCompareWithDifferentProviders1() {
+        Provides p1 = provides("p.S", "q.S2");
+        Provides p2 = provides("p.S", "q.S1");
+        assertNotEquals(p1, p2);
+        assertTrue(p1.compareTo(p2) == 1);
+        assertTrue(p2.compareTo(p1) == -1);
+    }
 
-    public void testContains() {
-        Set<String> packages = ModuleDescriptor.module("foo")
-                .contains("p")
-                .contains("q")
+    public void testProvidesCompareWithDifferentProviders2() {
+        Provides p1 = provides("p.S", List.of("q.S1", "q.S2"));
+        Provides p2 = provides("p.S", "q.S1");
+        assertNotEquals(p1, p2);
+        assertTrue(p1.compareTo(p2) == 1);
+        assertTrue(p2.compareTo(p1) == -1);
+    }
+
+    // packages
+
+    public void testPackages1() {
+        Set<String> packages = ModuleDescriptor.newModule("foo")
+                .packages(Set.of("p", "q"))
                 .build()
                 .packages();
         assertTrue(packages.size() == 2);
@@ -756,37 +805,10 @@
         assertTrue(packages.contains("q"));
     }
 
-    public void testContainsWithEmptySet() {
-        Set<String> packages = ModuleDescriptor.module("foo")
-                .contains(Collections.emptySet())
-                .build()
-                .packages();
-        assertTrue(packages.size() == 0);
-    }
-
-    @Test(expectedExceptions = IllegalStateException.class)
-    public void testContainsWithDuplicate() {
-        ModuleDescriptor.module("foo").contains("p").contains("p");
-    }
-
-    @Test(expectedExceptions = IllegalStateException.class)
-    public void testContainsWithExportedPackage() {
-        ModuleDescriptor.module("foo").exports("p").contains("p");
-    }
-
-    @Test(dataProvider = "invalidjavaidentifiers",
-          expectedExceptions = IllegalArgumentException.class )
-    public void testContainsWithBadName(String pn, String ignore) {
-        ModuleDescriptor.module("foo").contains(pn);
-    }
-
-
-    // packages
-
-    public void testPackages() {
-        Set<String> packages = ModuleDescriptor.module("foo")
-                .exports("p")
-                .contains("q")
+    public void testPackages2() {
+        Set<String> packages = ModuleDescriptor.newModule("foo")
+                .packages(Set.of("p"))
+                .packages(Set.of("q"))
                 .build()
                 .packages();
         assertTrue(packages.size() == 2);
@@ -795,17 +817,135 @@
     }
 
 
+    public void testPackagesWithEmptySet() {
+        Set<String> packages = ModuleDescriptor.newModule("foo")
+                .packages(Collections.emptySet())
+                .build()
+                .packages();
+        assertTrue(packages.size() == 0);
+    }
+
+    public void testPackagesDuplicate() {
+        Set<String> packages = ModuleDescriptor.newModule("foo")
+                .packages(Set.of("p"))
+                .packages(Set.of("p"))
+                .build()
+                .packages();
+        assertTrue(packages.size() == 1);
+        assertTrue(packages.contains("p"));
+    }
+
+    public void testPackagesAndExportsPackage1() {
+        Set<String> packages = ModuleDescriptor.newModule("foo")
+                .packages(Set.of("p"))
+                .exports("p")
+                .build()
+                .packages();
+        assertTrue(packages.size() == 1);
+        assertTrue(packages.contains("p"));
+    }
+
+    public void testPackagesAndExportsPackage2() {
+        Set<String> packages = ModuleDescriptor.newModule("foo")
+                .exports("p")
+                .packages(Set.of("p"))
+                .build()
+                .packages();
+        assertTrue(packages.size() == 1);
+        assertTrue(packages.contains("p"));
+    }
+
+    public void testPackagesAndOpensPackage1() {
+        Set<String> packages = ModuleDescriptor.newModule("foo")
+                .packages(Set.of("p"))
+                .opens("p")
+                .build()
+                .packages();
+        assertTrue(packages.size() == 1);
+        assertTrue(packages.contains("p"));
+    }
+
+    public void testPackagesAndOpensPackage2() {
+        Set<String> packages = ModuleDescriptor.newModule("foo")
+                .opens("p")
+                .packages(Set.of("p"))
+                .build()
+                .packages();
+        assertTrue(packages.size() == 1);
+        assertTrue(packages.contains("p"));
+    }
+
+    public void testPackagesAndProvides1() {
+        Set<String> packages = ModuleDescriptor.newModule("foo")
+                .packages(Set.of("p"))
+                .provides("q.S", List.of("p.T"))
+                .build()
+                .packages();
+        assertTrue(packages.size() == 1);
+        assertTrue(packages.contains("p"));
+    }
+
+    public void testPackagesAndProvides2() {
+        Set<String> packages = ModuleDescriptor.newModule("foo")
+                .provides("q.S", List.of("p.T"))
+                .packages(Set.of("p"))
+                .build()
+                .packages();
+        assertTrue(packages.size() == 1);
+        assertTrue(packages.contains("p"));
+    }
+
+    public void testPackagesAndMainClass1() {
+        Set<String> packages = ModuleDescriptor.newModule("foo")
+                .packages(Set.of("p"))
+                .mainClass("p.Main")
+                .build()
+                .packages();
+        assertTrue(packages.size() == 1);
+        assertTrue(packages.contains("p"));
+    }
+
+    public void testPackagesAndMainClass2() {
+        Set<String> packages = ModuleDescriptor.newModule("foo")
+                .mainClass("p.Main")
+                .packages(Set.of("p"))
+                .build()
+                .packages();
+        assertTrue(packages.size() == 1);
+        assertTrue(packages.contains("p"));
+    }
+
+    public void testPackagesAndAll() {
+        Set<String> packages = ModuleDescriptor.newModule("foo")
+                .exports("p1")
+                .opens("p2")
+                .packages(Set.of("p3"))
+                .provides("q.S", List.of("p4.T"))
+                .mainClass("p5.Main")
+                .build()
+                .packages();
+        assertTrue(Objects.equals(packages, Set.of("p1", "p2", "p3", "p4", "p5")));
+    }
+
+    @Test(dataProvider = "invalidjavaidentifiers",
+          expectedExceptions = IllegalArgumentException.class )
+    public void testPackagesWithBadName(String pn, String ignore) {
+        Set<String> pkgs = new HashSet<>();  // allows nulls
+        pkgs.add(pn);
+        ModuleDescriptor.newModule("foo").packages(pkgs);
+    }
+
     // name
 
     public void testModuleName() {
-        String mn = ModuleDescriptor.module("foo").build().name();
+        String mn = ModuleDescriptor.newModule("foo").build().name();
         assertEquals(mn, "foo");
     }
 
     @Test(dataProvider = "invalidjavaidentifiers",
           expectedExceptions = IllegalArgumentException.class )
     public void testBadModuleName(String mn, String ignore) {
-        ModuleDescriptor.module(mn);
+        ModuleDescriptor.newModule(mn);
     }
 
 
@@ -813,7 +953,7 @@
 
     public void testVersion1() {
         Version v1 = Version.parse("1.0");
-        Version v2 = ModuleDescriptor.module("foo")
+        Version v2 = ModuleDescriptor.newModule("foo")
                 .version(v1)
                 .build()
                 .version()
@@ -823,7 +963,7 @@
 
     public void testVersion2() {
         String vs = "1.0";
-        Version v1 = ModuleDescriptor.module("foo")
+        Version v1 = ModuleDescriptor.newModule("foo")
                 .version(vs)
                 .build()
                 .version()
@@ -834,86 +974,178 @@
 
     @Test(expectedExceptions = NullPointerException.class )
     public void testNullVersion1() {
-        ModuleDescriptor.module("foo").version((Version) null);
+        ModuleDescriptor.newModule("foo").version((Version) null);
     }
 
     @Test(expectedExceptions = IllegalArgumentException.class )
     public void testNullVersion2() {
-        ModuleDescriptor.module("foo").version((String) null);
+        ModuleDescriptor.newModule("foo").version((String) null);
     }
 
     @Test(expectedExceptions = IllegalArgumentException.class )
     public void testEmptyVersion() {
-        ModuleDescriptor.module("foo").version("");
+        ModuleDescriptor.newModule("foo").version("");
     }
 
 
     // toNameAndVersion
 
     public void testToNameAndVersion() {
-        ModuleDescriptor md1 = ModuleDescriptor.module("foo").build();
+        ModuleDescriptor md1 = ModuleDescriptor.newModule("foo").build();
         assertEquals(md1.toNameAndVersion(), "foo");
 
-        ModuleDescriptor md2 = ModuleDescriptor.module("foo").version("1.0").build();
+        ModuleDescriptor md2 = ModuleDescriptor.newModule("foo").version("1.0").build();
         assertEquals(md2.toNameAndVersion(), "foo@1.0");
     }
 
 
     // open modules
 
-    public void testOpenModules() {
-        ModuleDescriptor descriptor = ModuleDescriptor.openModule("m")
-                .requires("java.base")
-                .contains("p")
+    public void testOpenModule() {
+        ModuleDescriptor descriptor = ModuleDescriptor.newOpenModule("foo")
+                .requires("bar")
+                .exports("p")
+                .provides("p.Service", List.of("q.ServiceImpl"))
                 .build();
+
+        // modifiers
+        assertTrue(descriptor.modifiers().contains(ModuleDescriptor.Modifier.OPEN));
         assertTrue(descriptor.isOpen());
-        assertTrue(descriptor.packages().size() == 1);
-        assertTrue(descriptor.packages().contains("p"));
-        assertTrue(descriptor.exports().isEmpty());
+
+        // requires
+        assertTrue(descriptor.requires().size() == 2);
+        Set<String> names = descriptor.requires()
+                .stream()
+                .map(Requires::name)
+                .collect(Collectors.toSet());
+        assertEquals(names, Set.of("bar", "java.base"));
+
+        // packages
+        assertEquals(descriptor.packages(), Set.of("p", "q"));
+
+        // exports
+        assertTrue(descriptor.exports().size() == 1);
+        names = descriptor.exports()
+                .stream()
+                .map(Exports::source)
+                .collect(Collectors.toSet());
+        assertEquals(names, Set.of("p"));
+
+        // opens
+        assertTrue(descriptor.opens().isEmpty());
     }
 
     @Test(expectedExceptions = IllegalStateException.class)
-    public void testOpensOnWeakModule1() {
-        ModuleDescriptor.openModule("foo").opens("p");
+    public void testOpensOnOpenModule1() {
+        ModuleDescriptor.newOpenModule("foo").opens("p");
     }
 
     @Test(expectedExceptions = IllegalStateException.class)
-    public void testOpensOnWeakModule2() {
-        ModuleDescriptor.openModule("foo").opens("p", Set.of("bar"));
+    public void testOpensOnOpenModule2() {
+        ModuleDescriptor.newOpenModule("foo").opens("p", Set.of("bar"));
     }
 
     public void testIsOpen() {
-        assertFalse(ModuleDescriptor.module("m").build().isOpen());
-        assertFalse(ModuleDescriptor.automaticModule("m").build().isOpen());
-        assertTrue(ModuleDescriptor.openModule("m").build().isOpen());
+        assertFalse(ModuleDescriptor.newModule("m").build().isOpen());
+        assertFalse(ModuleDescriptor.newAutomaticModule("m").build().isOpen());
+        assertTrue(ModuleDescriptor.newOpenModule("m").build().isOpen());
     }
 
 
     // automatic modules
 
+    public void testAutomaticModule() {
+        ModuleDescriptor descriptor = ModuleDescriptor.newAutomaticModule("foo")
+                .packages(Set.of("p"))
+                .provides("p.Service", List.of("q.ServiceImpl"))
+                .build();
+
+        // modifiers
+        assertTrue(descriptor.modifiers().contains(ModuleDescriptor.Modifier.AUTOMATIC));
+        assertTrue(descriptor.isAutomatic());
+
+        // requires
+        assertTrue(descriptor.requires().size() == 1);
+        Set<String> names = descriptor.requires()
+                .stream()
+                .map(Requires::name)
+                .collect(Collectors.toSet());
+        assertEquals(names, Set.of("java.base"));
+
+        // packages
+        assertEquals(descriptor.packages(), Set.of("p", "q"));
+        assertTrue(descriptor.exports().isEmpty());
+        assertTrue(descriptor.opens().isEmpty());
+    }
+
+    @Test(expectedExceptions = IllegalStateException.class)
+    public void testRequiresOnAutomaticModule() {
+        ModuleDescriptor.newAutomaticModule("foo").requires("java.base");
+    }
+
+    @Test(expectedExceptions = IllegalStateException.class)
+    public void testExportsOnAutomaticModule1() {
+        ModuleDescriptor.newAutomaticModule("foo").exports("p");
+    }
+
+    @Test(expectedExceptions = IllegalStateException.class)
+    public void testExportsOnAutomaticModule2() {
+        ModuleDescriptor.newAutomaticModule("foo").exports("p", Set.of("bar"));
+    }
+
+    @Test(expectedExceptions = IllegalStateException.class)
+    public void testOpensOnAutomaticModule1() {
+        ModuleDescriptor.newAutomaticModule("foo").opens("p");
+    }
+
+    @Test(expectedExceptions = IllegalStateException.class)
+    public void testOpensOnAutomaticModule2() {
+        ModuleDescriptor.newAutomaticModule("foo").opens("p", Set.of("bar"));
+    }
+
+    @Test(expectedExceptions = IllegalStateException.class)
+    public void testUsesOnAutomaticModule() {
+        ModuleDescriptor.newAutomaticModule("foo").uses("p.Service");
+    }
+
     public void testIsAutomatic() {
-        ModuleDescriptor descriptor1 = ModuleDescriptor.module("foo").build();
+        ModuleDescriptor descriptor1 = ModuleDescriptor.newModule("foo").build();
         assertFalse(descriptor1.isAutomatic());
 
-        ModuleDescriptor descriptor2 = ModuleDescriptor.openModule("foo").build();
+        ModuleDescriptor descriptor2 = ModuleDescriptor.newOpenModule("foo").build();
         assertFalse(descriptor2.isAutomatic());
 
-        ModuleDescriptor descriptor3 = ModuleDescriptor.automaticModule("foo").build();
+        ModuleDescriptor descriptor3 = ModuleDescriptor.newAutomaticModule("foo").build();
         assertTrue(descriptor3.isAutomatic());
     }
 
-    // isSynthetic
-    public void testIsSynthetic() {
-        assertFalse(Object.class.getModule().getDescriptor().isSynthetic());
+
+    // newModule with modifiers
+
+    public void testNewModuleToBuildAutomaticModule() {
+        Set<ModuleDescriptor.Modifier> ms = Set.of(ModuleDescriptor.Modifier.AUTOMATIC);
+        ModuleDescriptor descriptor = ModuleDescriptor.newModule("foo", ms).build();
+        assertTrue(descriptor.modifiers().equals(ms));
+        assertTrue(descriptor.isAutomatic());
+    }
 
-        ModuleDescriptor descriptor1 = ModuleDescriptor.module("foo").build();
-        assertFalse(descriptor1.isSynthetic());
+    public void testNewModuleToBuildOpenModule() {
+        Set<ModuleDescriptor.Modifier> ms = Set.of(ModuleDescriptor.Modifier.OPEN);
+        ModuleDescriptor descriptor = ModuleDescriptor.newModule("foo", ms).build();
+        assertTrue(descriptor.modifiers().equals(ms));
+        assertTrue(descriptor.isOpen());
 
-        ModuleDescriptor descriptor2 = ModuleDescriptor.openModule("foo").build();
-        assertFalse(descriptor2.isSynthetic());
+        ms = Set.of(ModuleDescriptor.Modifier.OPEN, ModuleDescriptor.Modifier.SYNTHETIC);
+        descriptor = ModuleDescriptor.newModule("foo", ms).build();
+        assertTrue(descriptor.modifiers().equals(ms));
+        assertTrue(descriptor.isOpen());
+    }
 
-        ModuleDescriptor descriptor3 = ModuleDescriptor.automaticModule("foo").build();
-        assertFalse(descriptor3.isSynthetic());
+    @Test(expectedExceptions = IllegalArgumentException.class)
+    public void testNewModuleToBuildAutomaticAndOpenModule() {
+        Set<ModuleDescriptor.Modifier> ms = Set.of(ModuleDescriptor.Modifier.AUTOMATIC,
+                                                   ModuleDescriptor.Modifier.OPEN);
+        ModuleDescriptor.newModule("foo", ms);
     }
 
 
@@ -921,14 +1153,19 @@
 
     public void testMainClass() {
         String mainClass
-            = ModuleDescriptor.module("foo").mainClass("p.Main").build().mainClass().get();
+            = ModuleDescriptor.newModule("foo").mainClass("p.Main").build().mainClass().get();
         assertEquals(mainClass, "p.Main");
     }
 
+    @Test(expectedExceptions = IllegalArgumentException.class)
+    public void testMainClassWithSimpleIdentifier() {
+        ModuleDescriptor.newModule("foo").mainClass("Main");
+    }
+
     @Test(dataProvider = "invalidjavaidentifiers",
           expectedExceptions = IllegalArgumentException.class )
     public void testMainClassWithBadName(String mainClass, String ignore) {
-        Builder builder = ModuleDescriptor.module("foo");
+        Builder builder = ModuleDescriptor.newModule("foo");
         builder.mainClass(mainClass);
     }
 
@@ -936,54 +1173,54 @@
     // osName
 
     public void testOsName() {
-        String osName = ModuleDescriptor.module("foo").osName("Linux").build().osName().get();
+        String osName = ModuleDescriptor.newModule("foo").osName("Linux").build().osName().get();
         assertEquals(osName, "Linux");
     }
 
     @Test(expectedExceptions = IllegalArgumentException.class)
     public void testNullOsName() {
-        ModuleDescriptor.module("foo").osName(null);
+        ModuleDescriptor.newModule("foo").osName(null);
     }
 
     @Test(expectedExceptions = IllegalArgumentException.class)
     public void testEmptyOsName() {
-        ModuleDescriptor.module("foo").osName("");
+        ModuleDescriptor.newModule("foo").osName("");
     }
 
 
     // osArch
 
     public void testOsArch() {
-        String osArch = ModuleDescriptor.module("foo").osName("arm").build().osName().get();
+        String osArch = ModuleDescriptor.newModule("foo").osName("arm").build().osName().get();
         assertEquals(osArch, "arm");
     }
 
     @Test(expectedExceptions = IllegalArgumentException.class)
     public void testNullOsArch() {
-        ModuleDescriptor.module("foo").osArch(null);
+        ModuleDescriptor.newModule("foo").osArch(null);
     }
 
     @Test(expectedExceptions = IllegalArgumentException.class)
     public void testEmptyOsArch() {
-        ModuleDescriptor.module("foo").osArch("");
+        ModuleDescriptor.newModule("foo").osArch("");
     }
 
 
     // osVersion
 
     public void testOsVersion() {
-        String osVersion = ModuleDescriptor.module("foo").osName("11.2").build().osName().get();
+        String osVersion = ModuleDescriptor.newModule("foo").osName("11.2").build().osName().get();
         assertEquals(osVersion, "11.2");
     }
 
     @Test(expectedExceptions = IllegalArgumentException.class)
     public void testNullOsVersion() {
-        ModuleDescriptor.module("foo").osVersion(null);
+        ModuleDescriptor.newModule("foo").osVersion(null);
     }
 
     @Test(expectedExceptions = IllegalArgumentException.class)
     public void testEmptyOsVersion() {
-        ModuleDescriptor.module("foo").osVersion("");
+        ModuleDescriptor.newModule("foo").osVersion("");
     }
 
     // reads
@@ -1023,7 +1260,7 @@
      * Test ModuleDescriptor with a packager finder
      */
     public void testReadsWithPackageFinder() throws Exception {
-        ModuleDescriptor descriptor = ModuleDescriptor.module("foo")
+        ModuleDescriptor descriptor = ModuleDescriptor.newModule("foo")
                 .requires("java.base")
                 .build();
 
@@ -1044,7 +1281,7 @@
      */
     @Test(expectedExceptions = InvalidModuleDescriptorException.class)
     public void testReadsWithBadPackageFinder() throws Exception {
-        ModuleDescriptor descriptor = ModuleDescriptor.module("foo")
+        ModuleDescriptor descriptor = ModuleDescriptor.newModule("foo")
                 .requires("java.base")
                 .exports("p")
                 .build();
@@ -1077,7 +1314,7 @@
     @Test(expectedExceptions = InvalidModuleDescriptorException.class)
     public void testReadOfJavaBaseWithRequires() {
         ModuleDescriptor descriptor
-            = ModuleDescriptor.module("java.base")
+            = ModuleDescriptor.newModule("java.base")
                 .requires("other")
                 .build();
         ByteBuffer bb = ModuleInfoWriter.toByteBuffer(descriptor);
@@ -1087,7 +1324,8 @@
     // The requires table must have an entry for java.base
     @Test(expectedExceptions = InvalidModuleDescriptorException.class)
     public void testReadWithEmptyRequires() {
-        ModuleDescriptor descriptor = ModuleDescriptor.module("m1").build();
+        ModuleDescriptor descriptor = SharedSecrets.getJavaLangModuleAccess()
+                .newModuleBuilder("m1", false, Set.of()).build();
         ByteBuffer bb = ModuleInfoWriter.toByteBuffer(descriptor);
         ModuleDescriptor.read(bb);
     }
@@ -1095,10 +1333,8 @@
     // The requires table must have an entry for java.base
     @Test(expectedExceptions = InvalidModuleDescriptorException.class)
     public void testReadWithNoRequiresBase() {
-        ModuleDescriptor descriptor
-            = ModuleDescriptor.module("m1")
-                .requires("m2")
-                .build();
+        ModuleDescriptor descriptor = SharedSecrets.getJavaLangModuleAccess()
+                .newModuleBuilder("m1", false, Set.of()).requires("m2").build();
         ByteBuffer bb = ModuleInfoWriter.toByteBuffer(descriptor);
         ModuleDescriptor.read(bb);
     }
@@ -1138,22 +1374,50 @@
     // equals/hashCode/compareTo/toString
 
     public void testEqualsAndHashCode() {
-        ModuleDescriptor md1 = ModuleDescriptor.module("foo").build();
-        ModuleDescriptor md2 = ModuleDescriptor.module("foo").build();
+        ModuleDescriptor md1 = ModuleDescriptor.newModule("m").build();
+        ModuleDescriptor md2 = ModuleDescriptor.newModule("m").build();
         assertEquals(md1, md1);
         assertEquals(md1.hashCode(), md2.hashCode());
+        assertTrue(md1.compareTo(md2) == 0);
+        assertTrue(md2.compareTo(md1) == 0);
     }
 
-    public void testCompare() {
-        ModuleDescriptor md1 = ModuleDescriptor.module("foo").build();
-        ModuleDescriptor md2 = ModuleDescriptor.module("bar").build();
-        int n = "foo".compareTo("bar");
-        assertTrue(md1.compareTo(md2) == n);
-        assertTrue(md2.compareTo(md1) == -n);
+    @DataProvider(name = "sortedModuleDescriptors")
+    public Object[][] sortedModuleDescriptors() {
+        return new Object[][]{
+
+            { ModuleDescriptor.newModule("m2").build(),
+              ModuleDescriptor.newModule("m1").build()
+            },
+
+            { ModuleDescriptor.newModule("m").version("2").build(),
+              ModuleDescriptor.newModule("m").version("1").build()
+            },
+
+            { ModuleDescriptor.newModule("m").version("1").build(),
+              ModuleDescriptor.newModule("m").build()
+            },
+
+            { ModuleDescriptor.newOpenModule("m").build(),
+              ModuleDescriptor.newModule("m").build()
+            },
+
+        };
+    }
+
+    @Test(dataProvider = "sortedModuleDescriptors")
+    public void testCompare(ModuleDescriptor md1, ModuleDescriptor md2) {
+        assertNotEquals(md1, md2);
+        assertTrue(md1.compareTo(md2) == 1);
+        assertTrue(md2.compareTo(md1) == -1);
     }
 
     public void testToString() {
-        String s = ModuleDescriptor.module("m1").requires("m2").exports("p1").build().toString();
+        String s = ModuleDescriptor.newModule("m1")
+                .requires("m2")
+                .exports("p1")
+                .build()
+                .toString();
         assertTrue(s.contains("m1"));
         assertTrue(s.contains("m2"));
         assertTrue(s.contains("p1"));
--- a/jdk/test/java/lang/module/ModuleFinderTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/module/ModuleFinderTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -471,37 +471,11 @@
      * Test ModuleFinder.of with a file path to a directory containing a file
      * that will not be recognized as a module.
      */
-    public void testOfWithUnrecognizedEntryInDirectory() throws Exception {
+    public void testOfWithUnrecognizedEntryInDirectory1() throws Exception {
         Path dir = Files.createTempDirectory(USER_DIR, "mods");
         Files.createTempFile(dir, "m", ".junk");
 
         ModuleFinder finder = ModuleFinder.of(dir);
-        try {
-            finder.find("java.rhubarb");
-            assertTrue(false);
-        } catch (FindException e) {
-            // expected
-        }
-
-        finder = ModuleFinder.of(dir);
-        try {
-            finder.findAll();
-            assertTrue(false);
-        } catch (FindException e) {
-            // expected
-        }
-    }
-
-
-    /**
-     * Test ModuleFinder.of with a file path to a directory containing a file
-     * starting with ".", the file should be ignored.
-     */
-    public void testOfWithHiddenEntryInDirectory() throws Exception {
-        Path dir = Files.createTempDirectory(USER_DIR, "mods");
-        Files.createTempFile(dir, ".marker", "");
-
-        ModuleFinder finder = ModuleFinder.of(dir);
         assertFalse(finder.find("java.rhubarb").isPresent());
 
         finder = ModuleFinder.of(dir);
@@ -510,6 +484,24 @@
 
 
     /**
+     * Test ModuleFinder.of with a file path to a directory containing a file
+     * that will not be recognized as a module.
+     */
+    public void testOfWithUnrecognizedEntryInDirectory2() throws Exception {
+        Path dir = Files.createTempDirectory(USER_DIR, "mods");
+        createModularJar(dir.resolve("m1.jar"), "m1");
+        Files.createTempFile(dir, "m2", ".junk");
+
+        ModuleFinder finder = ModuleFinder.of(dir);
+        assertTrue(finder.find("m1").isPresent());
+        assertFalse(finder.find("m2").isPresent());
+
+        finder = ModuleFinder.of(dir);
+        assertTrue(finder.findAll().size() == 1);
+    }
+
+
+    /**
      * Test ModuleFinder.of with a directory that contains two
      * versions of the same module
      */
@@ -748,7 +740,7 @@
             vs = mid.substring(i+1);
         }
         ModuleDescriptor.Builder builder
-            = ModuleDescriptor.module(mn).requires("java.base");
+            = ModuleDescriptor.newModule(mn).requires("java.base");
         if (vs != null)
             builder.version(vs);
         return builder.build();
--- a/jdk/test/java/lang/module/ModuleNamesTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/module/ModuleNamesTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -235,7 +235,7 @@
      */
     private Builder newBuilder(String mn) {
         return SharedSecrets.getJavaLangModuleAccess()
-                            .newModuleBuilder(mn, false, false, false);
+                            .newModuleBuilder(mn, false, Set.of());
     }
 
     /**
--- a/jdk/test/java/lang/module/ModuleReader/ModuleReaderTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/module/ModuleReader/ModuleReaderTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -79,14 +79,52 @@
         "java/lang/Object.class"
     };
 
+    // resource names that should not be found in the base module
+    private static final String[] BAD_BASE_RESOURCES = {
+        "NotFound",
+        "java",
+        "/java",
+        "//java",
+        "java/",
+        "java/lang",
+        "/java/lang",
+        "//java/lang",
+        "java/lang/",
+        "java//lang",
+        "/java/lang/Object.class",
+        "//java/lang/Object.class",
+        "java/lang/Object.class/",
+        "java//lang//Object.class",
+        "./java/lang/Object.class",
+        "java/./lang/Object.class",
+        "java/lang/./Object.class",
+        "../java/lang/Object.class",
+        "java/../lang/Object.class",
+        "java/lang/../Object.class",
+    };
+
     // resources in test module (can't use module-info.class as a test
     // resource as it will be modified by the jmod tool)
     private static final String[] TEST_RESOURCES = {
         "p/Main.class"
     };
 
-    // a resource that is not in the base or test module
-    private static final String NOT_A_RESOURCE = "NotAResource";
+    // resource names that should not be found in the test module
+    private static final String[] BAD_TEST_RESOURCES = {
+        "NotFound",
+        "p",
+        "/p",
+        "//p",
+        "p/",
+        "/p/Main.class",
+        "//p/Main.class",
+        "p/Main.class/",
+        "p//Main.class",
+        "./p/Main.class",
+        "p/./Main.class",
+        "../p/Main.class",
+        "p/../p/Main.class"
+    };
 
 
     @BeforeTest
@@ -126,10 +164,11 @@
             }
 
             // test "not found"
-            assertFalse(reader.find(NOT_A_RESOURCE).isPresent());
-            assertFalse(reader.open(NOT_A_RESOURCE).isPresent());
-            assertFalse(reader.read(NOT_A_RESOURCE).isPresent());
-
+            for (String name : BAD_BASE_RESOURCES) {
+                assertFalse(reader.find(name).isPresent());
+                assertFalse(reader.open(name).isPresent());
+                assertFalse(reader.read(name).isPresent());
+            }
 
             // test nulls
             try {
@@ -216,7 +255,7 @@
      */
     void test(Path mp) throws IOException {
 
-        ModuleFinder finder = new ModulePath(Runtime.version(), true, mp);
+        ModuleFinder finder = ModulePath.of(Runtime.version(), true, mp);
         ModuleReference mref = finder.find(TEST_MODULE).get();
         ModuleReader reader = mref.open();
 
@@ -236,9 +275,11 @@
             }
 
             // test "not found"
-            assertFalse(reader.find(NOT_A_RESOURCE).isPresent());
-            assertFalse(reader.open(NOT_A_RESOURCE).isPresent());
-            assertFalse(reader.read(NOT_A_RESOURCE).isPresent());
+            for (String name : BAD_TEST_RESOURCES) {
+                assertFalse(reader.find(name).isPresent());
+                assertFalse(reader.open(name).isPresent());
+                assertFalse(reader.read(name).isPresent());
+            }
 
             // test nulls
             try {
--- a/jdk/test/java/lang/module/ModuleReferenceTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/module/ModuleReferenceTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -31,6 +31,7 @@
 import java.lang.module.ModuleReader;
 import java.lang.module.ModuleReference;
 import java.net.URI;
+import java.util.Set;
 
 import org.testng.annotations.Test;
 import static org.testng.Assert.*;
@@ -49,10 +50,10 @@
 
     public void testBasic() throws Exception {
         ModuleDescriptor descriptor
-            = ModuleDescriptor.module("m")
+            = ModuleDescriptor.newModule("m")
                 .exports("p")
                 .exports("q")
-                .contains("p.internal")
+                .packages(Set.of("p.internal"))
                 .build();
 
         URI uri = URI.create("module:/m");
@@ -71,7 +72,7 @@
 
     public void testNullLocation() {
         ModuleDescriptor descriptor
-            = ModuleDescriptor.module("m")
+            = ModuleDescriptor.newModule("m")
                 .exports("p")
                 .build();
         ModuleReference mref = newModuleReference(descriptor, null);
--- a/jdk/test/java/lang/module/MultiReleaseJarTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/module/MultiReleaseJarTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -65,7 +65,7 @@
 
     private static final String MODULE_INFO = "module-info.class";
 
-    private static final int RELEASE = Runtime.version().major();
+    private static final int VERSION = Runtime.version().major();
 
     // are multi-release JARs enabled?
     private static final boolean MULTI_RELEASE;
@@ -80,7 +80,7 @@
     public void testBasic() throws Exception {
         String name = "m1";
 
-        ModuleDescriptor descriptor = ModuleDescriptor.module(name)
+        ModuleDescriptor descriptor = ModuleDescriptor.newModule(name)
                 .requires("java.base")
                 .build();
 
@@ -88,8 +88,8 @@
                 .moduleInfo("module-info.class", descriptor)
                 .resource("p/Main.class")
                 .resource("p/Helper.class")
-                .resource("META-INF/versions/9/p/Helper.class")
-                .resource("META-INF/versions/9/p/internal/Helper9.class")
+                .resource("META-INF/versions/" + VERSION + "/p/Helper.class")
+                .resource("META-INF/versions/" + VERSION + "/p/internal/Helper.class")
                 .build();
 
         // find the module
@@ -117,12 +117,12 @@
     public void testModuleInfoInVersionedSection() throws Exception {
         String name = "m1";
 
-        ModuleDescriptor descriptor1 = ModuleDescriptor.module(name)
+        ModuleDescriptor descriptor1 = ModuleDescriptor.newModule(name)
                 .requires("java.base")
                 .build();
 
         // module descriptor for versioned section
-        ModuleDescriptor descriptor2 = ModuleDescriptor.module(name)
+        ModuleDescriptor descriptor2 = ModuleDescriptor.newModule(name)
                 .requires("java.base")
                 .requires("jdk.unsupported")
                 .build();
@@ -131,9 +131,9 @@
                 .moduleInfo(MODULE_INFO, descriptor1)
                 .resource("p/Main.class")
                 .resource("p/Helper.class")
-                .moduleInfo("META-INF/versions/9/" + MODULE_INFO, descriptor2)
-                .resource("META-INF/versions/9/p/Helper.class")
-                .resource("META-INF/versions/9/p/internal/Helper9.class")
+                .moduleInfo("META-INF/versions/" + VERSION + "/" + MODULE_INFO, descriptor2)
+                .resource("META-INF/versions/" + VERSION + "/p/Helper.class")
+                .resource("META-INF/versions/" + VERSION + "/p/internal/Helper.class")
                 .build();
 
         // find the module
@@ -161,8 +161,8 @@
         Path jar = new JarBuilder(name)
                 .resource("p/Main.class")
                 .resource("p/Helper.class")
-                .resource("META-INF/versions/9/p/Helper.class")
-                .resource("META-INF/versions/9/p/internal/Helper9.class")
+                .resource("META-INF/versions/" + VERSION + "/p/Helper.class")
+                .resource("META-INF/versions/" + VERSION + "/p/internal/Helper.class")
                 .build();
 
         // find the module
@@ -188,19 +188,19 @@
     public void testModuleReader() throws Exception {
         String name = "m1";
 
-        ModuleDescriptor descriptor1 = ModuleDescriptor.module(name)
+        ModuleDescriptor descriptor1 = ModuleDescriptor.newModule(name)
                 .requires("java.base")
                 .build();
 
         // module descriptor for versioned section
-        ModuleDescriptor descriptor2 = ModuleDescriptor.module(name)
+        ModuleDescriptor descriptor2 = ModuleDescriptor.newModule(name)
                 .requires("java.base")
                 .requires("jdk.unsupported")
                 .build();
 
         Path jar = new JarBuilder(name)
                 .moduleInfo(MODULE_INFO, descriptor1)
-                .moduleInfo("META-INF/versions/9/" + MODULE_INFO, descriptor2)
+                .moduleInfo("META-INF/versions/" + VERSION + "/" + MODULE_INFO, descriptor2)
                 .build();
 
         // find the module
@@ -243,7 +243,7 @@
 
             String expectedTail = "!/";
             if (MULTI_RELEASE)
-                expectedTail += "META-INF/versions/" + RELEASE + "/";
+                expectedTail += "META-INF/versions/" + VERSION + "/";
             expectedTail += MODULE_INFO;
             assertTrue(uri.toString().endsWith(expectedTail));
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/reflect/AccessibleObject/CanAccessTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,138 @@
+/*
+ * Copyright (c) 2017, 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
+ * @build CanAccessTest
+ * @modules java.base/jdk.internal.misc:+open
+ * @run testng CanAccessTest
+ * @summary Test AccessibleObject::canAccess method
+ */
+
+import java.lang.reflect.Constructor;
+import java.lang.reflect.Method;
+import java.security.SecureClassLoader;
+
+import jdk.internal.misc.Unsafe;
+import org.testng.annotations.Test;
+import static org.testng.Assert.*;
+
+@Test
+public class CanAccessTest {
+    private static Unsafe INSTANCE = Unsafe.getUnsafe();
+
+    /**
+     * null object parameter for Constructor
+     */
+    public void testConstructor() throws Exception {
+        Constructor<?> ctor = Unsafe.class.getDeclaredConstructor();
+        assertFalse(ctor.canAccess(null));
+        assertTrue(ctor.trySetAccessible());
+
+        try {
+            // non-null object parameter
+            ctor.canAccess(INSTANCE);
+            assertTrue(false);
+        } catch (IllegalArgumentException expected) {}
+    }
+
+    /**
+     * Test protected constructors
+     */
+    public void testProtectedConstructor() throws Exception {
+        TestLoader.testProtectedConstructorNonOpenedPackage();
+
+        Constructor<?> ctor = TestLoader.class.getDeclaredConstructor();
+        assertTrue(ctor.canAccess(null));
+    }
+
+    /**
+     * null object parameter  for static members
+     */
+    public void testStaticMember() throws Exception {
+        Method m = Unsafe.class.getDeclaredMethod("throwIllegalAccessError");
+        assertFalse(m.canAccess(null));
+        assertTrue(m.trySetAccessible());
+
+        try {
+            // non-null object parameter
+            m.canAccess(INSTANCE);
+            assertTrue(false);
+        } catch (IllegalArgumentException expected) { }
+    }
+
+    /**
+     * Test protected static
+     */
+    public void testProtectedStatic() throws Exception {
+        Method m = TestLoader.testProtectedStatic();
+        assertFalse(m.canAccess(null));
+    }
+
+    /**
+     * the specified object must be an instance of the declaring class
+     * for instance members
+     */
+    public void testInstanceMethod() throws Exception {
+        Method m = Unsafe.class.getDeclaredMethod("addressSize0");
+        assertFalse(m.canAccess(INSTANCE));
+
+        try {
+            m.canAccess(null);
+            assertTrue(false);
+        } catch (IllegalArgumentException expected) { }
+    }
+
+    /**
+     * the specified object must be an instance of the declaring class
+     * for instance members
+     */
+    public void testInvalidInstanceObject() throws Exception {
+        Class<?> clazz = Class.forName("sun.security.x509.X500Name");
+        Method m = clazz.getDeclaredMethod("size");
+
+        try {
+            m.canAccess(INSTANCE);
+            assertTrue(false);
+        } catch (IllegalArgumentException expected) { }
+    }
+
+
+    static class TestLoader extends SecureClassLoader {
+        public static Method testProtectedStatic() throws Exception {
+            Method m = ClassLoader.class.getDeclaredMethod("registerAsParallelCapable");
+            assertTrue(m.canAccess(null));
+            return m;
+        }
+
+        protected TestLoader() throws Exception {
+            Constructor<?> ctor = SecureClassLoader.class.getDeclaredConstructor();
+            assertFalse(ctor.canAccess(null));
+            assertFalse(ctor.trySetAccessible());
+        }
+
+        public static void testProtectedConstructorNonOpenedPackage() throws Exception {
+            new TestLoader();
+        }
+    }
+}
--- a/jdk/test/java/lang/reflect/AccessibleObject/ModuleSetAccessibleTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/reflect/AccessibleObject/ModuleSetAccessibleTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -30,7 +30,6 @@
  * @summary Test java.lang.reflect.AccessibleObject with modules
  */
 
-import java.lang.module.ModuleDescriptor;
 import java.lang.reflect.AccessibleObject;
 import java.lang.reflect.Constructor;
 import java.lang.reflect.Field;
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/reflect/AccessibleObject/TrySetAccessibleTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,201 @@
+/*
+ * Copyright (c) 2017, 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
+ * @build TrySetAccessibleTest
+ * @modules java.base/java.lang:open
+ *          java.base/jdk.internal.perf
+ *          java.base/jdk.internal.misc:+open
+ * @run testng TrySetAccessibleTest
+ * @summary Test AccessibleObject::trySetAccessible method
+ */
+
+import java.lang.reflect.AccessibleObject;
+import java.lang.reflect.Constructor;
+import java.lang.reflect.Field;
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+
+import jdk.internal.misc.Unsafe;
+import jdk.internal.perf.Perf;
+
+import org.testng.annotations.Test;
+import static org.testng.Assert.*;
+
+@Test
+public class TrySetAccessibleTest {
+    /**
+     * Invoke a private constructor on a public class in an exported package
+     */
+    public void testPrivateConstructorInExportedPackage() throws Exception {
+        Constructor<?> ctor = Perf.class.getDeclaredConstructor();
+
+        try {
+            ctor.newInstance();
+            assertTrue(false);
+        } catch (IllegalAccessException expected) { }
+
+        assertFalse(ctor.trySetAccessible());
+        assertFalse(ctor.canAccess(null));
+    }
+
+    /**
+     * Invoke a private constructor on a public class in an open package
+     */
+    public void testPrivateConstructorInOpenedPackage() throws Exception {
+        Constructor<?> ctor = Unsafe.class.getDeclaredConstructor();
+
+        try {
+            ctor.newInstance();
+            assertTrue(false);
+        } catch (IllegalAccessException expected) { }
+
+        assertTrue(ctor.trySetAccessible());
+        assertTrue(ctor.canAccess(null));
+        Unsafe unsafe = (Unsafe) ctor.newInstance();
+    }
+
+    /**
+     * Invoke a private method on a public class in an exported package
+     */
+    public void testPrivateMethodInExportedPackage() throws Exception {
+        Method m = Perf.class.getDeclaredMethod("getBytes", String.class);
+        try {
+            m.invoke(null);
+            assertTrue(false);
+        } catch (IllegalAccessException expected) { }
+
+        assertFalse(m.trySetAccessible());
+        assertFalse(m.canAccess(null));
+    }
+
+
+    /**
+     * Invoke a private method on a public class in an open package
+     */
+    public void testPrivateMethodInOpenedPackage() throws Exception {
+        Method m = Unsafe.class.getDeclaredMethod("throwIllegalAccessError");
+        assertFalse(m.canAccess(null));
+
+        try {
+            m.invoke(null);
+            assertTrue(false);
+        } catch (IllegalAccessException expected) { }
+
+        assertTrue(m.trySetAccessible());
+        assertTrue(m.canAccess(null));
+        try {
+            m.invoke(null);
+            assertTrue(false);
+        } catch (InvocationTargetException e) {
+            // thrown by throwIllegalAccessError
+            assertTrue(e.getCause() instanceof IllegalAccessError);
+        }
+    }
+
+    /**
+     * Invoke a private method on a public class in an exported package
+     */
+    public void testPrivateFieldInExportedPackage() throws Exception {
+        Field f = Perf.class.getDeclaredField("instance");
+        try {
+            f.get(null);
+            assertTrue(false);
+        } catch (IllegalAccessException expected) { }
+
+        assertFalse(f.trySetAccessible());
+        assertFalse(f.canAccess(null));
+        try {
+            f.get(null);
+            assertTrue(false);
+        } catch (IllegalAccessException expected) {}
+    }
+
+    /**
+     * Access a private field in a public class that is an exported package
+     */
+    public void testPrivateFieldInOpenedPackage() throws Exception {
+        Field f = Unsafe.class.getDeclaredField("theUnsafe");
+
+        try {
+            f.get(null);
+            assertTrue(false);
+        } catch (IllegalAccessException expected) { }
+
+        assertTrue(f.trySetAccessible());
+        assertTrue(f.canAccess(null));
+        Unsafe unsafe = (Unsafe) f.get(null);
+    }
+
+
+    /**
+     * Invoke a public constructor on a public class in a non-exported package
+     */
+    public void testPublicConstructorInNonExportedPackage() throws Exception {
+        Class<?> clazz = Class.forName("sun.security.x509.X500Name");
+        Constructor<?> ctor = clazz.getConstructor(String.class);
+
+        try {
+            ctor.newInstance("cn=duke");
+            assertTrue(false);
+        } catch (IllegalAccessException expected) { }
+
+        assertFalse(ctor.trySetAccessible());
+        assertFalse(ctor.canAccess(null));
+        assertTrue(ctor.trySetAccessible() == ctor.isAccessible());
+    }
+
+
+    /**
+     * Access a public field in a public class that in a non-exported package
+     */
+    public void testPublicFieldInNonExportedPackage() throws Exception {
+        Class<?> clazz = Class.forName("sun.security.x509.X500Name");
+        Field f = clazz.getField("SERIALNUMBER_OID");
+
+        try {
+            f.get(null);
+            assertTrue(false);
+        } catch (IllegalAccessException expected) { }
+
+        assertFalse(f.trySetAccessible());
+        assertFalse(f.canAccess(null));
+    }
+
+
+    /**
+     * Test that the Class constructor cannot be make accessible.
+     */
+    public void testJavaLangClass() throws Exception {
+
+        // non-public constructor
+        Constructor<?> ctor
+            = Class.class.getDeclaredConstructor(ClassLoader.class, Class.class);
+        AccessibleObject[] ctors = { ctor };
+
+        assertFalse(ctor.trySetAccessible());
+        assertFalse(ctor.canAccess(null));
+    }
+
+}
--- a/jdk/test/java/lang/reflect/Layer/BasicLayerTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/reflect/Layer/BasicLayerTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2014, 2017, 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
@@ -24,6 +24,7 @@
 /**
  * @test
  * @library /lib/testlibrary
+ * @modules java.base/jdk.internal.misc
  * @build BasicLayerTest ModuleUtils
  * @compile layertest/Test.java
  * @run testng BasicLayerTest
@@ -43,6 +44,7 @@
 import java.util.Set;
 import java.util.stream.Collectors;
 
+import jdk.internal.misc.SharedSecrets;
 import org.testng.annotations.Test;
 import static org.testng.Assert.*;
 
@@ -50,6 +52,15 @@
 public class BasicLayerTest {
 
     /**
+     * Creates a "non-strict" builder for building a module. This allows the
+     * test the create ModuleDescriptor objects that do not require java.base.
+     */
+    private static ModuleDescriptor.Builder newBuilder(String mn) {
+        return SharedSecrets.getJavaLangModuleAccess()
+                .newModuleBuilder(mn, false, Set.of());
+    }
+
+    /**
      * Exercise Layer.empty()
      */
     public void testEmpty() {
@@ -109,25 +120,22 @@
      * Exercise Layer defineModules, created with empty layer as parent
      */
     public void testLayerOnEmpty() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .requires("m2")
                 .exports("p1")
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires("m3")
                 .build();
 
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .build();
 
         ModuleFinder finder
             = ModuleUtils.finderOf(descriptor1, descriptor2, descriptor3);
 
-        Configuration cf = resolveRequires(finder, "m1");
+        Configuration cf = resolve(finder, "m1");
 
         // map each module to its own class loader for this test
         ClassLoader loader1 = new ClassLoader() { };
@@ -191,15 +199,13 @@
      * Exercise Layer defineModules, created with boot layer as parent
      */
     public void testLayerOnBoot() {
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .requires("m2")
                 .requires("java.base")
                 .exports("p1")
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires("java.base")
                 .build();
 
@@ -207,7 +213,7 @@
             = ModuleUtils.finderOf(descriptor1, descriptor2);
 
         Configuration parent = Layer.boot().configuration();
-        Configuration cf = resolveRequires(parent, finder, "m1");
+        Configuration cf = resolve(parent, finder, "m1");
 
         ClassLoader loader = new ClassLoader() { };
 
@@ -256,21 +262,19 @@
      * have the same module-private package.
      */
     public void testPackageContainedInSelfAndOther() {
-        ModuleDescriptor descriptor1
-            =  ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 =  newBuilder("m1")
                 .requires("m2")
-                .contains("p")
+                .packages(Set.of("p"))
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
-                .contains("p")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
+                .packages(Set.of("p"))
                 .build();
 
         ModuleFinder finder
             = ModuleUtils.finderOf(descriptor1, descriptor2);
 
-        Configuration cf = resolveRequires(finder, "m1");
+        Configuration cf = resolve(finder, "m1");
         assertTrue(cf.modules().size() == 2);
 
         // one loader per module, should be okay
@@ -292,22 +296,18 @@
     public void testSameExportInPartitionedGraph() {
 
         // m1 reads m2, m2 exports p to m1
-        ModuleDescriptor descriptor1
-            =  ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 =  newBuilder("m1")
                 .requires("m2")
                 .build();
-        ModuleDescriptor descriptor2
-            =  ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 =  newBuilder("m2")
                 .exports("p", Set.of("m1"))
                 .build();
 
         // m3 reads m4, m4 exports p to m3
-        ModuleDescriptor descriptor3
-            =  ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .requires("m4")
                 .build();
-        ModuleDescriptor descriptor4
-            =  ModuleDescriptor.module("m4")
+        ModuleDescriptor descriptor4 = newBuilder("m4")
                 .exports("p", Set.of("m3"))
                 .build();
 
@@ -317,7 +317,7 @@
                                    descriptor3,
                                    descriptor4);
 
-        Configuration cf = resolveRequires(finder, "m1", "m3");
+        Configuration cf = resolve(finder, "m1", "m3");
         assertTrue(cf.modules().size() == 4);
 
         // one loader per module
@@ -353,16 +353,15 @@
         ModuleDescriptor base = Object.class.getModule().getDescriptor();
         assertTrue(base.packages().contains("sun.launcher"));
 
-        ModuleDescriptor descriptor
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor = newBuilder("m1")
                .requires("java.base")
-               .contains("sun.launcher")
+               .packages(Set.of("sun.launcher"))
                .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor);
 
         Configuration parent = Layer.boot().configuration();
-        Configuration cf = parent.resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+        Configuration cf = parent.resolve(finder, ModuleFinder.of(), Set.of("m1"));
         assertTrue(cf.modules().size() == 1);
 
         ClassLoader loader = new ClassLoader() { };
@@ -382,18 +381,16 @@
 
         // cf1: m1 and m2, m2 requires transitive m1
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires(Set.of(Requires.Modifier.TRANSITIVE), "m1")
                 .build();
 
         ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1, descriptor2);
 
-        Configuration cf1 = resolveRequires(finder1, "m2");
+        Configuration cf1 = resolve(finder1, "m2");
 
         ClassLoader cl1 = new ClassLoader() { };
         Layer layer1 = Layer.empty().defineModules(cf1, mn -> cl1);
@@ -401,14 +398,13 @@
 
         // cf2: m3, m3 requires m2
 
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .requires("m2")
                 .build();
 
         ModuleFinder finder2 = ModuleUtils.finderOf(descriptor3);
 
-        Configuration cf2 = resolveRequires(cf1, finder2, "m3");
+        Configuration cf2 = resolve(cf1, finder2, "m3");
 
         ClassLoader cl2 = new ClassLoader() { };
         Layer layer2 = layer1.defineModules(cf2, mn -> cl2);
@@ -456,13 +452,11 @@
 
         // cf1: m1
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
-                .build();
+        ModuleDescriptor descriptor1 = newBuilder("m1").build();
 
         ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1);
 
-        Configuration cf1 = resolveRequires(finder1, "m1");
+        Configuration cf1 = resolve(finder1, "m1");
 
         ClassLoader cl1 = new ClassLoader() { };
         Layer layer1 = Layer.empty().defineModules(cf1, mn -> cl1);
@@ -470,19 +464,17 @@
 
         // cf2: m2, m3: m2 requires transitive m1, m3 requires m2
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires(Set.of(Requires.Modifier.TRANSITIVE), "m1")
                 .build();
 
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .requires("m2")
                 .build();
 
         ModuleFinder finder2 = ModuleUtils.finderOf(descriptor2, descriptor3);
 
-        Configuration cf2 = resolveRequires(cf1, finder2, "m3");
+        Configuration cf2 = resolve(cf1, finder2, "m3");
 
         ClassLoader cl2 = new ClassLoader() { };
         Layer layer2 = layer1.defineModules(cf2, mn -> cl2);
@@ -527,13 +519,11 @@
 
         // cf1: m1
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
-                .build();
+        ModuleDescriptor descriptor1 = newBuilder("m1").build();
 
         ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1);
 
-        Configuration cf1 = resolveRequires(finder1, "m1");
+        Configuration cf1 = resolve(finder1, "m1");
 
         ClassLoader cl1 = new ClassLoader() { };
         Layer layer1 = Layer.empty().defineModules(cf1, mn -> cl1);
@@ -541,14 +531,13 @@
 
         // cf2: m2 requires transitive m1
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires(Set.of(Requires.Modifier.TRANSITIVE), "m1")
                 .build();
 
         ModuleFinder finder2 = ModuleUtils.finderOf(descriptor2);
 
-        Configuration cf2 = resolveRequires(cf1, finder2, "m2");
+        Configuration cf2 = resolve(cf1, finder2, "m2");
 
         ClassLoader cl2 = new ClassLoader() { };
         Layer layer2 = layer1.defineModules(cf2, mn -> cl2);
@@ -556,14 +545,13 @@
 
         // cf3: m3 requires m2
 
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .requires("m2")
                 .build();
 
         ModuleFinder finder3 = ModuleUtils.finderOf(descriptor3);
 
-        Configuration cf3 = resolveRequires(cf2, finder3, "m3");
+        Configuration cf3 = resolve(cf2, finder3, "m3");
 
         ClassLoader cl3 = new ClassLoader() { };
         Layer layer3 = layer2.defineModules(cf3, mn -> cl3);
@@ -610,18 +598,16 @@
 
         // cf1: m1, m2 requires transitive m1
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .build();
 
-        ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+        ModuleDescriptor descriptor2 = newBuilder("m2")
                 .requires(Set.of(Requires.Modifier.TRANSITIVE), "m1")
                 .build();
 
         ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1, descriptor2);
 
-        Configuration cf1 = resolveRequires(finder1, "m2");
+        Configuration cf1 = resolve(finder1, "m2");
 
         ClassLoader cl1 = new ClassLoader() { };
         Layer layer1 = Layer.empty().defineModules(cf1, mn -> cl1);
@@ -629,20 +615,18 @@
 
         // cf2: m3 requires transitive m2, m4 requires m3
 
-        ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3")
+        ModuleDescriptor descriptor3 = newBuilder("m3")
                 .requires(Set.of(Requires.Modifier.TRANSITIVE), "m2")
                 .build();
 
-        ModuleDescriptor descriptor4
-            = ModuleDescriptor.module("m4")
+        ModuleDescriptor descriptor4 = newBuilder("m4")
                 .requires("m3")
                 .build();
 
 
         ModuleFinder finder2 = ModuleUtils.finderOf(descriptor3, descriptor4);
 
-        Configuration cf2 = resolveRequires(cf1, finder2, "m3", "m4");
+        Configuration cf2 = resolve(cf1, finder2, "m3", "m4");
 
         ClassLoader cl2 = new ClassLoader() { };
         Layer layer2 = layer1.defineModules(cf2, mn -> cl2);
@@ -693,8 +677,7 @@
     @Test(expectedExceptions = { LayerInstantiationException.class })
     public void testModuleAlreadyDefinedToLoader() {
 
-        ModuleDescriptor md
-            = ModuleDescriptor.module("m")
+        ModuleDescriptor md = newBuilder("m")
                 .requires("java.base")
                 .build();
 
@@ -702,7 +685,7 @@
 
         Configuration parent = Layer.boot().configuration();
 
-        Configuration cf = parent.resolveRequires(finder, ModuleFinder.of(), Set.of("m"));
+        Configuration cf = parent.resolve(finder, ModuleFinder.of(), Set.of("m"));
 
         ClassLoader loader = new ClassLoader() { };
 
@@ -722,15 +705,13 @@
     @Test(expectedExceptions = { LayerInstantiationException.class })
     public void testPackageAlreadyInNamedModule() {
 
-        ModuleDescriptor md1
-            = ModuleDescriptor.module("m1")
-                .contains("p")
+        ModuleDescriptor md1 = newBuilder("m1")
+                .packages(Set.of("p"))
                 .requires("java.base")
                 .build();
 
-        ModuleDescriptor md2
-            = ModuleDescriptor.module("m2")
-                .contains("p")
+        ModuleDescriptor md2 = newBuilder("m2")
+                .packages(Set.of("p"))
                 .requires("java.base")
                 .build();
 
@@ -742,13 +723,13 @@
 
         Configuration parent = Layer.boot().configuration();
 
-        Configuration cf1 = parent.resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+        Configuration cf1 = parent.resolve(finder, ModuleFinder.of(), Set.of("m1"));
 
         Layer layer1 = Layer.boot().defineModules(cf1, mn -> loader);
 
         // attempt to define m2 containing package p to class loader
 
-        Configuration cf2 = parent.resolveRequires(finder, ModuleFinder.of(), Set.of("m2"));
+        Configuration cf2 = parent.resolve(finder, ModuleFinder.of(), Set.of("m2"));
 
         // should throw exception because p already in m1
         Layer layer2 = Layer.boot().defineModules(cf2, mn -> loader);
@@ -767,16 +748,15 @@
         Class<?> c = layertest.Test.class;
         assertFalse(c.getModule().isNamed());  // in unnamed module
 
-        ModuleDescriptor md
-            = ModuleDescriptor.module("m")
-                .contains(c.getPackageName())
+        ModuleDescriptor md = newBuilder("m")
+                .packages(Set.of(c.getPackageName()))
                 .requires("java.base")
                 .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(md);
 
         Configuration parent = Layer.boot().configuration();
-        Configuration cf = parent.resolveRequires(finder, ModuleFinder.of(), Set.of("m"));
+        Configuration cf = parent.resolve(finder, ModuleFinder.of(), Set.of("m"));
 
         Layer.boot().defineModules(cf, mn -> c.getClassLoader());
     }
@@ -786,8 +766,7 @@
      * Attempt to create a Layer with a module named "java.base".
      */
     public void testLayerWithJavaBase() {
-        ModuleDescriptor descriptor
-            = ModuleDescriptor.module("java.base")
+        ModuleDescriptor descriptor = newBuilder("java.base")
                 .exports("java.lang")
                 .build();
 
@@ -795,7 +774,7 @@
 
         Configuration cf = Layer.boot()
             .configuration()
-            .resolveRequires(finder, ModuleFinder.of(), Set.of("java.base"));
+            .resolve(finder, ModuleFinder.of(), Set.of("java.base"));
         assertTrue(cf.modules().size() == 1);
 
         ClassLoader scl = ClassLoader.getSystemClassLoader();
@@ -824,16 +803,15 @@
      */
     @Test(enabled = false)
     public void testLayerWithJavaPackage() {
-        ModuleDescriptor descriptor
-            = ModuleDescriptor.module("foo")
-                .contains("java.foo")
+        ModuleDescriptor descriptor = newBuilder("foo")
+                .packages(Set.of("java.foo"))
                 .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor);
 
         Configuration cf = Layer.boot()
                 .configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("foo"));
+                .resolve(finder, ModuleFinder.of(), Set.of("foo"));
         assertTrue(cf.modules().size() == 1);
 
         ClassLoader pcl = ClassLoader.getPlatformClassLoader();
@@ -870,15 +848,14 @@
      */
     @Test(expectedExceptions = { LayerInstantiationException.class })
     public void testLayerWithBootLoader() {
-        ModuleDescriptor descriptor
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor = newBuilder("m1")
                 .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor);
 
         Configuration cf = Layer.boot()
             .configuration()
-            .resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+            .resolve(finder, ModuleFinder.of(), Set.of("m1"));
         assertTrue(cf.modules().size() == 1);
 
         Layer.boot().defineModules(cf, mn -> null );
@@ -891,15 +868,14 @@
     @Test(expectedExceptions = { IllegalArgumentException.class })
     public void testIncorrectParent1() {
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .requires("java.base")
                 .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1);
 
         Configuration parent = Layer.boot().configuration();
-        Configuration cf = parent.resolveRequires(finder, ModuleFinder.of(), Set.of("m1"));
+        Configuration cf = parent.resolve(finder, ModuleFinder.of(), Set.of("m1"));
 
         ClassLoader loader = new ClassLoader() { };
         Layer.empty().defineModules(cf, mn -> loader);
@@ -912,13 +888,12 @@
     @Test(expectedExceptions = { IllegalArgumentException.class })
     public void testIncorrectParent2() {
 
-        ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
+        ModuleDescriptor descriptor1 = newBuilder("m1")
                 .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1);
 
-        Configuration cf = resolveRequires(finder, "m1");
+        Configuration cf = resolve(finder, "m1");
 
         ClassLoader loader = new ClassLoader() { };
         Layer.boot().defineModules(cf, mn -> loader);
@@ -935,7 +910,7 @@
 
     @Test(expectedExceptions = { NullPointerException.class })
     public void testCreateWithNull2() {
-        Configuration cf = resolveRequires(Layer.boot().configuration(), ModuleFinder.of());
+        Configuration cf = resolve(Layer.boot().configuration(), ModuleFinder.of());
         Layer.boot().defineModules(cf, null);
     }
 
@@ -975,14 +950,14 @@
      * Resolve the given modules, by name, and returns the resulting
      * Configuration.
      */
-    private static Configuration resolveRequires(Configuration cf,
-                                                 ModuleFinder finder,
-                                                 String... roots) {
-        return cf.resolveRequires(finder, ModuleFinder.of(), Set.of(roots));
+    private static Configuration resolve(Configuration cf,
+                                         ModuleFinder finder,
+                                         String... roots) {
+        return cf.resolve(finder, ModuleFinder.of(), Set.of(roots));
     }
 
-    private static Configuration resolveRequires(ModuleFinder finder,
-                                                 String... roots) {
-        return resolveRequires(Configuration.empty(), finder, roots);
+    private static Configuration resolve(ModuleFinder finder,
+                                         String... roots) {
+        return resolve(Configuration.empty(), finder, roots);
     }
 }
--- a/jdk/test/java/lang/reflect/Layer/LayerAndLoadersTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/reflect/Layer/LayerAndLoadersTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -81,7 +81,7 @@
      */
     public void testWithOneLoader() throws Exception {
 
-        Configuration cf = resolveRequires("m1");
+        Configuration cf = resolve("m1");
 
         ClassLoader scl = ClassLoader.getSystemClassLoader();
 
@@ -110,7 +110,7 @@
      */
     public void testWithManyLoaders() throws Exception {
 
-        Configuration cf = resolveRequires("m1");
+        Configuration cf = resolve("m1");
 
         ClassLoader scl = ClassLoader.getSystemClassLoader();
 
@@ -145,7 +145,7 @@
      */
     public void testServicesWithOneLoader() throws Exception {
 
-        Configuration cf = resolveRequiresAndUses("m1");
+        Configuration cf = resolveAndBind("m1");
 
         ClassLoader scl = ClassLoader.getSystemClassLoader();
 
@@ -186,7 +186,7 @@
      */
     public void testServicesWithManyLoaders() throws Exception {
 
-        Configuration cf = resolveRequiresAndUses("m1");
+        Configuration cf = resolveAndBind("m1");
 
         ClassLoader scl = ClassLoader.getSystemClassLoader();
 
@@ -233,7 +233,7 @@
      */
     public void testDelegationToParent() throws Exception {
 
-        Configuration cf = resolveRequires("m1");
+        Configuration cf = resolve("m1");
 
         ClassLoader parent = this.getClass().getClassLoader();
         String cn = this.getClass().getName();
@@ -267,16 +267,16 @@
     public void testOverlappingPackages() {
 
         ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1").exports("p").build();
+            = ModuleDescriptor.newModule("m1").exports("p").build();
 
         ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2").exports("p").build();
+            = ModuleDescriptor.newModule("m2").exports("p").build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1, descriptor2);
 
         Configuration cf = Layer.boot()
             .configuration()
-            .resolveRequires(finder, ModuleFinder.of(), Set.of("m1", "m2"));
+            .resolve(finder, ModuleFinder.of(), Set.of("m1", "m2"));
 
         // cannot define both module m1 and m2 to the same class loader
         try {
@@ -301,29 +301,29 @@
     public void testSplitDelegation() {
 
         ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1").exports("p").build();
+            = ModuleDescriptor.newModule("m1").exports("p").build();
 
         ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2").exports("p").build();
+            = ModuleDescriptor.newModule("m2").exports("p").build();
 
         ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1, descriptor2);
 
         Configuration cf1 = Layer.boot()
             .configuration()
-            .resolveRequires(finder1, ModuleFinder.of(), Set.of("m1", "m2"));
+            .resolve(finder1, ModuleFinder.of(), Set.of("m1", "m2"));
 
         Layer layer1 = Layer.boot().defineModulesWithManyLoaders(cf1, null);
         checkLayer(layer1, "m1", "m2");
 
         ModuleDescriptor descriptor3
-            = ModuleDescriptor.module("m3").requires("m1").build();
+            = ModuleDescriptor.newModule("m3").requires("m1").build();
 
         ModuleDescriptor descriptor4
-            = ModuleDescriptor.module("m4").requires("m2").build();
+            = ModuleDescriptor.newModule("m4").requires("m2").build();
 
         ModuleFinder finder2 = ModuleUtils.finderOf(descriptor3, descriptor4);
 
-        Configuration cf2 = cf1.resolveRequires(finder2, ModuleFinder.of(),
+        Configuration cf2 = cf1.resolve(finder2, ModuleFinder.of(),
                                                 Set.of("m3", "m4"));
 
         // package p cannot be supplied by two class loaders
@@ -349,13 +349,13 @@
      */
     public void testOverriding1() throws Exception {
 
-        Configuration cf1 = resolveRequires("m1");
+        Configuration cf1 = resolve("m1");
 
         Layer layer1 = Layer.boot().defineModulesWithOneLoader(cf1, null);
         checkLayer(layer1, "m1", "m2", "m3");
 
         ModuleFinder finder = ModuleFinder.of(MODS_DIR);
-        Configuration cf2 = cf1.resolveRequires(finder, ModuleFinder.of(),
+        Configuration cf2 = cf1.resolve(finder, ModuleFinder.of(),
                                                 Set.of("m1"));
 
         Layer layer2 = layer1.defineModulesWithOneLoader(cf2, null);
@@ -398,13 +398,13 @@
      */
     public void testOverriding2() throws Exception {
 
-        Configuration cf1 = resolveRequires("m1");
+        Configuration cf1 = resolve("m1");
 
         Layer layer1 = Layer.boot().defineModulesWithManyLoaders(cf1, null);
         checkLayer(layer1, "m1", "m2", "m3");
 
         ModuleFinder finder = ModuleFinder.of(MODS_DIR);
-        Configuration cf2 = cf1.resolveRequires(finder, ModuleFinder.of(),
+        Configuration cf2 = cf1.resolve(finder, ModuleFinder.of(),
                                                 Set.of("m1"));
 
         Layer layer2 = layer1.defineModulesWithManyLoaders(cf2, null);
@@ -492,14 +492,14 @@
      */
     public void testOverriding3() throws Exception {
 
-        Configuration cf1 = resolveRequires("m1");
+        Configuration cf1 = resolve("m1");
 
         Layer layer1 = Layer.boot().defineModulesWithOneLoader(cf1, null);
         checkLayer(layer1, "m1", "m2", "m3");
 
         ModuleFinder finder = finderFor("m1", "m3");
 
-        Configuration cf2 = cf1.resolveRequires(finder, ModuleFinder.of(),
+        Configuration cf2 = cf1.resolve(finder, ModuleFinder.of(),
                                                 Set.of("m1"));
 
         Layer layer2 = layer1.defineModulesWithOneLoader(cf2, null);
@@ -529,14 +529,14 @@
      */
     public void testOverriding4() throws Exception {
 
-        Configuration cf1 = resolveRequires("m1");
+        Configuration cf1 = resolve("m1");
 
         Layer layer1 = Layer.boot().defineModulesWithManyLoaders(cf1, null);
         checkLayer(layer1, "m1", "m2", "m3");
 
         ModuleFinder finder = finderFor("m1", "m3");
 
-        Configuration cf2 = cf1.resolveRequires(finder, ModuleFinder.of(),
+        Configuration cf2 = cf1.resolve(finder, ModuleFinder.of(),
                                                 Set.of("m1"));
 
         Layer layer2 = layer1.defineModulesWithManyLoaders(cf2, null);
@@ -577,7 +577,7 @@
      * Layer.defineModulesWithOneLoader.
      */
     public void testResourcesOneLoader() throws Exception {
-        Configuration cf = resolveRequires("m1");
+        Configuration cf = resolve("m1");
         ClassLoader scl = ClassLoader.getSystemClassLoader();
         Layer layer = Layer.boot().defineModulesWithOneLoader(cf, scl);
         ClassLoader loader = layer.findLoader("m1");
@@ -589,7 +589,7 @@
      * Layer.defineModulesWithOneLoader.
      */
     public void testResourcesManyLoaders() throws Exception {
-        Configuration cf = resolveRequires("m1");
+        Configuration cf = resolve("m1");
         ClassLoader scl = ClassLoader.getSystemClassLoader();
         Layer layer = Layer.boot().defineModulesWithManyLoaders(cf, scl);
         ClassLoader loader = layer.findLoader("m1");
@@ -621,22 +621,22 @@
      * Resolve the given modules, by name, and returns the resulting
      * Configuration.
      */
-    private static Configuration resolveRequires(String... roots) {
+    private static Configuration resolve(String... roots) {
         ModuleFinder finder = ModuleFinder.of(MODS_DIR);
         return Layer.boot()
             .configuration()
-            .resolveRequires(finder, ModuleFinder.of(), Set.of(roots));
+            .resolve(finder, ModuleFinder.of(), Set.of(roots));
     }
 
     /**
      * Resolve the given modules, by name, and returns the resulting
      * Configuration.
      */
-    private static Configuration resolveRequiresAndUses(String... roots) {
+    private static Configuration resolveAndBind(String... roots) {
         ModuleFinder finder = ModuleFinder.of(MODS_DIR);
         return Layer.boot()
             .configuration()
-            .resolveRequiresAndUses(finder, ModuleFinder.of(), Set.of(roots));
+            .resolveAndBind(finder, ModuleFinder.of(), Set.of(roots));
     }
 
 
--- a/jdk/test/java/lang/reflect/Layer/LayerControllerTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/reflect/Layer/LayerControllerTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -50,22 +50,22 @@
      */
     private Layer.Controller createTestLayer() {
         ModuleDescriptor descriptor1
-            = ModuleDescriptor.module("m1")
-                .contains("p1")
+            = ModuleDescriptor.newModule("m1")
+                .packages(Set.of("p1"))
                 .requires("java.base")
                 .build();
 
         ModuleDescriptor descriptor2
-            = ModuleDescriptor.module("m2")
+            = ModuleDescriptor.newModule("m2")
                 .requires("java.base")
-                .contains("p2")
+                .packages(Set.of("p2"))
                 .build();
 
         ModuleFinder finder = ModuleUtils.finderOf(descriptor1, descriptor2);
         Layer bootLayer = Layer.boot();
 
         Configuration cf = bootLayer.configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of("m1", "m2"));
+                .resolve(finder, ModuleFinder.of(), Set.of("m1", "m2"));
 
         ClassLoader scl = ClassLoader.getSystemClassLoader();
 
@@ -193,4 +193,4 @@
             assertTrue(false);
         } catch (NullPointerException expected) { }
     }
-}
\ No newline at end of file
+}
--- a/jdk/test/java/lang/reflect/Module/AnnotationsTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/reflect/Module/AnnotationsTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -144,7 +144,7 @@
         Layer bootLayer = Layer.boot();
 
         Configuration cf = bootLayer.configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of(name));
+                .resolve(finder, ModuleFinder.of(), Set.of(name));
 
         ClassLoader scl = ClassLoader.getSystemClassLoader();
         Layer layer = bootLayer.defineModulesWithOneLoader(cf, scl);
--- a/jdk/test/java/lang/reflect/Module/BasicModuleTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/reflect/Module/BasicModuleTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2014, 2017, 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
@@ -25,8 +25,10 @@
 import java.lang.module.ResolvedModule;
 import java.lang.reflect.Layer;
 import java.lang.reflect.Module;
+import java.nio.file.spi.FileSystemProvider;  // service type in java.base
 import java.util.function.Predicate;
 import java.util.stream.Stream;
+import javax.print.PrintServiceLookup;        // service type in java.desktop
 
 import org.testng.annotations.Test;
 import static org.testng.Assert.*;
@@ -170,6 +172,14 @@
 
         // canRead
         assertTrue(base.canRead(base));
+        assertFalse(base.canRead(thisModule));
+
+        // addReads
+        try {
+            base.addReads(thisModule);
+            assertTrue(false);
+        } catch (IllegalCallerException expected) { }
+        assertFalse(base.canRead(thisModule));
 
         // isExported
         assertTrue(base.isExported("java.lang"));
@@ -182,6 +192,18 @@
         assertFalse(base.isExported("java.wombat", thisModule));
         assertFalse(base.isExported("java.wombat", base));
 
+        // addExports
+        try {
+            base.addExports("java.lang", thisModule);
+            assertTrue(false);
+        } catch (IllegalCallerException expected) { }
+        try {
+            base.addExports("jdk.internal.misc", thisModule);
+            assertTrue(false);
+        } catch (IllegalCallerException expected) { }
+        assertFalse(base.isExported("jdk.internal.misc"));
+        assertFalse(base.isExported("jdk.internal.misc", thisModule));
+
         // isOpen
         assertFalse(base.isOpen("java.lang"));
         assertFalse(base.isOpen("java.lang", thisModule));
@@ -192,6 +214,29 @@
         assertFalse(base.isOpen("java.wombat"));
         assertFalse(base.isOpen("java.wombat", thisModule));
         assertFalse(base.isOpen("java.wombat", base));
+
+        // addOpens
+        try {
+            base.addOpens("jdk.internal.misc", thisModule);
+            assertTrue(false);
+        } catch (IllegalCallerException expected) { }
+        assertFalse(base.isOpen("jdk.internal.misc"));
+        assertFalse(base.isOpen("jdk.internal.misc", thisModule));
+
+        // canUse
+        assertTrue(base.canUse(FileSystemProvider.class));
+        assertFalse(base.canUse(Thread.class));
+
+        // addUses
+        try {
+            base.addUses(FileSystemProvider.class);
+            assertTrue(false);
+        } catch (IllegalCallerException expected) { }
+        try {
+            base.addUses(Thread.class);
+            assertTrue(false);
+        } catch (IllegalCallerException expected) { }
+        assertFalse(base.canUse(Thread.class));
     }
 
 
@@ -226,26 +271,68 @@
         assertTrue(desktop.canRead(base));
         assertTrue(desktop.canRead(xml));
 
+        // addReads
+        try {
+            desktop.addReads(thisModule);
+            assertTrue(false);
+        } catch (IllegalCallerException expected) { }
+        assertFalse(desktop.canRead(thisModule));
+
         // isExported
         assertTrue(desktop.isExported("java.awt"));
         assertTrue(desktop.isExported("java.awt", thisModule));
+        assertFalse(desktop.isExported("sun.awt"));
+        assertFalse(desktop.isExported("sun.awt", thisModule));
+        assertTrue(desktop.isExported("sun.awt", desktop));
         assertFalse(desktop.isExported("java.wombat"));
         assertFalse(desktop.isExported("java.wombat", thisModule));
+        assertFalse(desktop.isExported("java.wombat", base));
+
+        // addExports
+        try {
+            desktop.addExports("java.awt", thisModule);
+            assertTrue(false);
+        } catch (IllegalCallerException expected) { }
+        try {
+            desktop.addExports("sun.awt", thisModule);
+            assertTrue(false);
+        } catch (IllegalCallerException expected) { }
+        assertFalse(desktop.isExported("sun.awt"));
+        assertFalse(desktop.isExported("sun.awt", thisModule));
+
+        // isOpen
+        assertFalse(desktop.isOpen("java.awt"));
+        assertFalse(desktop.isOpen("java.awt", thisModule));
+        assertTrue(desktop.isOpen("java.awt", desktop));
+        assertFalse(desktop.isOpen("sun.awt"));
+        assertFalse(desktop.isOpen("sun.awt", thisModule));
+        assertTrue(desktop.isOpen("sun.awt", desktop));
+        assertFalse(desktop.isOpen("java.wombat"));
+        assertFalse(desktop.isOpen("java.wombat", thisModule));
+        assertFalse(desktop.isOpen("java.wombat", desktop));
+
+        // addOpens
+        try {
+            base.addOpens("sun.awt", thisModule);
+            assertTrue(false);
+        } catch (IllegalCallerException expected) { }
+        assertFalse(desktop.isOpen("sun.awt"));
+        assertFalse(desktop.isOpen("sun.awt", thisModule));
+
+        // canUse
+        assertTrue(base.canUse(FileSystemProvider.class));
+        assertFalse(base.canUse(Thread.class));
+
+        // addUses
+        try {
+            desktop.addUses(PrintServiceLookup.class);
+            assertTrue(false);
+        } catch (IllegalCallerException expected) { }
+        try {
+            desktop.addUses(Thread.class);
+            assertTrue(false);
+        } catch (IllegalCallerException expected) { }
+        assertFalse(desktop.canUse(Thread.class));
     }
 
-
-    @Test(expectedExceptions = { NullPointerException.class })
-    public void testIsExportedNull() {
-        Module thisModule = this.getClass().getModule();
-        thisModule.isExported(null, thisModule);
-    }
-
-
-    @Test(expectedExceptions = { NullPointerException.class })
-    public void testIsExportedToNull() {
-        Module thisModule = this.getClass().getModule();
-        thisModule.isExported("", null);
-    }
-
-
 }
--- a/jdk/test/java/lang/reflect/Module/WithSecurityManager.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/reflect/Module/WithSecurityManager.java	Wed Jul 05 22:52:01 2017 +0200
@@ -126,7 +126,7 @@
         Layer bootLayer = Layer.boot();
         Configuration cf = bootLayer
             .configuration()
-            .resolveRequires(finder, ModuleFinder.of(), Set.of(ANOTHER_MODULE));
+            .resolve(finder, ModuleFinder.of(), Set.of(ANOTHER_MODULE));
         Layer layer = bootLayer.defineModulesWithOneLoader(cf, null);
 
         Optional<Module> om = layer.findModule(mn);
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/reflect/Module/addXXX/Driver.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,29 @@
+/*
+ * Copyright (c) 2017, 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
+ * @build test/* m1/* m2/* m3/* m4/*
+ * @run testng/othervm test/test.Main
+ * @summary Basic test case for Module::addXXX methods
+ */
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/reflect/Module/addXXX/m1/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,25 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+module m1 {
+    exports p1;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/reflect/Module/addXXX/m1/p1/C.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,27 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+package p1;
+
+public class C {
+    public C() { }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/reflect/Module/addXXX/m2/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,25 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+module m2 {
+    exports p2;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/reflect/Module/addXXX/m2/p2/C.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,32 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+package p2;
+
+import java.lang.reflect.Module;
+
+public class C {
+
+    public static void export(String pn, Module m) {
+        C.class.getModule().addExports(pn, m);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/reflect/Module/addXXX/m2/p2/internal/C.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,26 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+package p2.internal;
+
+public class C {
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/reflect/Module/addXXX/m3/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,26 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+module m3 {
+    exports p3 to test;
+    opens p3 to test;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/reflect/Module/addXXX/m3/p3/C.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,26 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+package p3;
+
+public class C {
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/reflect/Module/addXXX/m4/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,25 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+module m4 {
+    exports p4;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/reflect/Module/addXXX/m4/p4/C.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,32 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+package p4;
+
+import java.lang.reflect.Constructor;
+
+public class C {
+    public static Object tryNewInstance(Class<?> clazz) throws Exception {
+        Constructor<?> ctor = clazz.getDeclaredConstructor();
+        return ctor.newInstance();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/reflect/Module/addXXX/test/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,30 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+module test {
+    exports test to testng;
+
+    requires m2;
+    requires m3;
+    requires m4;
+    requires testng;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/reflect/Module/addXXX/test/test/C.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,26 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+
+package test;
+
+public class C { }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/reflect/Module/addXXX/test/test/Main.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,196 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+
+package test;
+
+import java.lang.invoke.MethodHandle;
+import java.lang.invoke.MethodHandles;
+import java.lang.invoke.MethodType;
+import java.lang.reflect.Constructor;
+import java.lang.reflect.Module;
+import java.util.ServiceConfigurationError;
+import java.util.ServiceLoader;
+
+import org.testng.annotations.Test;
+import static org.testng.Assert.*;
+
+/**
+ * Basic test case for Module::addXXXX methods
+ */
+
+@Test
+public class Main {
+
+    /**
+     * Test Module::addReads
+     *
+     *     module test { }
+     *
+     *     module m1 {
+     *         exports p1;
+     *     }
+     */
+    public void testAddReads() throws Throwable {
+        Module thisModule = Main.class.getModule();
+        Class<?> clazz = Class.forName("p1.C");
+        Module m1 = clazz.getModule();
+
+        // test does not read m1
+        assertFalse(thisModule.canRead(m1));
+        MethodHandles.Lookup lookup = MethodHandles.lookup();
+        MethodType mt = MethodType.methodType(void.class);
+        try {
+            lookup.findConstructor(clazz, mt);
+            assertTrue(false);
+        } catch (IllegalAccessException expected) { }
+
+        // update test to read m1
+        Module result = thisModule.addReads(m1);
+        assertTrue(result== thisModule);
+        assertTrue(thisModule.canRead(m1));
+        MethodHandle mh = lookup.findConstructor(clazz, mt);
+        Object obj = mh.invoke();
+
+        // attempt to update m1 to read test
+        try {
+            m1.addReads(thisModule);
+            assertTrue(false);
+        } catch (IllegalCallerException expected) { }
+    }
+
+
+    /**
+     * Test Module::addExports
+     *
+     *     module test {
+     *         requires m2;
+     *     }
+     *     module m2 {
+     *         exports p2;
+     *         contains package p2.internal;
+     *     }
+     */
+    public void testAddExports() throws Exception {
+        Module thisModule = Main.class.getModule();
+        Module m2 = p2.C.class.getModule();
+        Class<?> targetClass = Class.forName("p2.internal.C");
+        String p2Internal = targetClass.getPackageName();
+        assertTrue(targetClass.getModule() == m2);
+
+        // m2 does not export p2.internal to test
+        assertFalse(m2.isExported(p2Internal, thisModule));
+        Constructor<?> ctor = targetClass.getDeclaredConstructor();
+        try {
+            ctor.newInstance();
+            assertTrue(false);
+        } catch (IllegalAccessException expected) { }
+
+        // update m2 to export p2.internal to test
+        p2.C.export(p2Internal, thisModule);
+        assertTrue(m2.isExported(p2Internal, thisModule));
+        ctor.newInstance(); // should succeed
+
+        // attempt to update m2 to export a package to test
+        try {
+            m2.addExports("p2.other", thisModule);
+            assertTrue(false);
+        } catch (IllegalCallerException expected) { }
+    }
+
+    /**
+     * Test Module::addOpens
+     *
+     *     module test {
+     *         requires m3;
+     *         requires m4;
+     *     }
+     *
+     *     module m3 {
+     *         exports p3 to test;
+     *         opens p3 to test;
+     *     }
+     *
+     *     module m4 {
+     *         exports p4;
+     *     }
+     */
+    public void testAddOpens() throws Exception {
+        Module thisModule = Main.class.getModule();
+        Module m3 = p3.C.class.getModule();
+        Module m4 = p4.C.class.getModule();
+
+        // test does not open package test to m4
+        assertFalse(thisModule.isOpen("test", m4));
+        try {
+            p4.C.tryNewInstance(test.C.class);
+            assertTrue(false);
+        } catch (IllegalAccessException expected) { }
+
+        // open test to m4
+        thisModule.addOpens("test", m4);
+        p4.C.tryNewInstance(test.C.class);  // should succeed
+
+
+        // m3 does not open p3 to m4
+        assertFalse(m3.isOpen("p3", m4));
+        try {
+            p4.C.tryNewInstance(p3.C.class);
+            assertTrue(false);
+        } catch (IllegalAccessException expected) { }
+
+
+        // m3 opens p3 to test => test allowed to open m3/p3 to m4
+        assertTrue(m3.isOpen("p3", thisModule));
+        m3.addOpens("p3", m4);
+        assertTrue(m3.isOpen("p3", m4));
+        p4.C.tryNewInstance(p3.C.class);   // should succeed
+
+
+        // attempt to update m4 to open package to m3
+        try {
+            m4.addOpens("p4", m3);
+            assertTrue(false);
+        } catch (IllegalCallerException expected) { }
+    }
+
+
+    /**
+     * Test Module::addUses
+     */
+    public void testAddUses() {
+        Module thisModule = Main.class.getModule();
+
+        assertFalse(thisModule.canUse(Service.class));
+        try {
+            ServiceLoader.load(Service.class);
+            assertTrue(false);
+        } catch (ServiceConfigurationError expected) { }
+
+        Module result = thisModule.addUses(Service.class);
+        assertTrue(result== thisModule);
+
+        assertTrue(thisModule.canUse(Service.class));
+        ServiceLoader.load(Service.class); // no exception
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/reflect/Module/addXXX/test/test/Service.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,29 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+
+package test;
+
+/**
+ * Simple service type
+ */
+public interface Service { }
--- a/jdk/test/java/lang/reflect/Proxy/ProxyClassAccessTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/reflect/Proxy/ProxyClassAccessTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -91,7 +91,7 @@
         Layer bootLayer = Layer.boot();
         Configuration cf = bootLayer
                 .configuration()
-                .resolveRequiresAndUses(ModuleFinder.of(), finder, modules);
+                .resolveAndBind(ModuleFinder.of(), finder, modules);
         ClassLoader parentLoader = this.getClass().getClassLoader();
         Layer layer = bootLayer.defineModulesWithOneLoader(cf, parentLoader);
 
--- a/jdk/test/java/lang/reflect/Proxy/ProxyLayerTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/reflect/Proxy/ProxyLayerTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -79,7 +79,7 @@
         Layer bootLayer = Layer.boot();
         Configuration cf = bootLayer
                 .configuration()
-                .resolveRequiresAndUses(ModuleFinder.of(), finder, Arrays.asList(modules));
+                .resolveAndBind(ModuleFinder.of(), finder, Arrays.asList(modules));
         ClassLoader scl = ClassLoader.getSystemClassLoader();
         Layer layer = bootLayer.defineModulesWithOneLoader(cf, scl);
 
@@ -113,7 +113,7 @@
         Layer bootLayer = Layer.boot();
         Configuration cf = bootLayer
                 .configuration()
-                .resolveRequiresAndUses(ModuleFinder.of(), finder, Arrays.asList(modules));
+                .resolveAndBind(ModuleFinder.of(), finder, Arrays.asList(modules));
         ClassLoader scl = ClassLoader.getSystemClassLoader();
         Layer layer = bootLayer.defineModulesWithOneLoader(cf, scl);
 
@@ -143,7 +143,7 @@
         Layer bootLayer = Layer.boot();
         Configuration cf = bootLayer
                 .configuration()
-                .resolveRequiresAndUses(ModuleFinder.of(), finder, Arrays.asList(modules));
+                .resolveAndBind(ModuleFinder.of(), finder, Arrays.asList(modules));
         ClassLoader scl = ClassLoader.getSystemClassLoader();
         Layer layer = bootLayer.defineModulesWithOneLoader(cf, scl);
 
--- a/jdk/test/java/lang/reflect/PublicMethods/PublicMethodsTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/lang/reflect/PublicMethods/PublicMethodsTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -57,6 +57,9 @@
 /*
  * @test
  * @bug 8062389
+ * @modules java.compiler
+ *          jdk.compiler
+ *          jdk.zipfs
  * @summary Nearly exhaustive test of Class.getMethod() and Class.getMethods()
  * @run main PublicMethodsTest
  */
--- a/jdk/test/java/net/httpclient/security/Driver.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/net/httpclient/security/Driver.java	Wed Jul 05 22:52:01 2017 +0200
@@ -127,6 +127,7 @@
             cmd.add("-Dtest.src=" + testSrc);
             cmd.add("-Dtest.classes=" + testClasses);
             cmd.add("-Djava.security.manager");
+            cmd.add("--add-modules=jdk.incubator.httpclient");
             cmd.add("-Djava.security.policy=" + testSrc + sep + policy);
             cmd.add("-Dport.number=" + Integer.toString(Utils.getFreePort()));
             cmd.add("-Dport.number1=" + Integer.toString(Utils.getFreePort()));
--- a/jdk/test/java/nio/channels/FileChannel/Transfer.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/nio/channels/FileChannel/Transfer.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2001, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2001, 2017, 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
@@ -24,43 +24,53 @@
 /* @test
  * @bug 4434723 4482726 4559072 4638365 4795550 5081340 5103988 6253145
  *   6984545
- * @summary Test FileChannel.transferFrom and transferTo
+ * @summary Test FileChannel.transferFrom and transferTo (use -Dseed=X to set PRNG seed)
  * @library ..
+ * @library /lib/testlibrary/
+ * @build jdk.testlibrary.*
+ * @run testng Transfer
  * @key randomness
  */
 
-import java.io.*;
-import java.net.*;
-import java.nio.*;
-import java.nio.channels.*;
+import java.io.BufferedReader;
+import java.io.BufferedWriter;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileOutputStream;
+import java.io.InputStreamReader;
+import java.io.IOException;
+import java.io.OutputStreamWriter;
+import java.io.PrintStream;
+import java.io.RandomAccessFile;
+import java.io.Reader;
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+import java.net.InetAddress;
+import java.net.InetSocketAddress;
+import java.nio.ByteBuffer;
+import java.nio.channels.FileChannel;
+import java.nio.channels.NonReadableChannelException;
+import java.nio.channels.Pipe;
+import java.nio.channels.ServerSocketChannel;
+import java.nio.channels.SocketChannel;
 import java.nio.channels.spi.SelectorProvider;
 import java.nio.file.StandardOpenOption;
 import java.nio.file.FileAlreadyExistsException;
 import java.util.Random;
+import java.util.concurrent.TimeUnit;
 
+import jdk.testlibrary.RandomFactory;
+
+import org.testng.annotations.Test;
 
 public class Transfer {
 
-    private static Random generator = new Random();
-
-    private static int[] testSizes = {
-        0, 10, 1023, 1024, 1025, 2047, 2048, 2049 };
+    private static Random generator = RandomFactory.getRandom();
+    private static PrintStream err = System.err;
+    private static PrintStream out = System.out;
 
-    public static void main(String[] args) throws Exception {
-        testFileChannel();
-        for (int i=0; i<testSizes.length; i++)
-            testReadableByteChannel(testSizes[i]);
-        xferTest02(); // for bug 4482726
-        xferTest03(); // for bug 4559072
-        xferTest04(); // for bug 4638365
-        xferTest05(); // for bug 4638365
-        xferTest06(); // for bug 5081340
-        xferTest07(); // for bug 5103988
-        xferTest08(); // for bug 6253145
-        xferTest09(); // for bug 6984545
-    }
-
-    private static void testFileChannel() throws Exception {
+    @Test
+    public void testFileChannel() throws Exception {
         File source = File.createTempFile("source", null);
         source.deleteOnExit();
         File sink = File.createTempFile("sink", null);
@@ -105,52 +115,58 @@
         sink.delete();
     }
 
-    private static void testReadableByteChannel(int size) throws Exception {
-        SelectorProvider sp = SelectorProvider.provider();
-        Pipe p = sp.openPipe();
-        Pipe.SinkChannel sink = p.sink();
-        Pipe.SourceChannel source = p.source();
-        sink.configureBlocking(false);
+    @Test
+    public void testReadableByteChannel() throws Exception {
+        int[] testSizes = { 0, 10, 1023, 1024, 1025, 2047, 2048, 2049 };
 
-        ByteBuffer outgoingdata = ByteBuffer.allocateDirect(size + 10);
-        byte[] someBytes = new byte[size + 10];
-        generator.nextBytes(someBytes);
-        outgoingdata.put(someBytes);
-        outgoingdata.flip();
+        for (int size : testSizes) {
+            SelectorProvider sp = SelectorProvider.provider();
+            Pipe p = sp.openPipe();
+            Pipe.SinkChannel sink = p.sink();
+            Pipe.SourceChannel source = p.source();
+            sink.configureBlocking(false);
 
-        int totalWritten = 0;
-        while (totalWritten < size + 10) {
-            int written = sink.write(outgoingdata);
-            if (written < 0)
-                throw new Exception("Write failed");
-            totalWritten += written;
-        }
+            ByteBuffer outgoingdata = ByteBuffer.allocateDirect(size + 10);
+            byte[] someBytes = new byte[size + 10];
+            generator.nextBytes(someBytes);
+            outgoingdata.put(someBytes);
+            outgoingdata.flip();
 
-        File f = File.createTempFile("blah"+size, null);
-        f.deleteOnExit();
-        RandomAccessFile raf = new RandomAccessFile(f, "rw");
-        FileChannel fc = raf.getChannel();
-        long oldPosition = fc.position();
+            int totalWritten = 0;
+            while (totalWritten < size + 10) {
+                int written = sink.write(outgoingdata);
+                if (written < 0)
+                    throw new Exception("Write failed");
+                totalWritten += written;
+            }
 
-        long bytesWritten = fc.transferFrom(source, 0, size);
-        fc.force(true);
-        if (bytesWritten != size)
-            throw new RuntimeException("Transfer failed");
+            File f = File.createTempFile("blah"+size, null);
+            f.deleteOnExit();
+            RandomAccessFile raf = new RandomAccessFile(f, "rw");
+            FileChannel fc = raf.getChannel();
+            long oldPosition = fc.position();
 
-        if (fc.position() != oldPosition)
-            throw new RuntimeException("Position changed");
+            long bytesWritten = fc.transferFrom(source, 0, size);
+            fc.force(true);
+            if (bytesWritten != size)
+                throw new RuntimeException("Transfer failed");
 
-        if (fc.size() != size)
-            throw new RuntimeException("Unexpected sink size "+ fc.size());
+            if (fc.position() != oldPosition)
+                throw new RuntimeException("Position changed");
 
-        fc.close();
-        sink.close();
-        source.close();
+            if (fc.size() != size)
+                throw new RuntimeException("Unexpected sink size "+ fc.size());
 
-        f.delete();
+            fc.close();
+            sink.close();
+            source.close();
+
+            f.delete();
+        }
     }
 
-    public static void xferTest02() throws Exception {
+    @Test
+    public void xferTest02() throws Exception { // for bug 4482726
         byte[] srcData = new byte[5000];
         for (int i=0; i<5000; i++)
             srcData[i] = (byte)generator.nextInt();
@@ -187,7 +203,8 @@
         dest.delete();
     }
 
-    public static void xferTest03() throws Exception {
+    @Test
+    public void xferTest03() throws Exception { // for bug 4559072
         byte[] srcData = new byte[] {1,2,3,4} ;
 
         // get filechannel for the source file.
@@ -225,7 +242,8 @@
     }
 
     // Test transferTo with large file
-    public static void xferTest04() throws Exception {
+    @Test
+    public void xferTest04() throws Exception { // for bug 4638365
         // Windows and Linux can't handle the really large file sizes for a
         // truncate or a positional write required by the test for 4563125
         String osName = System.getProperty("os.name");
@@ -264,7 +282,8 @@
     }
 
     // Test transferFrom with large file
-    public static void xferTest05() throws Exception {
+    @Test
+    public void xferTest05() throws Exception { // for bug 4638365
         // Create a source file & large sink file for the test
         File source = File.createTempFile("blech", null);
         source.deleteOnExit();
@@ -294,7 +313,7 @@
                      testSize - 40);
         } catch (IOException e) {
             // Can't set up the test, abort it
-            System.err.println("xferTest05 was aborted.");
+            err.println("xferTest05 was aborted.");
             return;
         } finally {
             fc.close();
@@ -337,7 +356,8 @@
     }
 
     // Test transferFrom asking for more bytes than remain in source
-    public static void xferTest06() throws Exception {
+    @Test
+    public void xferTest06() throws Exception { // for bug 5081340
         String data = "Use the source, Luke!";
 
         File source = File.createTempFile("source", null);
@@ -370,7 +390,8 @@
     }
 
     // Test transferTo to non-blocking socket channel
-    public static void xferTest07() throws Exception {
+    @Test
+    public void xferTest07() throws Exception { // for bug 5103988
         File source = File.createTempFile("source", null);
         source.deleteOnExit();
 
@@ -405,7 +426,8 @@
 
 
     // Test transferTo with file positions larger than 2 and 4GB
-    public static void xferTest08() throws Exception {
+    @Test
+    public void xferTest08() throws Exception { // for bug 6253145
         // Creating a sparse 6GB file on Windows takes too long
         String osName = System.getProperty("os.name");
         if (osName.startsWith("Windows"))
@@ -421,10 +443,15 @@
         RandomAccessFile raf = new RandomAccessFile(file, "rw");
         FileChannel fc = raf.getChannel();
 
+        out.println("  Creating large file...");
+        long t0 = System.nanoTime();
         try {
             fc.write(ByteBuffer.wrap("0123456789012345".getBytes("UTF-8")), 6*G);
+            long t1 = System.nanoTime();
+            out.printf("  Created large file in %d ns (%d ms) %n",
+            t1 - t0, TimeUnit.NANOSECONDS.toMillis(t1 - t0));
         } catch (IOException x) {
-            System.err.println("Unable to create test file:" + x);
+            err.println("  Unable to create test file:" + x);
             fc.close();
             return;
         }
@@ -480,7 +507,10 @@
 
                 // write to file and transfer to echo server
                 fc.write(sendbuf, position);
+                t0 = System.nanoTime();
                 fc.transferTo(position, count, source);
+                out.printf("  transferTo(%d, %2d, source): %d ns%n",
+                    position, count, System.nanoTime() - t0);
 
                 // read from echo server
                 long nread = 0;
@@ -495,7 +525,7 @@
                 readbuf.flip();
                 sendbuf.flip();
                 if (!readbuf.equals(sendbuf))
-                    throw new RuntimeException("Echo'ed bytes do not match!");
+                    throw new RuntimeException("Echoed bytes do not match!");
                 readbuf.clear();
                 sendbuf.clear();
             }
@@ -509,7 +539,8 @@
 
     // Test that transferFrom with FileChannel source that is not readable
     // throws NonReadableChannelException
-    static void xferTest09() throws Exception {
+    @Test
+    public void xferTest09() throws Exception { // for bug 6984545
         File source = File.createTempFile("source", null);
         source.deleteOnExit();
 
--- a/jdk/test/java/nio/channels/Selector/SelectTimeout.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/nio/channels/Selector/SelectTimeout.java	Wed Jul 05 22:52:01 2017 +0200
@@ -30,14 +30,13 @@
  */
 import java.io.IOException;
 import java.nio.channels.Selector;
+import java.util.concurrent.atomic.AtomicBoolean;
+import java.util.concurrent.atomic.AtomicReference;
 
 public class SelectTimeout {
     private static final long BIG_TIMEOUT    = 100_000_001_000L; // 8165000
     private static final long BIGGER_TIMEOUT = 850_000_000_000_000L; // 8172547
-    private static final long SLEEP_MILLIS   = 10000;
-
-    private static volatile Exception theException;
-    private static volatile boolean isTimedOut;
+    private static final long SLEEP_MILLIS   = 10_000;
 
     public static void main(String[] args)
         throws IOException, InterruptedException {
@@ -59,17 +58,18 @@
 
     private static boolean test(final long timeout)
         throws InterruptedException, IOException {
-        theException = null;
+        AtomicReference<Exception> theException =
+            new AtomicReference<>();
+        AtomicBoolean isTimedOut = new AtomicBoolean();
 
         Selector selector = Selector.open();
 
         Thread t = new Thread(() -> {
             try {
-                isTimedOut = false;
                 selector.select(timeout);
-                isTimedOut = true;
+                isTimedOut.set(true);
             } catch (IOException ioe) {
-                theException = ioe;
+                theException.set(ioe);
             }
         });
         t.start();
@@ -77,8 +77,8 @@
         t.join(SLEEP_MILLIS);
 
         boolean result;
-        if (theException == null) {
-            if (timeout > SLEEP_MILLIS && isTimedOut) {
+        if (theException.get() == null) {
+            if (timeout > SLEEP_MILLIS && isTimedOut.get()) {
                 System.err.printf("Test timed out early with timeout %d%n",
                     timeout);
                 result = false;
@@ -88,11 +88,12 @@
             }
         } else {
             System.err.printf("Test failed with timeout %d%n", timeout);
-            theException.printStackTrace();
+            theException.get().printStackTrace();
             result = false;
         }
 
         t.interrupt();
+        selector.close();
 
         return result;
     }
--- a/jdk/test/java/nio/file/FileSystem/Basic.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/nio/file/FileSystem/Basic.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2008, 2017, 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
@@ -30,11 +30,18 @@
  */
 
 import java.io.File;
-import java.nio.file.*;
 import java.io.IOException;
 import java.net.URI;
 import java.net.URISyntaxException;
+import java.nio.file.Files;
+import java.nio.file.FileStore;
+import java.nio.file.FileSystem;
+import java.nio.file.FileSystems;
+import java.nio.file.Path;
+import java.nio.file.Paths;
+import java.nio.file.ProviderNotFoundException;
 import java.util.HashMap;
+import java.util.concurrent.TimeUnit;
 import jdk.testlibrary.FileUtils;
 
 /**
@@ -47,6 +54,44 @@
             throw new RuntimeException(msg);
     }
 
+    static void checkFileStores(String os, FileSystem fs) throws IOException {
+        boolean checkFileStores = true;
+        if (!os.equals("Windows")) {
+            // try to check whether 'df' hangs
+            System.out.println("\n--- Begin df output ---");
+            System.out.flush();
+            Process proc = new ProcessBuilder("df").inheritIO().start();
+            try {
+                proc.waitFor(90, TimeUnit.SECONDS);
+            } catch (InterruptedException ignored) {
+            }
+            System.out.println("--- End df output ---\n");
+            System.out.flush();
+            try {
+                int exitValue = proc.exitValue();
+                if (exitValue != 0) {
+                    System.err.printf("df process exited with %d != 0%n",
+                        exitValue);
+                    checkFileStores = false;
+                }
+            } catch (IllegalThreadStateException ignored) {
+                System.err.println("df command apparently hung");
+                checkFileStores = false;
+            }
+        }
+
+        // sanity check method
+        if (checkFileStores) {
+            System.out.println("\n--- Begin FileStores ---");
+            for (FileStore store: fs.getFileStores()) {
+                System.out.println(store);
+            }
+            System.out.println("--- EndFileStores ---\n");
+        } else {
+            System.err.println("Skipping FileStore check due to df failure");
+        }
+    }
+
     static void checkSupported(FileSystem fs, String... views) {
         for (String view: views) {
             check(fs.supportedFileAttributeViews().contains(view),
@@ -70,7 +115,9 @@
         }
     }
 
-    public static void main(String[] args) throws IOException, URISyntaxException {
+    public static void main(String[] args)
+        throws IOException, URISyntaxException {
+        String os = System.getProperty("os.name");
         FileSystem fs = FileSystems.getDefault();
 
         // close should throw UOE
@@ -85,15 +132,11 @@
         check(fs.provider().getScheme().equals("file"),
             "should use 'file' scheme");
 
-        // santity check method - need to re-visit this in future as I/O errors
-        // are possible
-        for (FileStore store: fs.getFileStores()) {
-            System.out.println(store);
-        }
+        // sanity check FileStores
+        checkFileStores(os, fs);
 
         // sanity check supportedFileAttributeViews
         checkSupported(fs, "basic");
-        String os = System.getProperty("os.name");
         if (os.equals("SunOS"))
             checkSupported(fs, "posix", "unix", "owner", "acl", "user");
         if (os.equals("Linux"))
--- a/jdk/test/java/security/modules/ModularTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/security/modules/ModularTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -164,9 +164,9 @@
         final Builder builder;
         if (moduleType == MODULE_TYPE.EXPLICIT) {
             System.out.format(" %nGenerating ModuleDescriptor object");
-            builder = ModuleDescriptor.module(moduleName).exports(pkg);
+            builder = ModuleDescriptor.newModule(moduleName).exports(pkg);
             if (isService && serviceInterface != null && serviceImpl != null) {
-                builder.provides(serviceInterface, serviceImpl);
+                builder.provides(serviceInterface, List.of(serviceImpl));
             } else {
                 if (serviceInterface != null) {
                     builder.uses(serviceInterface);
--- a/jdk/test/java/time/TEST.properties	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/time/TEST.properties	Wed Jul 05 22:52:01 2017 +0200
@@ -1,6 +1,5 @@
-# Threeten test uses TestNG
+# java.time tests use TestNG
 TestNG.dirs = .
 othervm.dirs = tck/java/time/chrono test/java/time/chrono test/java/time/format
 lib.dirs = ../../lib/testlibrary
 lib.build = jdk.testlibrary.RandomFactory
-modules = java.base/java.time:open java.base/java.time.chrono:open java.base/java.time.zone:open
--- a/jdk/test/java/time/tck/java/time/AbstractTCKTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/time/tck/java/time/AbstractTCKTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012, 2017, 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
@@ -69,14 +69,35 @@
 import java.io.ObjectOutputStream;
 import java.io.ObjectStreamConstants;
 import java.io.Serializable;
-import java.lang.reflect.Field;
 import java.util.Formatter;
+import java.util.Map;
 
 /**
  * Base test class.
  */
 public abstract class AbstractTCKTest {
 
+    /**
+     * Map from package name to the serialVersionUID of the .Ser class for the package.
+     */
+    private static Map<String, Long> serialVersionUIDs = Map.of(
+                "java.time",        -7683839454370182990L,
+                "java.time.chrono", -6103370247208168577L,
+                "java.time.zone",   -8885321777449118786L
+                );
+
+    /**
+     * Returns the serialVersionUID for the class.
+     * The SUIDs are defined by the specification for each class.
+     * @param serClass the class to return the SUID of
+     * @return returns the serialVersionUID for the class
+     */
+    public final static long getSUID(Class<?> serClass) {
+        String pkgName = serClass.getPackageName();
+        return serialVersionUIDs.get(pkgName);
+    }
+
+
     protected static boolean isIsoLeap(long year) {
         if (year % 4 != 0) {
             return false;
@@ -111,10 +132,8 @@
 
     protected static void assertSerializedBySer(Object object, byte[] expectedBytes, byte[]... matches) throws Exception {
         String serClass = object.getClass().getPackage().getName() + ".Ser";
-        Class<?> serCls = Class.forName(serClass);
-        Field field = serCls.getDeclaredField("serialVersionUID");
-        field.setAccessible(true);
-        long serVer = (Long) field.get(null);
+        long serVer = getSUID(object.getClass());
+
         ByteArrayOutputStream baos = new ByteArrayOutputStream();
         try (ObjectOutputStream oos = new ObjectOutputStream(baos) ) {
             oos.writeObject(object);
@@ -172,9 +191,8 @@
      * @throws Exception if an unexpected condition occurs
      */
     protected static void assertNotSerializable(Class<?> serClass) throws Exception {
-        Field field = serClass.getDeclaredField("serialVersionUID");
-        field.setAccessible(true);
-        long serVer = (Long) field.get(null);
+        long serVer = getSUID(serClass);
+
         ByteArrayOutputStream baos = new ByteArrayOutputStream();
         try (DataOutputStream out = new DataOutputStream(baos)) {
             out.writeShort(ObjectStreamConstants.STREAM_MAGIC);
@@ -201,7 +219,6 @@
         fail("Class should not be deserializable " + serClass.getName());
     }
 
-
     /**
      * Utility method to dump a byte array in a java syntax.
      * @param bytes and array of bytes
--- a/jdk/test/java/time/tck/java/time/TCKOffsetDateTime.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/time/tck/java/time/TCKOffsetDateTime.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012, 2017, 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
@@ -104,8 +104,6 @@
 import static org.testng.Assert.assertTrue;
 import static org.testng.Assert.fail;
 
-import java.lang.reflect.Constructor;
-import java.lang.reflect.InvocationTargetException;
 import java.time.Clock;
 import java.time.DateTimeException;
 import java.time.Duration;
@@ -470,24 +468,12 @@
     //-----------------------------------------------------------------------
     @Test(expectedExceptions=NullPointerException.class)
     public void constructor_nullTime() throws Throwable  {
-        Constructor<OffsetDateTime> con = OffsetDateTime.class.getDeclaredConstructor(LocalDateTime.class, ZoneOffset.class);
-        con.setAccessible(true);
-        try {
-            con.newInstance(null, OFFSET_PONE);
-        } catch (InvocationTargetException ex) {
-            throw ex.getCause();
-        }
+        OffsetDateTime.of(null, OFFSET_PONE);
     }
 
     @Test(expectedExceptions=NullPointerException.class)
     public void constructor_nullOffset() throws Throwable  {
-        Constructor<OffsetDateTime> con = OffsetDateTime.class.getDeclaredConstructor(LocalDateTime.class, ZoneOffset.class);
-        con.setAccessible(true);
-        try {
-            con.newInstance(LocalDateTime.of(LocalDate.of(2008, 6, 30), LocalTime.of(11, 30)), null);
-        } catch (InvocationTargetException ex) {
-            throw ex.getCause();
-        }
+        OffsetDateTime.of(LocalDateTime.of(LocalDate.of(2008, 6, 30), LocalTime.of(11, 30)), null);
     }
 
     //-----------------------------------------------------------------------
--- a/jdk/test/java/time/tck/java/time/TCKOffsetTime.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/time/tck/java/time/TCKOffsetTime.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012, 2017, 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
@@ -89,8 +89,6 @@
 import static org.testng.Assert.assertTrue;
 import static org.testng.Assert.fail;
 
-import java.lang.reflect.Constructor;
-import java.lang.reflect.InvocationTargetException;
 import java.time.Clock;
 import java.time.DateTimeException;
 import java.time.Instant;
@@ -465,28 +463,16 @@
     }
 
     //-----------------------------------------------------------------------
-    // constructor
+    // constructor via factory
     //-----------------------------------------------------------------------
     @Test(expectedExceptions=NullPointerException.class)
     public void constructor_nullTime() throws Throwable  {
-        Constructor<OffsetTime> con = OffsetTime.class.getDeclaredConstructor(LocalTime.class, ZoneOffset.class);
-        con.setAccessible(true);
-        try {
-            con.newInstance(null, OFFSET_PONE);
-        } catch (InvocationTargetException ex) {
-            throw ex.getCause();
-        }
+        OffsetTime.of(null, OFFSET_PONE);
     }
 
     @Test(expectedExceptions=NullPointerException.class)
     public void constructor_nullOffset() throws Throwable  {
-        Constructor<OffsetTime> con = OffsetTime.class.getDeclaredConstructor(LocalTime.class, ZoneOffset.class);
-        con.setAccessible(true);
-        try {
-            con.newInstance(LocalTime.of(11, 30, 0, 0), null);
-        } catch (InvocationTargetException ex) {
-            throw ex.getCause();
-        }
+       OffsetTime.of(LocalTime.of(11, 30, 0, 0), null);
     }
 
     //-----------------------------------------------------------------------
--- a/jdk/test/java/time/tck/java/time/serial/TCKZoneIdSerialization.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/time/tck/java/time/serial/TCKZoneIdSerialization.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012, 2017, 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
@@ -63,8 +63,11 @@
 import org.testng.annotations.Test;
 import tck.java.time.AbstractTCKTest;
 
-import java.io.*;
-import java.lang.reflect.Field;
+import java.io.ByteArrayInputStream;
+import java.io.ByteArrayOutputStream;
+import java.io.DataOutputStream;
+import java.io.ObjectInputStream;
+import java.io.ObjectStreamConstants;
 import java.time.DateTimeException;
 import java.time.ZoneId;
 import java.time.zone.ZoneRulesException;
@@ -153,10 +156,8 @@
 
     private ZoneId deserialize(String id) throws Exception {
         String serClass = ZoneId.class.getPackage().getName() + ".Ser";
-        Class<?> serCls = Class.forName(serClass);
-        Field field = serCls.getDeclaredField("serialVersionUID");
-        field.setAccessible(true);
-        long serVer = (Long) field.get(null);
+        long serVer = getSUID(ZoneId.class);
+
         ByteArrayOutputStream baos = new ByteArrayOutputStream();
         try (DataOutputStream dos = new DataOutputStream(baos)) {
             dos.writeShort(ObjectStreamConstants.STREAM_MAGIC);
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/time/test/java/time/TEST.properties	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,2 @@
+# java.time test system clock
+modules = java.base/java.time:open
--- a/jdk/test/java/util/ServiceLoader/modules/BadProvidersTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/util/ServiceLoader/modules/BadProvidersTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -90,7 +90,7 @@
         Layer bootLayer = Layer.boot();
 
         Configuration cf = bootLayer.configuration()
-                .resolveRequiresAndUses(finder, ModuleFinder.of(), Set.of(moduleName));
+                .resolveAndBind(finder, ModuleFinder.of(), Set.of(moduleName));
 
         ClassLoader scl = ClassLoader.getSystemClassLoader();
 
--- a/jdk/test/java/util/ServiceLoader/modules/Basic.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/java/util/ServiceLoader/modules/Basic.java	Wed Jul 05 22:52:01 2017 +0200
@@ -311,17 +311,17 @@
         ModuleFinder finder = ModuleFinder.of(dir);
 
         // layer1
-        Configuration cf1 = cf0.resolveRequiresAndUses(finder, ModuleFinder.of(), Set.of());
+        Configuration cf1 = cf0.resolveAndBind(finder, ModuleFinder.of(), Set.of());
         Layer layer1 = bootLayer.defineModulesWithOneLoader(cf1, scl);
         assertTrue(layer1.modules().size() == 1);
 
         // layer2
-        Configuration cf2 = cf0.resolveRequiresAndUses(finder, ModuleFinder.of(), Set.of());
+        Configuration cf2 = cf0.resolveAndBind(finder, ModuleFinder.of(), Set.of());
         Layer layer2 = bootLayer.defineModulesWithOneLoader(cf2, scl);
         assertTrue(layer2.modules().size() == 1);
 
         // layer3 with layer1 and layer2 as parents
-        Configuration cf3 = Configuration.resolveRequiresAndUses(finder,
+        Configuration cf3 = Configuration.resolveAndBind(finder,
                 List.of(cf1, cf2),
                 ModuleFinder.of(),
                 Set.of());
@@ -413,7 +413,7 @@
         Collections.addAll(roots, modules);
         Layer bootLayer = Layer.boot();
         Configuration parent = bootLayer.configuration();
-        Configuration cf = parent.resolveRequires(finder, ModuleFinder.of(), roots);
+        Configuration cf = parent.resolve(finder, ModuleFinder.of(), roots);
         ClassLoader scl = ClassLoader.getSystemClassLoader();
         Layer layer = bootLayer.defineModulesWithOneLoader(cf, scl);
         assertTrue(layer.modules().size() == 1);
--- a/jdk/test/javax/xml/jaxp/common/8035437/Document.java	Mon Feb 13 11:57:56 2017 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,28 +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.
- *
- * 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 org.w3c.dom;
-
-public interface Document {
-
-    public org.w3c.dom.DocumentType getDoctype();
-}
--- a/jdk/test/javax/xml/jaxp/common/8035437/DocumentImpl.java	Mon Feb 13 11:57:56 2017 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,67 +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.
- *
- * 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 com.sun.org.apache.xerces.internal.dom;
-
-import org.w3c.dom.Document;
-import org.w3c.dom.Node;
-import org.w3c.dom.DOMImplementation;
-
-public class DocumentImpl implements Document, Node {
-
-    public short getNodeType() {
-        return 9; //DOCUMENT_NODE = 9
-    }
-
-    public org.w3c.dom.Document getOwnerDocument() {
-        return null;
-    }
-
-    public Node getFirstChild() {
-        return null;
-    }
-
-    public String getPrefix() {
-        return "TestPrefix";
-    }
-
-    public String getLocalName() {
-        return "LocalName";
-    }
-
-    public boolean hasAttributes() {
-        return false;
-    }
-
-    public Node renameNode(Node n, String namespaceURI, String name) {
-        return n;
-    }
-
-    public org.w3c.dom.DocumentType getDoctype() {
-        return null;
-    }
-
-    public DOMImplementation getImplementation() {
-        return DOMImplementationImpl.getDOMImplementation();
-    }
-
-}
--- a/jdk/test/javax/xml/jaxp/common/8035437/Node.java	Mon Feb 13 11:57:56 2017 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,38 +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.
- *
- * 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 org.w3c.dom;
-
-public interface Node {
-
-    public short getNodeType();
-
-    public org.w3c.dom.Document getOwnerDocument();
-
-    public Node getFirstChild();
-
-    public String getPrefix();
-
-    public String getLocalName();
-
-    public boolean hasAttributes();
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/javax/xml/jaxp/common/8035437/patch-src1/org/w3c/dom/Document.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,28 @@
+/*
+ * 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.
+ *
+ * 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 org.w3c.dom;
+
+public interface Document {
+
+    public org.w3c.dom.DocumentType getDoctype();
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/javax/xml/jaxp/common/8035437/patch-src1/org/w3c/dom/Node.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,38 @@
+/*
+ * 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.
+ *
+ * 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 org.w3c.dom;
+
+public interface Node {
+
+    public short getNodeType();
+
+    public org.w3c.dom.Document getOwnerDocument();
+
+    public Node getFirstChild();
+
+    public String getPrefix();
+
+    public String getLocalName();
+
+    public boolean hasAttributes();
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/javax/xml/jaxp/common/8035437/patch-src2/com/sun/org/apache/xerces/internal/dom/DocumentImpl.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,67 @@
+/*
+ * 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.
+ *
+ * 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 com.sun.org.apache.xerces.internal.dom;
+
+import org.w3c.dom.Document;
+import org.w3c.dom.Node;
+import org.w3c.dom.DOMImplementation;
+
+public class DocumentImpl implements Document, Node {
+
+    public short getNodeType() {
+        return 9; //DOCUMENT_NODE = 9
+    }
+
+    public org.w3c.dom.Document getOwnerDocument() {
+        return null;
+    }
+
+    public Node getFirstChild() {
+        return null;
+    }
+
+    public String getPrefix() {
+        return "TestPrefix";
+    }
+
+    public String getLocalName() {
+        return "LocalName";
+    }
+
+    public boolean hasAttributes() {
+        return false;
+    }
+
+    public Node renameNode(Node n, String namespaceURI, String name) {
+        return n;
+    }
+
+    public org.w3c.dom.DocumentType getDoctype() {
+        return null;
+    }
+
+    public DOMImplementation getImplementation() {
+        return DOMImplementationImpl.getDOMImplementation();
+    }
+
+}
--- a/jdk/test/javax/xml/jaxp/common/8035437/run.sh	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/javax/xml/jaxp/common/8035437/run.sh	Wed Jul 05 22:52:01 2017 +0200
@@ -28,13 +28,43 @@
 # @summary Tests that java.lang.AbstractMethodError is not thrown when
 #    serializing improper version of DocumentImpl class.
 
+OS=`uname -s`
+case "$OS" in
+  SunOS )
+    PS=":"
+    ;;
+  Linux )
+    PS=":"
+    ;;
+  Darwin )
+    PS=":"
+    ;;
+  AIX )
+    PS=":"
+    ;;
+  Windows*)
+    PS=";"
+    ;;
+  CYGWIN*)
+    PS=";"
+    ;;
+  * )
+    echo "Unrecognized system!"
+    exit 1;
+    ;;
+esac
+
 mkdir -p exec/java.xml compile/java.xml
 
 $COMPILEJAVA/bin/javac ${TESTJAVACOPTS} ${TESTTOOLVMOPTS} \
-   -d compile/java.xml -Xmodule:java.xml $TESTSRC/Document.java $TESTSRC/Node.java || exit 1
+   -d compile/java.xml --patch-module java.xml=$TESTSRC/patch-src1 \
+   $TESTSRC/patch-src1/org/w3c/dom/Document.java \
+   $TESTSRC/patch-src1/org/w3c/dom/Node.java || exit 1
 
 $COMPILEJAVA/bin/javac ${TESTJAVACOPTS} ${TESTTOOLVMOPTS} \
-   -d exec/java.xml --patch-module java.xml=compile/java.xml -Xmodule:java.xml $TESTSRC/DocumentImpl.java || exit 2
+   -d exec/java.xml --patch-module java.xml=compile/java.xml${PS}$TESTSRC/patch-src2 \
+   $TESTSRC/patch-src2/com/sun/org/apache/xerces/internal/dom/DocumentImpl.java \
+   || exit 2
 
 $COMPILEJAVA/bin/javac ${TESTJAVACOPTS} ${TESTTOOLVMOPTS} \
    $TESTSRC/AbstractMethodErrorTest.java -d exec || exit 3
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/jdk/internal/reflect/CallerSensitive/CheckCSMs.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,251 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+
+import com.sun.tools.classfile.*;
+import com.sun.tools.jdeps.ClassFileReader;
+import static com.sun.tools.classfile.ConstantPool.*;
+import java.io.File;
+import java.io.IOException;
+import java.io.UncheckedIOException;
+import java.net.URI;
+import java.nio.file.FileSystem;
+import java.nio.file.FileSystems;
+import java.nio.file.Files;
+import java.nio.file.Path;
+import java.nio.file.Paths;
+import java.util.ArrayList;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
+import java.util.concurrent.Callable;
+import java.util.concurrent.ConcurrentSkipListSet;
+import java.util.concurrent.ExecutionException;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+import java.util.concurrent.FutureTask;
+import java.util.stream.Collectors;
+import java.util.stream.Stream;
+
+/*
+ * @test
+ * @summary CallerSensitive methods should be static or final instance
+ *          methods except the known list of non-final instance methods
+ * @modules jdk.jdeps/com.sun.tools.classfile
+ *          jdk.jdeps/com.sun.tools.jdeps
+ * @build CheckCSMs
+ * @run main/othervm/timeout=900 CheckCSMs
+ */
+public class CheckCSMs {
+    private static int numThreads = 3;
+    private static boolean listCSMs = false;
+    private final ExecutorService pool;
+
+    // The goal is to remove this list of Non-final instance @CS methods
+    // over time.  Do not add any new one to this list.
+    private static Set<String> KNOWN_NON_FINAL_CSMS =
+      Set.of("java/io/ObjectStreamField#getType ()Ljava/lang/Class;",
+             "java/io/ObjectStreamClass#forClass ()Ljava/lang/Class;",
+             "java/lang/Runtime#load (Ljava/lang/String;)V",
+             "java/lang/Runtime#loadLibrary (Ljava/lang/String;)V",
+             "java/lang/Thread#getContextClassLoader ()Ljava/lang/ClassLoader;",
+             "javax/sql/rowset/serial/SerialJavaObject#getFields ()[Ljava/lang/reflect/Field;"
+      );
+
+    public static void main(String[] args) throws Exception {
+        if (args.length > 0 && args[0].equals("--list")) {
+            listCSMs = true;
+        }
+
+        CheckCSMs checkCSMs = new CheckCSMs();
+        Set<String> result = checkCSMs.run(getPlatformClasses());
+        if (!KNOWN_NON_FINAL_CSMS.equals(result)) {
+            Set<String> diff = new HashSet<>(result);
+            diff.removeAll(KNOWN_NON_FINAL_CSMS);
+            throw new RuntimeException("Unexpected non-final instance method: " +
+                result.stream().sorted()
+                      .collect(Collectors.joining("\n", "\n", "")));
+        }
+    }
+
+    private final Set<String> nonFinalCSMs = new ConcurrentSkipListSet<>();
+    private final ReferenceFinder finder;
+    public CheckCSMs() {
+        this.finder = new ReferenceFinder(getFilter(), getVisitor());
+        pool = Executors.newFixedThreadPool(numThreads);
+
+    }
+
+    public Set<String> run(Stream<Path> classes)
+        throws IOException, InterruptedException, ExecutionException,
+               ConstantPoolException
+    {
+        classes.forEach(this::processPath);
+        waitForCompletion();
+        pool.shutdown();
+        return nonFinalCSMs;
+    }
+
+
+    private ReferenceFinder.Filter getFilter() {
+        final String classname = "jdk/internal/reflect/Reflection";
+        final String method = "getCallerClass";
+        return new ReferenceFinder.Filter() {
+            public boolean accept(ConstantPool cpool, CPRefInfo cpref) {
+                try {
+                    CONSTANT_NameAndType_info nat = cpref.getNameAndTypeInfo();
+                    return cpref.getClassName().equals(classname) && nat.getName().equals(method);
+                } catch (ConstantPoolException ex) {
+                    throw new RuntimeException(ex);
+                }
+            }
+        };
+    }
+
+    private ReferenceFinder.Visitor getVisitor() {
+        return new ReferenceFinder.Visitor() {
+            public void visit(ClassFile cf, Method m,  List<CPRefInfo> refs) {
+                try {
+                    // ignore jdk.unsupported/sun.reflect.Reflection.getCallerClass
+                    // which is a "special" delegate to the internal getCallerClass
+                    if (cf.getName().equals("sun/reflect/Reflection") &&
+                        m.getName(cf.constant_pool).equals("getCallerClass"))
+                        return;
+
+                    String name = String.format("%s#%s %s", cf.getName(),
+                                                m.getName(cf.constant_pool),
+                                                m.descriptor.getValue(cf.constant_pool));
+                    if (!CheckCSMs.isStaticOrFinal(cf, m, cf.constant_pool)) {
+                        System.err.println("Unsupported @CallerSensitive: " + name);
+                        nonFinalCSMs.add(name);
+                    } else {
+                        if (listCSMs) {
+                            System.out.format("@CS  %s%n", name);
+                        }
+                    }
+                } catch (ConstantPoolException ex) {
+                    throw new RuntimeException(ex);
+                }
+            }
+        };
+    }
+
+    void processPath(Path path) {
+        try {
+            ClassFileReader reader = ClassFileReader.newInstance(path);
+            for (ClassFile cf : reader.getClassFiles()) {
+                if (cf.access_flags.is(AccessFlags.ACC_MODULE))
+                    continue;
+
+                String classFileName = cf.getName();
+                // for each ClassFile
+                //    parse constant pool to find matching method refs
+                //      parse each method (caller)
+                //      - visit and find method references matching the given method name
+                pool.submit(getTask(cf));
+            }
+        } catch (IOException x) {
+            throw new UncheckedIOException(x);
+        } catch (ConstantPoolException x) {
+            throw new RuntimeException(x);
+        }
+    }
+
+    private static final String CALLER_SENSITIVE_ANNOTATION
+        = "Ljdk/internal/reflect/CallerSensitive;";
+
+    private static boolean isCallerSensitive(Method m, ConstantPool cp)
+        throws ConstantPoolException
+    {
+        RuntimeAnnotations_attribute attr =
+            (RuntimeAnnotations_attribute)m.attributes.get(Attribute.RuntimeVisibleAnnotations);
+        if (attr != null) {
+            for (int i = 0; i < attr.annotations.length; i++) {
+                Annotation ann = attr.annotations[i];
+                String annType = cp.getUTF8Value(ann.type_index);
+                if (CALLER_SENSITIVE_ANNOTATION.equals(annType)) {
+                    return true;
+                }
+            }
+        }
+        return false;
+    }
+
+    private static boolean isStaticOrFinal(ClassFile cf, Method m, ConstantPool cp)
+        throws ConstantPoolException
+    {
+        if (!isCallerSensitive(m, cp))
+            return false;
+
+        // either a static method or a final instance method
+        return m.access_flags.is(AccessFlags.ACC_STATIC) ||
+               m.access_flags.is(AccessFlags.ACC_FINAL) ||
+               cf.access_flags.is(AccessFlags.ACC_FINAL);
+    }
+
+    private final List<FutureTask<Void>> tasks = new ArrayList<FutureTask<Void>>();
+    private FutureTask<Void> getTask(final ClassFile cf) {
+        FutureTask<Void> task = new FutureTask<Void>(new Callable<Void>() {
+            public Void call() throws Exception {
+                finder.parse(cf);
+                return null;
+            }
+        });
+        tasks.add(task);
+        return task;
+    }
+
+    private void waitForCompletion() throws InterruptedException, ExecutionException {
+        for (FutureTask<Void> t : tasks) {
+            t.get();
+        }
+        if (tasks.isEmpty()) {
+            throw new RuntimeException("No classes found, or specified.");
+        }
+        System.out.println("Parsed " + tasks.size() + " classfiles");
+    }
+
+    static Stream<Path> getPlatformClasses() throws IOException {
+        Path home = Paths.get(System.getProperty("java.home"));
+
+        // Either an exploded build or an image.
+        File classes = home.resolve("modules").toFile();
+        if (classes.isDirectory()) {
+            return Stream.of(classes.toPath());
+        } else {
+            return jrtPaths();
+        }
+    }
+
+    static Stream<Path> jrtPaths() {
+        FileSystem jrt = FileSystems.getFileSystem(URI.create("jrt:/"));
+        Path root = jrt.getPath("/");
+
+        try {
+            return Files.walk(root)
+                    .filter(p -> p.getNameCount() > 1)
+                    .filter(p -> p.toString().endsWith(".class"));
+        } catch (IOException x) {
+            throw new UncheckedIOException(x);
+        }
+    }
+}
--- a/jdk/test/jdk/modules/etc/VerifyModuleDelegation.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/jdk/modules/etc/VerifyModuleDelegation.java	Wed Jul 05 22:52:01 2017 +0200
@@ -46,7 +46,7 @@
     private static final String JAVA_BASE = "java.base";
 
     private static final ModuleDescriptor BASE
-        = ModuleDescriptor.module(JAVA_BASE).build();
+        = ModuleDescriptor.newModule(JAVA_BASE).build();
 
     private static final Set<ModuleDescriptor> MREFS
             = Layer.boot().modules().stream().map(Module::getDescriptor)
--- a/jdk/test/jdk/modules/scenarios/container/src/container/container/Main.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/jdk/modules/scenarios/container/src/container/container/Main.java	Wed Jul 05 22:52:01 2017 +0200
@@ -71,9 +71,9 @@
         ModuleFinder finder = ModuleFinder.of(paths);
 
         Configuration cf = Layer.boot().configuration()
-            .resolveRequiresAndUses(finder,
-                                    ModuleFinder.of(),
-                                    Set.of(appModuleName));
+            .resolveAndBind(finder,
+                            ModuleFinder.of(),
+                            Set.of(appModuleName));
 
         System.out.println("Resolved");
         cf.modules().stream()
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/org/omg/CORBA/OrbPropertiesTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,78 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+
+import java.io.BufferedWriter;
+import java.io.FileWriter;
+import java.io.IOException;
+import java.io.PrintWriter;
+
+import org.omg.CORBA.ORB;
+
+/*
+ * @test
+ * @bug 8049375
+ * @summary Extend how the org.omg.CORBA.ORB handles the search for orb.properties
+ * @library /lib/testlibrary
+ * @build jdk.testlibrary.*
+ * @modules java.corba
+ * @compile OrbPropertiesTest.java TestOrbImpl.java TestSingletonOrbImpl.java
+ * @run main/othervm
+ *    -Djava.naming.provider.url=iiop://localhost:1050
+ *    -Djava.naming.factory.initial=com.sun.jndi.cosnaming.CNCtxFactory
+ *    OrbPropertiesTest -port 1049
+ * @run main/othervm/secure=java.lang.SecurityManager/policy=jtreg.test.policy
+ *    -Djava.naming.provider.url=iiop://localhost:3050
+ *    -Djava.naming.factory.initial=com.sun.jndi.cosnaming.CNCtxFactory
+ *    OrbPropertiesTest -port 3049
+ */
+public class OrbPropertiesTest {
+
+    public static void main(String[] args) throws Exception {
+        updateOrbPropertiesFile();
+        // create and initialize the ORB
+        ORB orb = ORB.init(args, null);
+        if (!(orb instanceof TestOrbImpl)) {
+            throw new RuntimeException("org.omg.CORBA.ORBClass property not set as expected");
+        }
+        ORB singletonOrb = ORB.init();
+        System.out.println("singletonOrb class == " + singletonOrb.getClass().getName());
+        if (!(singletonOrb instanceof TestSingletonOrbImpl)) {
+            throw new RuntimeException("org.omg.CORBA.ORBSingletonClass property not set as expected");
+        }
+
+    }
+
+    private static void updateOrbPropertiesFile() throws Exception {
+        String orbPropertiesFile = System.getProperty("java.home", ".") + "/conf/orb.properties";
+        String orbClassMapping = "org.omg.CORBA.ORBClass TestOrbImpl";
+        String orbSingletonClassMapping = "org.omg.CORBA.ORBSingletonClass TestSingletonOrbImpl";
+        String orbPropertiesMappings = orbClassMapping + "\n" + orbSingletonClassMapping +"\n";
+        try (PrintWriter hfPWriter = new PrintWriter(new BufferedWriter(
+                new FileWriter(orbPropertiesFile, false)))) {
+            hfPWriter.println(orbPropertiesMappings);
+        } catch (IOException ioEx) {
+            ioEx.printStackTrace();
+            throw ioEx;
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/org/omg/CORBA/TestOrbImpl.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,203 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+
+import java.applet.Applet;
+import java.util.Properties;
+
+import org.omg.CORBA.Any;
+import org.omg.CORBA.Context;
+import org.omg.CORBA.ContextList;
+import org.omg.CORBA.Environment;
+import org.omg.CORBA.ExceptionList;
+import org.omg.CORBA.NVList;
+import org.omg.CORBA.NamedValue;
+import org.omg.CORBA.ORB;
+import org.omg.CORBA.Object;
+import org.omg.CORBA.Request;
+import org.omg.CORBA.StructMember;
+import org.omg.CORBA.TCKind;
+import org.omg.CORBA.TypeCode;
+import org.omg.CORBA.UnionMember;
+import org.omg.CORBA.WrongTransaction;
+import org.omg.CORBA.ORBPackage.InvalidName;
+import org.omg.CORBA.portable.OutputStream;
+
+
+public class TestOrbImpl extends ORB{
+
+    @Override
+    protected void set_parameters(String[] args, Properties props) {
+
+    }
+
+    @Override
+    protected void set_parameters(Applet app, Properties props) {
+
+    }
+
+    @Override
+    public String[] list_initial_services() {
+        return null;
+    }
+
+    @Override
+    public Object resolve_initial_references(String object_name)
+            throws InvalidName {
+        return null;
+    }
+
+    @Override
+    public String object_to_string(Object obj) {
+        return null;
+    }
+
+    @Override
+    public Object string_to_object(String str) {
+        return null;
+    }
+
+    @Override
+    public NVList create_list(int count) {
+        return null;
+    }
+
+    @Override
+    public NamedValue create_named_value(String s, Any any, int flags) {
+        return null;
+    }
+
+    @Override
+    public ExceptionList create_exception_list() {
+        return null;
+    }
+
+    @Override
+    public ContextList create_context_list() {
+        return null;
+    }
+
+    @Override
+    public Context get_default_context() {
+        return null;
+    }
+
+    @Override
+    public Environment create_environment() {
+        return null;
+    }
+
+    @Override
+    public OutputStream create_output_stream() {
+        return null;
+    }
+
+    @Override
+    public void send_multiple_requests_oneway(Request[] req) {
+
+    }
+
+    @Override
+    public void send_multiple_requests_deferred(Request[] req) {
+
+    }
+
+    @Override
+    public boolean poll_next_response() {
+        return false;
+    }
+
+    @Override
+    public Request get_next_response() throws WrongTransaction {
+        return null;
+    }
+
+    @Override
+    public TypeCode get_primitive_tc(TCKind tcKind) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_struct_tc(String id, String name,
+            StructMember[] members) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_union_tc(String id, String name,
+            TypeCode discriminator_type, UnionMember[] members) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_enum_tc(String id, String name, String[] members) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_alias_tc(String id, String name,
+            TypeCode original_type) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_exception_tc(String id, String name,
+            StructMember[] members) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_interface_tc(String id, String name) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_string_tc(int bound) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_wstring_tc(int bound) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_sequence_tc(int bound, TypeCode element_type) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_recursive_sequence_tc(int bound, int offset) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_array_tc(int length, TypeCode element_type) {
+        return null;
+    }
+
+    @Override
+    public Any create_any() {
+        return null;
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/org/omg/CORBA/TestSingletonOrbImpl.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,203 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+
+import java.applet.Applet;
+import java.util.Properties;
+
+import org.omg.CORBA.Any;
+import org.omg.CORBA.Context;
+import org.omg.CORBA.ContextList;
+import org.omg.CORBA.Environment;
+import org.omg.CORBA.ExceptionList;
+import org.omg.CORBA.NVList;
+import org.omg.CORBA.NamedValue;
+import org.omg.CORBA.ORB;
+import org.omg.CORBA.Object;
+import org.omg.CORBA.Request;
+import org.omg.CORBA.StructMember;
+import org.omg.CORBA.TCKind;
+import org.omg.CORBA.TypeCode;
+import org.omg.CORBA.UnionMember;
+import org.omg.CORBA.WrongTransaction;
+import org.omg.CORBA.ORBPackage.InvalidName;
+import org.omg.CORBA.portable.OutputStream;
+
+
+public class TestSingletonOrbImpl extends ORB {
+
+    @Override
+    protected void set_parameters(String[] args, Properties props) {
+
+    }
+
+    @Override
+    protected void set_parameters(Applet app, Properties props) {
+
+    }
+
+    @Override
+    public String[] list_initial_services() {
+        return null;
+    }
+
+    @Override
+    public Object resolve_initial_references(String object_name)
+            throws InvalidName {
+        return null;
+    }
+
+    @Override
+    public String object_to_string(Object obj) {
+        return null;
+    }
+
+    @Override
+    public Object string_to_object(String str) {
+        return null;
+    }
+
+    @Override
+    public NVList create_list(int count) {
+        return null;
+    }
+
+    @Override
+    public NamedValue create_named_value(String s, Any any, int flags) {
+        return null;
+    }
+
+    @Override
+    public ExceptionList create_exception_list() {
+        return null;
+    }
+
+    @Override
+    public ContextList create_context_list() {
+        return null;
+    }
+
+    @Override
+    public Context get_default_context() {
+        return null;
+    }
+
+    @Override
+    public Environment create_environment() {
+        return null;
+    }
+
+    @Override
+    public OutputStream create_output_stream() {
+        return null;
+    }
+
+    @Override
+    public void send_multiple_requests_oneway(Request[] req) {
+
+    }
+
+    @Override
+    public void send_multiple_requests_deferred(Request[] req) {
+
+    }
+
+    @Override
+    public boolean poll_next_response() {
+        return false;
+    }
+
+    @Override
+    public Request get_next_response() throws WrongTransaction {
+        return null;
+    }
+
+    @Override
+    public TypeCode get_primitive_tc(TCKind tcKind) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_struct_tc(String id, String name,
+            StructMember[] members) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_union_tc(String id, String name,
+            TypeCode discriminator_type, UnionMember[] members) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_enum_tc(String id, String name, String[] members) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_alias_tc(String id, String name,
+            TypeCode original_type) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_exception_tc(String id, String name,
+            StructMember[] members) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_interface_tc(String id, String name) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_string_tc(int bound) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_wstring_tc(int bound) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_sequence_tc(int bound, TypeCode element_type) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_recursive_sequence_tc(int bound, int offset) {
+        return null;
+    }
+
+    @Override
+    public TypeCode create_array_tc(int length, TypeCode element_type) {
+        return null;
+    }
+
+    @Override
+    public Any create_any() {
+        return null;
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/org/omg/CORBA/jtreg.test.policy	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,32 @@
+/*
+ * Copyright (c) 2016, 2017, 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.
+ */
+
+grant {
+  permission java.util.PropertyPermission "*", "read";
+  permission java.io.FilePermission "<<ALL FILES>>", "read, write, execute";
+};
+
+grant codeBase "file:${test.classes}/*" {
+  permission java.net.SocketPermission "*:*", "connect, accept, listen, resolve";
+  permission java.lang.RuntimePermission "accessClassInPackage.com.sun.jndi.cosnaming";
+};
--- a/jdk/test/sun/management/jdp/JdpJmxRemoteDynamicPortTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/sun/management/jdp/JdpJmxRemoteDynamicPortTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -27,7 +27,7 @@
  *  @summary Verify a non-zero value is assigned to jmxremote.port
  *           when VM is started with jmxremote.port=0.
  *  @library /lib/testlibrary
- *  @modules java.management/sun.management.jdp
+ *  @modules jdk.management.agent/sun.management.jdp
  *  @build jdk.testlibrary.* ClientConnection JdpTestUtil JdpTestCase JdpJmxRemoteDynamicPortTestCase DynamicLauncher
  *  @run main JdpJmxRemoteDynamicPortTest
  */
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/sun/security/ssl/ServerHandshaker/HelloExtensionsTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,287 @@
+/*
+ * Copyright (c) 2017, 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
+ * @bug 8173783
+ * @summary 6u141 IllegalArgumentException: jdk.tls.namedGroups
+ * run main/othervm HelloExtensionsTest
+ * run main/othervm HelloExtensionsTest -Djdk.tls.namedGroups="bug, bug"
+ * run main/othervm HelloExtensionsTest -Djdk.tls.namedGroups="secp521r1"
+ *
+ */
+import javax.crypto.*;
+import javax.net.ssl.*;
+import javax.net.ssl.SSLEngineResult.*;
+import java.io.*;
+import java.nio.*;
+import java.security.*;
+
+public class HelloExtensionsTest {
+
+    private static boolean debug = false;
+    private static boolean proceed = true;
+    private static boolean EcAvailable = isEcAvailable();
+
+    static String pathToStores = "../../../../javax/net/ssl/etc";
+    private static String keyStoreFile = "keystore";
+    private static String trustStoreFile = "truststore";
+    private static String passwd = "passphrase";
+
+    private static String keyFilename =
+            System.getProperty("test.src", "./") + "/" + pathToStores +
+                "/" + keyStoreFile;
+    private static String trustFilename =
+            System.getProperty("test.src", "./") + "/" + pathToStores +
+                "/" + trustStoreFile;
+
+    private static void checkDone(SSLEngine ssle) throws Exception {
+        if (!ssle.isInboundDone()) {
+            throw new Exception("isInboundDone isn't done");
+        }
+        if (!ssle.isOutboundDone()) {
+            throw new Exception("isOutboundDone isn't done");
+        }
+    }
+
+    private static void runTest(SSLEngine ssle) throws Exception {
+
+         /*
+
+         A client hello message captured via wireshark by selecting
+         a TLSv1.2 Client Hello record and clicking through to the
+         TLSv1.2 Record Layer line and then selecting the hex stream
+         via "copy -> bytes -> hex stream".
+
+         For Record purposes, here's the ClientHello :
+
+         *** ClientHello, TLSv1.2
+         RandomCookie:  GMT: 1469560450 bytes = { 108, 140, 12, 202,
+         2, 213, 10, 236, 143, 223, 58, 162, 228, 155, 239, 3, 98,
+         232, 89, 41, 116, 120, 13, 37, 105, 153, 97, 241 }
+         Session ID:  {}
+         Cipher Suites: [TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256,
+         TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256, TLS_RSA_WITH_AES_128_CBC_SHA256,
+         TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA256,
+         TLS_ECDH_RSA_WITH_AES_128_CBC_SHA256,
+         TLS_DHE_RSA_WITH_AES_128_CBC_SHA256,
+         TLS_DHE_DSS_WITH_AES_128_CBC_SHA256,
+         TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA,
+         TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA,
+         TLS_RSA_WITH_AES_128_CBC_SHA,
+         TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA,
+         TLS_ECDH_RSA_WITH_AES_128_CBC_SHA,
+         TLS_DHE_RSA_WITH_AES_128_CBC_SHA,
+         TLS_DHE_DSS_WITH_AES_128_CBC_SHA,
+         TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256,
+         TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256,
+         TLS_RSA_WITH_AES_128_GCM_SHA256,
+         TLS_ECDH_ECDSA_WITH_AES_128_GCM_SHA256,
+         TLS_ECDH_RSA_WITH_AES_128_GCM_SHA256,
+         TLS_DHE_RSA_WITH_AES_128_GCM_SHA256,
+         TLS_DHE_DSS_WITH_AES_128_GCM_SHA256,
+         TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA,
+         TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA,
+         SSL_RSA_WITH_3DES_EDE_CBC_SHA,
+         TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA,
+         TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA,
+         SSL_DHE_RSA_WITH_3DES_EDE_CBC_SHA,
+         SSL_DHE_DSS_WITH_3DES_EDE_CBC_SHA,
+         TLS_EMPTY_RENEGOTIATION_INFO_SCSV]
+         Compression Methods:  { 0 }
+         Extension elliptic_curves, curve names: {secp256r1,
+         sect163k1, sect163r2, secp192r1, secp224r1, sect233k1, sect233r1,
+         sect283k1, sect283r1, secp384r1, sect409k1, sect409r1, secp521r1,
+         sect571k1, sect571r1, secp160k1, secp160r1, secp160r2, sect163r1,
+         secp192k1, sect193r1, sect193r2, secp224k1, sect239k1, secp256k1}
+         Extension ec_point_formats, formats: [uncompressed]
+         Extension signature_algorithms, signature_algorithms:
+         SHA512withECDSA, SHA512withRSA, SHA384withECDSA, SHA384withRSA,
+         SHA256withECDSA, SHA256withRSA, Unknown (hash:0x3, signature:0x3),
+         Unknown (hash:0x3, signature:0x1), SHA1withECDSA,
+         SHA1withRSA, SHA1withDSA
+         Extension server_name, server_name:
+         [host_name: bugs.openjdk.java.net]
+         */
+
+        String hello = "16030300df010000db03035898b7826c8c0cc" +
+            "a02d50aec8fdf3aa2e49bef0362e8592974780d25699961f" +
+            "100003ac023c027003cc025c02900670040c009c013002fc" +
+            "004c00e00330032c02bc02f009cc02dc031009e00a2c008c" +
+            "012000ac003c00d0016001300ff01000078000a003400320" +
+            "0170001000300130015000600070009000a0018000b000c0" +
+            "019000d000e000f001000110002001200040005001400080" +
+            "016000b00020100000d00180016060306010503050104030" +
+            "401030303010203020102020000001a00180000156275677" +
+            "32e6f70656e6a646b2e6a6176612e6e6574";
+
+        byte[] msg_clihello = hexStringToByteArray(hello);
+        ByteBuffer bf_clihello = ByteBuffer.wrap(msg_clihello);
+
+        SSLSession session = ssle.getSession();
+        int appBufferMax = session.getApplicationBufferSize();
+        int netBufferMax = session.getPacketBufferSize();
+
+        ByteBuffer serverIn = ByteBuffer.allocate(appBufferMax + 50);
+        ByteBuffer serverOut = ByteBuffer.wrap("I'm Server".getBytes());
+        ByteBuffer sTOc = ByteBuffer.allocate(netBufferMax);
+
+        ssle.beginHandshake();
+
+        // unwrap the clientHello message.
+        SSLEngineResult result = ssle.unwrap(bf_clihello, serverIn);
+        System.out.println("server unwrap " + result);
+        runDelegatedTasks(result, ssle);
+
+        if (!proceed) {
+            //expected exception occurred. Don't process anymore
+            return;
+        }
+
+        // one more step, ensure the clientHello message is parsed.
+        SSLEngineResult.HandshakeStatus status = ssle.getHandshakeStatus();
+        if ( status == HandshakeStatus.NEED_UNWRAP) {
+            result = ssle.unwrap(bf_clihello, serverIn);
+            System.out.println("server unwrap " + result);
+            runDelegatedTasks(result, ssle);
+        } else if ( status == HandshakeStatus.NEED_WRAP) {
+            result = ssle.wrap(serverOut, sTOc);
+            System.out.println("server wrap " + result);
+            runDelegatedTasks(result, ssle);
+        } else {
+            throw new Exception("unexpected handshake status " + status);
+        }
+
+        // enough, stop
+    }
+
+    /*
+     * If the result indicates that we have outstanding tasks to do,
+     * go ahead and run them in this thread.
+     */
+    private static void runDelegatedTasks(SSLEngineResult result,
+            SSLEngine engine) throws Exception {
+
+        if (result.getHandshakeStatus() == HandshakeStatus.NEED_TASK) {
+            Runnable runnable;
+            try {
+                while ((runnable = engine.getDelegatedTask()) != null) {
+                    log("\trunning delegated task...");
+                    runnable.run();
+                }
+            } catch (ExceptionInInitializerError e) {
+                String v = System.getProperty("jdk.tls.namedGroups");
+                if (!EcAvailable || v == null) {
+                    // we weren't expecting this if no EC providers
+                    throw new RuntimeException("Unexpected Error :" + e);
+                }
+                if (v != null && v.contains("bug")) {
+                    // OK - we were expecting this Error
+                    log("got expected error for bad jdk.tls.namedGroups");
+                    proceed = false;
+                    return;
+                } else {
+                    System.out.println("Unexpected error. " +
+                        "jdk.tls.namedGroups value: " + v);
+                    throw e;
+                }
+            }
+            HandshakeStatus hsStatus = engine.getHandshakeStatus();
+            if (hsStatus == HandshakeStatus.NEED_TASK) {
+                throw new Exception(
+                    "handshake shouldn't need additional tasks");
+            }
+            log("\tnew HandshakeStatus: " + hsStatus);
+        }
+    }
+
+    private static byte[] hexStringToByteArray(String s) {
+        int len = s.length();
+        byte[] data = new byte[len / 2];
+        for (int i = 0; i < len; i += 2) {
+            data[i / 2] = (byte) ((Character.digit(s.charAt(i), 16) << 4)
+                + Character.digit(s.charAt(i+1), 16));
+        }
+        return data;
+    }
+
+    private static boolean isEcAvailable() {
+        try {
+            Signature.getInstance("SHA1withECDSA");
+            Signature.getInstance("NONEwithECDSA");
+            KeyAgreement.getInstance("ECDH");
+            KeyFactory.getInstance("EC");
+            KeyPairGenerator.getInstance("EC");
+            AlgorithmParameters.getInstance("EC");
+        } catch (Exception e) {
+            log("EC not available. Received: " + e);
+            return false;
+        }
+        return true;
+    }
+
+    public static void main(String args[]) throws Exception {
+        SSLEngine ssle = createSSLEngine(keyFilename, trustFilename);
+        runTest(ssle);
+        System.out.println("Test Passed.");
+    }
+
+    /*
+     * Create an initialized SSLContext to use for this test.
+     */
+    static private SSLEngine createSSLEngine(String keyFile, String trustFile)
+            throws Exception {
+
+        SSLEngine ssle;
+
+        KeyStore ks = KeyStore.getInstance("JKS");
+        KeyStore ts = KeyStore.getInstance("JKS");
+
+        char[] passphrase = "passphrase".toCharArray();
+
+        ks.load(new FileInputStream(keyFile), passphrase);
+        ts.load(new FileInputStream(trustFile), passphrase);
+
+        KeyManagerFactory kmf = KeyManagerFactory.getInstance("SunX509");
+        kmf.init(ks, passphrase);
+
+        TrustManagerFactory tmf = TrustManagerFactory.getInstance("SunX509");
+        tmf.init(ts);
+
+        SSLContext sslCtx = SSLContext.getInstance("TLS");
+
+        sslCtx.init(kmf.getKeyManagers(), tmf.getTrustManagers(), null);
+
+        ssle = sslCtx.createSSLEngine();
+        ssle.setUseClientMode(false);
+
+        return ssle;
+    }
+
+
+    private static void log(String str) {
+        if (debug) {
+            System.out.println(str);
+        }
+    }
+}
--- a/jdk/test/sun/security/tools/jarsigner/TimestampCheck.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/sun/security/tools/jarsigner/TimestampCheck.java	Wed Jul 05 22:52:01 2017 +0200
@@ -456,7 +456,7 @@
                 .shouldMatch("Timestamp signature algorithm: .*key.*weak");
         verify(file, "-J-Djava.security.debug=jar")
                 .shouldHaveExitValue(0)
-                .shouldMatch("SignatureException:.*Disabled");
+                .shouldMatch("SignatureException:.*disabled");
     }
 
     static void checkHalfWeak(String file) throws Throwable {
--- a/jdk/test/sun/text/IntHashtable/Bug4170614Test.java	Mon Feb 13 11:57:56 2017 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,191 +0,0 @@
-/*
- * Copyright (c) 1999, 2016, 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.
- */
-
-/*
-    (this test doesn't have an at-test tag because it's run by a shell
-    script instead of directly by the test harness)
-*/
-
-/*
- *
- *
- * (C) Copyright Taligent, Inc. 1996, 1997 - All Rights Reserved
- * (C) Copyright IBM Corp. 1996 - 1998 - All Rights Reserved
- *
- * Portions copyright (c) 2007 Sun Microsystems, Inc.
- * All Rights Reserved.
- *
- * The original version of this source code and documentation
- * is copyrighted and owned by Taligent, Inc., a wholly-owned
- * subsidiary of IBM. These materials are provided under terms
- * of a License Agreement between Taligent and Sun. This technology
- * is protected by multiple US and International patents.
- *
- * This notice and attribution to Taligent may not be removed.
- * Taligent is a registered trademark of Taligent, Inc.
- *
- * Permission to use, copy, modify, and distribute this software
- * and its documentation for NON-COMMERCIAL purposes and without
- * fee is hereby granted provided that this copyright notice
- * appears in all copies. Please refer to the file "copyright.html"
- * for further important copyright and licensing information.
- *
- * SUN MAKES NO REPRESENTATIONS OR WARRANTIES ABOUT THE SUITABILITY OF
- * THE SOFTWARE, EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED
- * TO THE IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
- * PARTICULAR PURPOSE, OR NON-INFRINGEMENT. SUN SHALL NOT BE LIABLE FOR
- * ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF USING, MODIFYING OR
- * DISTRIBUTING THIS SOFTWARE OR ITS DERIVATIVES.
- *
- */
-package java.text;
-import sun.text.IntHashtable;
-
-
-/**
- * This class tests some internal hashCode() functions.
- * Bug #4170614 complained that we had two iternal classes that
- * break the invariant that if a.equals(b) than a.hashCode() ==
- * b.hashCode().  This is because these classes overrode equals()
- * but not hashCode().  These are both purely internal classes, and
- * the library itself doesn't actually call hashCode(), so this isn't
- * actually causing anyone problems yet.  But if these classes are
- * ever exposed in the API, their hashCode() methods need to work right.
- * PatternEntry will never be exposed in the API, but IntHashtable
- * might be.  This is a shell test to allow us to access classes that
- * are declared package private.
- * @author Richard Gillam
- */
-public class Bug4170614Test {
-    public static void main(String[] args) throws Exception {
-        testIntHashtable();
-        testPatternEntry();
-    }
-
-
-    public static void testIntHashtable() throws Exception {
-        IntHashtable fred = new IntHashtable();
-        fred.put(1, 10);
-        fred.put(2, 20);
-        fred.put(3, 30);
-
-        IntHashtable barney = new IntHashtable();
-        barney.put(1, 10);
-        barney.put(3, 30);
-        barney.put(2, 20);
-
-        IntHashtable homer = new IntHashtable();
-        homer.put(3, 30);
-        homer.put(1, 10);
-        homer.put(7, 900);
-
-        if (fred.equals(barney)) {
-            System.out.println("fred.equals(barney)");
-        }
-        else {
-            System.out.println("!fred.equals(barney)");
-        }
-        System.out.println("fred.hashCode() == " + fred.hashCode());
-        System.out.println("barney.hashCode() == " + barney.hashCode());
-
-        if (!fred.equals(barney)) {
-            throw new Exception("equals() failed on two hashtables that are equal");
-        }
-
-        if (fred.hashCode() != barney.hashCode()) {
-           throw new Exception("hashCode() failed on two hashtables that are equal");
-        }
-
-        System.out.println();
-        if (fred.equals(homer)) {
-            System.out.println("fred.equals(homer)");
-        }
-        else {
-            System.out.println("!fred.equals(homer)");
-        }
-        System.out.println("fred.hashCode() == " + fred.hashCode());
-        System.out.println("homer.hashCode() == " + homer.hashCode());
-
-        if (fred.equals(homer)) {
-            throw new Exception("equals() failed on two hashtables that are not equal");
-        }
-
-        if (fred.hashCode() == homer.hashCode()) {
-            throw new Exception("hashCode() failed on two hashtables that are not equal");
-        }
-
-        System.out.println();
-        System.out.println("testIntHashtable() passed.\n");
-    }
-
-    public static void testPatternEntry() throws Exception {
-        PatternEntry fred = new PatternEntry(1,
-                                             new StringBuffer("hello"),
-                                             new StringBuffer("up"));
-        PatternEntry barney = new PatternEntry(1,
-                                               new StringBuffer("hello"),
-                                               new StringBuffer("down"));
-        // (equals() only considers the "chars" field, so fred and barney are equal)
-        PatternEntry homer = new PatternEntry(1,
-                                              new StringBuffer("goodbye"),
-                                              new StringBuffer("up"));
-
-        if (fred.equals(barney)) {
-            System.out.println("fred.equals(barney)");
-        }
-        else {
-            System.out.println("!fred.equals(barney)");
-        }
-        System.out.println("fred.hashCode() == " + fred.hashCode());
-        System.out.println("barney.hashCode() == " + barney.hashCode());
-
-        if (!fred.equals(barney)) {
-            throw new Exception("equals() failed on two hashtables that are equal");
-        }
-
-        if (fred.hashCode() != barney.hashCode()) {
-           throw new Exception("hashCode() failed on two hashtables that are equal");
-        }
-
-        System.out.println();
-        if (fred.equals(homer)) {
-            System.out.println("fred.equals(homer)");
-        }
-        else {
-            System.out.println("!fred.equals(homer)");
-        }
-        System.out.println("fred.hashCode() == " + fred.hashCode());
-        System.out.println("homer.hashCode() == " + homer.hashCode());
-
-        if (fred.equals(homer)) {
-            throw new Exception("equals() failed on two hashtables that are not equal");
-        }
-
-        if (fred.hashCode() == homer.hashCode()) {
-            throw new Exception("hashCode() failed on two hashtables that are not equal");
-        }
-
-        System.out.println();
-        System.out.println("testPatternEntry() passed.\n");
-    }
-}
--- a/jdk/test/sun/text/IntHashtable/Bug4170614Test.sh	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/sun/text/IntHashtable/Bug4170614Test.sh	Wed Jul 05 22:52:01 2017 +0200
@@ -60,8 +60,8 @@
 TEST_JAVABASE=${TESTCLASSES}/java.base
 mkdir -p ${TEST_JAVABASE}
 ${COMPILEJAVA}/bin/javac ${TESTJAVACOPTS} ${TESTTOOLVMOPTS} \
-    -Xmodule:java.base \
-    -d ${TEST_JAVABASE} Bug4170614Test.java
+    --patch-module java.base=patch-src \
+    -d ${TEST_JAVABASE} patch-src/java/text/Bug4170614Test.java
 
 ${TESTJAVA}/bin/java ${TESTVMOPTS} --patch-module java.base=${TEST_JAVABASE} java.text.Bug4170614Test
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/sun/text/IntHashtable/patch-src/java/text/Bug4170614Test.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,191 @@
+/*
+ * Copyright (c) 1999, 2016, 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.
+ */
+
+/*
+    (this test doesn't have an at-test tag because it's run by a shell
+    script instead of directly by the test harness)
+*/
+
+/*
+ *
+ *
+ * (C) Copyright Taligent, Inc. 1996, 1997 - All Rights Reserved
+ * (C) Copyright IBM Corp. 1996 - 1998 - All Rights Reserved
+ *
+ * Portions copyright (c) 2007 Sun Microsystems, Inc.
+ * All Rights Reserved.
+ *
+ * The original version of this source code and documentation
+ * is copyrighted and owned by Taligent, Inc., a wholly-owned
+ * subsidiary of IBM. These materials are provided under terms
+ * of a License Agreement between Taligent and Sun. This technology
+ * is protected by multiple US and International patents.
+ *
+ * This notice and attribution to Taligent may not be removed.
+ * Taligent is a registered trademark of Taligent, Inc.
+ *
+ * Permission to use, copy, modify, and distribute this software
+ * and its documentation for NON-COMMERCIAL purposes and without
+ * fee is hereby granted provided that this copyright notice
+ * appears in all copies. Please refer to the file "copyright.html"
+ * for further important copyright and licensing information.
+ *
+ * SUN MAKES NO REPRESENTATIONS OR WARRANTIES ABOUT THE SUITABILITY OF
+ * THE SOFTWARE, EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED
+ * TO THE IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
+ * PARTICULAR PURPOSE, OR NON-INFRINGEMENT. SUN SHALL NOT BE LIABLE FOR
+ * ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF USING, MODIFYING OR
+ * DISTRIBUTING THIS SOFTWARE OR ITS DERIVATIVES.
+ *
+ */
+package java.text;
+import sun.text.IntHashtable;
+
+
+/**
+ * This class tests some internal hashCode() functions.
+ * Bug #4170614 complained that we had two iternal classes that
+ * break the invariant that if a.equals(b) than a.hashCode() ==
+ * b.hashCode().  This is because these classes overrode equals()
+ * but not hashCode().  These are both purely internal classes, and
+ * the library itself doesn't actually call hashCode(), so this isn't
+ * actually causing anyone problems yet.  But if these classes are
+ * ever exposed in the API, their hashCode() methods need to work right.
+ * PatternEntry will never be exposed in the API, but IntHashtable
+ * might be.  This is a shell test to allow us to access classes that
+ * are declared package private.
+ * @author Richard Gillam
+ */
+public class Bug4170614Test {
+    public static void main(String[] args) throws Exception {
+        testIntHashtable();
+        testPatternEntry();
+    }
+
+
+    public static void testIntHashtable() throws Exception {
+        IntHashtable fred = new IntHashtable();
+        fred.put(1, 10);
+        fred.put(2, 20);
+        fred.put(3, 30);
+
+        IntHashtable barney = new IntHashtable();
+        barney.put(1, 10);
+        barney.put(3, 30);
+        barney.put(2, 20);
+
+        IntHashtable homer = new IntHashtable();
+        homer.put(3, 30);
+        homer.put(1, 10);
+        homer.put(7, 900);
+
+        if (fred.equals(barney)) {
+            System.out.println("fred.equals(barney)");
+        }
+        else {
+            System.out.println("!fred.equals(barney)");
+        }
+        System.out.println("fred.hashCode() == " + fred.hashCode());
+        System.out.println("barney.hashCode() == " + barney.hashCode());
+
+        if (!fred.equals(barney)) {
+            throw new Exception("equals() failed on two hashtables that are equal");
+        }
+
+        if (fred.hashCode() != barney.hashCode()) {
+           throw new Exception("hashCode() failed on two hashtables that are equal");
+        }
+
+        System.out.println();
+        if (fred.equals(homer)) {
+            System.out.println("fred.equals(homer)");
+        }
+        else {
+            System.out.println("!fred.equals(homer)");
+        }
+        System.out.println("fred.hashCode() == " + fred.hashCode());
+        System.out.println("homer.hashCode() == " + homer.hashCode());
+
+        if (fred.equals(homer)) {
+            throw new Exception("equals() failed on two hashtables that are not equal");
+        }
+
+        if (fred.hashCode() == homer.hashCode()) {
+            throw new Exception("hashCode() failed on two hashtables that are not equal");
+        }
+
+        System.out.println();
+        System.out.println("testIntHashtable() passed.\n");
+    }
+
+    public static void testPatternEntry() throws Exception {
+        PatternEntry fred = new PatternEntry(1,
+                                             new StringBuffer("hello"),
+                                             new StringBuffer("up"));
+        PatternEntry barney = new PatternEntry(1,
+                                               new StringBuffer("hello"),
+                                               new StringBuffer("down"));
+        // (equals() only considers the "chars" field, so fred and barney are equal)
+        PatternEntry homer = new PatternEntry(1,
+                                              new StringBuffer("goodbye"),
+                                              new StringBuffer("up"));
+
+        if (fred.equals(barney)) {
+            System.out.println("fred.equals(barney)");
+        }
+        else {
+            System.out.println("!fred.equals(barney)");
+        }
+        System.out.println("fred.hashCode() == " + fred.hashCode());
+        System.out.println("barney.hashCode() == " + barney.hashCode());
+
+        if (!fred.equals(barney)) {
+            throw new Exception("equals() failed on two hashtables that are equal");
+        }
+
+        if (fred.hashCode() != barney.hashCode()) {
+           throw new Exception("hashCode() failed on two hashtables that are equal");
+        }
+
+        System.out.println();
+        if (fred.equals(homer)) {
+            System.out.println("fred.equals(homer)");
+        }
+        else {
+            System.out.println("!fred.equals(homer)");
+        }
+        System.out.println("fred.hashCode() == " + fred.hashCode());
+        System.out.println("homer.hashCode() == " + homer.hashCode());
+
+        if (fred.equals(homer)) {
+            throw new Exception("equals() failed on two hashtables that are not equal");
+        }
+
+        if (fred.hashCode() == homer.hashCode()) {
+            throw new Exception("hashCode() failed on two hashtables that are not equal");
+        }
+
+        System.out.println();
+        System.out.println("testPatternEntry() passed.\n");
+    }
+}
--- a/jdk/test/tools/jar/mmrjar/Basic.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/tools/jar/mmrjar/Basic.java	Wed Jul 05 22:52:01 2017 +0200
@@ -268,7 +268,7 @@
 
         actual = lines(outbytes);
         expected = Set.of(
-                "hi",
+                "module hi (module-info.class)",
                 "requires mandated java.base",
                 "contains p",
                 "contains p.internal"
@@ -304,7 +304,7 @@
 
         actual = lines(outbytes);
         expected = Set.of(
-                "hi",
+                "module hi (module-info.class)",
                 "requires mandated java.base",
                 "contains p",
                 "contains p.internal",
@@ -331,7 +331,7 @@
         ModuleInfoExtender mie = ModuleInfoExtender.newExtender(
             new ByteArrayInputStream(mdBytes));
 
-        mie.mainClass("foo.main");
+        mie.mainClass("p.Main");
         mie.version(Version.parse("1.0"));
 
         ByteArrayOutputStream baos = new ByteArrayOutputStream();
@@ -345,7 +345,7 @@
 
         // different main-class
         mie = ModuleInfoExtender.newExtender(new ByteArrayInputStream(mdBytes));
-        mie.mainClass("foo.main2");
+        mie.mainClass("p.Main2");
         mie.version(Version.parse("1.0"));
         baos.reset();
         mie.write(baos);
@@ -360,7 +360,7 @@
 
         // different version
         mie = ModuleInfoExtender.newExtender(new ByteArrayInputStream(mdBytes));
-        mie.mainClass("foo.main");
+        mie.mainClass("p.Main");
         mie.version(Version.parse("2.0"));
         baos.reset();
         mie.write(baos);
@@ -395,21 +395,21 @@
         Files.copy(Paths.get("test7-v9", "module-info.class"),
                    Paths.get("test7-v10", "module-info.class"));
 
-        int rc = jar("--create --file mmr.jar --main-class=foo.main -C test7 . --release 9 -C test7-v9 . --release 10 -C test7-v10 .");
-
-System.out.println("-----------------------");
-System.out.println( new String(errbytes.toByteArray()));
-
-
+        int rc = jar("--create --file mmr.jar --main-class=p.Main -C test7 . --release 9 -C test7-v9 . --release 10 -C test7-v10 .");
         Assert.assertEquals(rc, 0);
 
-
-        jar("-tf mmr.jar");
+        jar("-d --file=mmr.jar");
+        System.out.println("-----------------------");
+        System.out.println( new String(outbytes.toByteArray()));
+        Assert.assertEquals(lines(outbytes),
+                            Set.of(
+                           "module m1 (META-INF/versions/9/module-info.class)",
+                           "module m1 (META-INF/versions/10/module-info.class)",
+                           "requires mandated java.base",
+                           "exports p",
+                           "main-class p.Main"));
 
-System.out.println("-----------------------");
-System.out.println( new String(outbytes.toByteArray()));
-
-        Optional<String> exp = Optional.of("foo.main");
+        Optional<String> exp = Optional.of("p.Main");
         try (ZipFile zf = new ZipFile("mmr.jar")) {
             Assert.assertTrue(zf.getEntry("module-info.class") == null);
 
--- a/jdk/test/tools/jar/modularJar/Basic.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/tools/jar/modularJar/Basic.java	Wed Jul 05 22:52:01 2017 +0200
@@ -46,7 +46,7 @@
 
 /*
  * @test
- * @bug 8167328 8171830
+ * @bug 8167328 8171830 8165640
  * @library /lib/testlibrary
  * @modules jdk.compiler
  *          jdk.jartool
@@ -241,11 +241,6 @@
 
         java(mp, FOO.moduleName + "/" + FOO.mainClass)
             .assertSuccess()
-.resultChecker(r -> {
-        System.out.println("===================================");
-        System.out.println(r.output);
-        System.out.println("===================================");
-})
             .resultChecker(r -> assertModuleData(r, FOO));
         try (InputStream fis = Files.newInputStream(modularJar);
              JarInputStream jis = new JarInputStream(fis)) {
@@ -328,7 +323,7 @@
             .resultChecker(r -> assertModuleData(r, FOO));
     }
 
-    @Test
+    @Test(enabled = false)
     public void partialUpdateFooMainClass() throws IOException {
         Path mp = Paths.get("partialUpdateFooMainClass");
         createTestDir(mp);
@@ -484,7 +479,7 @@
             .resultChecker(r -> {
                 // Expect similar output: "bar, requires mandated foo, ...
                 // conceals jdk.test.foo, conceals jdk.test.foo.internal"
-                Pattern p = Pattern.compile("\\s+bar\\s+requires\\s++foo");
+                Pattern p = Pattern.compile("module bar \\(module-info.class\\)\\s+requires\\s++foo");
                 assertTrue(p.matcher(r.output).find(),
                            "Expecting to find \"bar, requires foo,...\"",
                            "in output, but did not: [" + r.output + "]");
@@ -740,6 +735,53 @@
     }
 
     @Test
+    public void servicesCreateWithoutFailureNonRootMRMJAR() throws IOException {
+        // without a root module-info.class
+        Path mp = Paths.get("servicesCreateWithoutFailureNonRootMRMJAR");
+        createTestDir(mp);
+        Path modClasses = MODULE_CLASSES.resolve("baz");
+        Path mrjarDir = MRJAR_DIR.resolve("baz");
+        Path modularJar = mp.resolve("baz.jar");
+
+        jar("--create",
+            "--file=" + modularJar.toString(),
+            "--main-class=" + "jdk.test.baz.Baz",
+            "-m", mrjarDir.resolve("META-INF/MANIFEST.MF").toRealPath().toString(),
+            "-C", mrjarDir.toString(), "META-INF/versions/9/module-info.class",
+            "-C", modClasses.toString(), "jdk/test/baz/BazService.class",
+            "-C", modClasses.toString(), "jdk/test/baz/Baz.class",
+            "-C", modClasses.toString(), "jdk/test/baz/internal/BazServiceImpl.class")
+            .assertSuccess();
+
+
+        for (String option : new String[]  {"--print-module-descriptor", "-d" }) {
+
+            jar(option,
+                "--file=" + modularJar.toString())
+                .assertSuccess()
+                .resultChecker(r ->
+                    assertTrue(r.output.contains("main-class jdk.test.baz.Baz"),
+                              "Expected to find ", "main-class jdk.test.baz.Baz",
+                               " in [", r.output, "]"));
+
+            jarWithStdin(modularJar.toFile(),  option)
+                .assertSuccess()
+                .resultChecker(r ->
+                    assertTrue(r.output.contains("main-class jdk.test.baz.Baz"),
+                              "Expected to find ", "main-class jdk.test.baz.Baz",
+                               " in [", r.output, "]"));
+
+        }
+        // run module maain class
+        java(mp, "baz/jdk.test.baz.Baz")
+            .assertSuccess()
+            .resultChecker(r ->
+               assertTrue(r.output.contains("mainClass:jdk.test.baz.Baz"),
+                          "Expected to find ", "mainClass:jdk.test.baz.Baz",
+                          " in [", r.output, "]"));
+    }
+
+    @Test
     public void exportCreateWithMissingPkg() throws IOException {
 
         Path foobar = TEST_SRC.resolve("src").resolve("foobar");
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/tools/jar/modularJar/src/baz/jdk/test/baz/Baz.java	Wed Jul 05 22:52:01 2017 +0200
@@ -0,0 +1,34 @@
+/*
+ * Copyright (c) 2017, 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.
+ */
+
+package jdk.test.baz;
+
+import java.lang.module.ModuleDescriptor;
+
+public class Baz {
+    public static void main(String[] args) {
+        ModuleDescriptor md = Baz.class.getModule().getDescriptor();
+        System.out.println("nameAndVersion:" + md.toNameAndVersion());
+        md.mainClass().ifPresent(mc -> System.out.println("mainClass:" + mc));
+    }
+}
--- a/jdk/test/tools/jlink/JLinkNegativeTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/tools/jlink/JLinkNegativeTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -250,7 +250,7 @@
         String moduleName = "hacked4";
         Path jmod = helper.generateDefaultJModule(moduleName).assertSuccess();
         JImageGenerator.addFiles(jmod,
-                new InMemoryFile("/native", new byte[0]),
+                new InMemoryFile("/lib", new byte[0]),
                 new InMemoryFile("/conf", new byte[0]),
                 new InMemoryFile("/bin", new byte[0]));
         try {
@@ -274,7 +274,7 @@
                 helper.getJmodSrcDir(), helper.getJmodClassesDir(), moduleName2, classNames);
 
         try (OutputStream out = Files.newOutputStream(module2.resolve("module-info.class"))) {
-            ModuleInfoWriter.write(ModuleDescriptor.module(moduleName1)
+            ModuleInfoWriter.write(ModuleDescriptor.newModule(moduleName1)
                     .requires("java.base").build(), out);
         }
 
@@ -332,7 +332,7 @@
                 helper.getJarSrcDir(), helper.getJarClassesDir(), moduleName2, classNames);
 
         try (OutputStream out = Files.newOutputStream(module2.resolve("module-info.class"))) {
-            ModuleInfoWriter.write(ModuleDescriptor.module(moduleName1)
+            ModuleInfoWriter.write(ModuleDescriptor.newModule(moduleName1)
                     .requires("java.base").build(), out);
         }
 
--- a/jdk/test/tools/jlink/plugins/ExcludeVMPluginTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/tools/jlink/plugins/ExcludeVMPluginTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -155,10 +155,10 @@
             String[] winput = new String[input.length];
             String[] woutput = new String[expectedOutput.length];
             for (int i = 0; i < input.length; i++) {
-                winput[i] = "/java.base/native" + arch + input[i];
+                winput[i] = "/java.base/lib" + arch + input[i];
             }
             for (int i = 0; i < expectedOutput.length; i++) {
-                woutput[i] = "/java.base/native" + arch + expectedOutput[i];
+                woutput[i] = "/java.base/lib" + arch + expectedOutput[i];
             }
             doCheckVM(vm, winput, jvmcfg, woutput, expectdJvmCfg);
         }
@@ -169,7 +169,7 @@
         byte[] jvmcfgContent = jvmcfg.getBytes();
         ResourcePoolManager poolMgr = new ResourcePoolManager();
         poolMgr.add(
-            ResourcePoolEntry.create("/java.base/native/jvm.cfg",
+            ResourcePoolEntry.create("/java.base/lib/jvm.cfg",
                 ResourcePoolEntry.Type.NATIVE_LIB, jvmcfgContent));
 
         // java.base/module-info.class is used by exclude vm plugin
@@ -192,7 +192,7 @@
         p.configure(config);
         ResourcePool out = p.transform(poolMgr.resourcePool(), outMgr.resourcePoolBuilder());
 
-        String newContent = new String(out.findEntry("/java.base/native/jvm.cfg").get().contentBytes());
+        String newContent = new String(out.findEntry("/java.base/lib/jvm.cfg").get().contentBytes());
 
         if (!expectdJvmCfg.equals(newContent)) {
             throw new Exception("Got content " + newContent + " expected " + expectdJvmCfg);
@@ -209,7 +209,7 @@
         }
 
         out.entries().forEach(md -> {
-            if (md.path().equals("/java.base/native/jvm.cfg") ||
+            if (md.path().equals("/java.base/lib/jvm.cfg") ||
                 md.path().equals("/java.base/module-info.class")) {
                 return;
             }
--- a/jdk/test/tools/jlink/plugins/SystemModuleDescriptors/UserModuleTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/tools/jlink/plugins/SystemModuleDescriptors/UserModuleTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -45,7 +45,7 @@
 
 /**
  * @test
- * @bug 8142968 8173381
+ * @bug 8142968 8173381 8174740
  * @library /lib/testlibrary
  * @modules jdk.compiler jdk.jlink
  * @build UserModuleTest CompilerUtils jdk.testlibrary.FileUtils jdk.testlibrary.ProcessTools
--- a/jdk/test/tools/jlink/plugins/SystemModuleDescriptors/src/m1/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/tools/jlink/plugins/SystemModuleDescriptors/src/m1/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2017, 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
@@ -21,5 +21,9 @@
  * questions.
  */
 
+/*
+ * m1 has an exported package and also internal package
+ */
 module m1 {
+    exports p1;
 }
--- a/jdk/test/tools/jmod/JmodTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/tools/jmod/JmodTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -66,7 +66,7 @@
 
     static final String CLASSES_PREFIX = "classes/";
     static final String CMDS_PREFIX = "bin/";
-    static final String LIBS_PREFIX = "native/";
+    static final String LIBS_PREFIX = "lib/";
     static final String CONFIGS_PREFIX = "conf/";
 
     @BeforeTest
--- a/jdk/test/tools/jmod/hashes/HashesTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/tools/jmod/hashes/HashesTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -312,9 +312,7 @@
         assertTrue(ht.hashes("m2") == null);
 
         // should not override any JDK packaged modules
-        ModuleFinder finder = new ModulePath(Runtime.version(),
-                                             true,
-                                             mpath);
+        ModuleFinder finder = ModulePath.of(Runtime.version(), true, mpath);
         assertTrue(ht.hashes(finder,"jdk.compiler") == null);
         assertTrue(ht.hashes(finder,"jdk.attach") == null);
     }
@@ -325,9 +323,7 @@
     }
 
     private ModuleHashes hashes(String name) {
-        ModuleFinder finder = new ModulePath(Runtime.version(),
-                                             true,
-                                             lib);
+        ModuleFinder finder = ModulePath.of(Runtime.version(), true, lib);
         return hashes(finder, name);
     }
 
--- a/jdk/test/tools/launcher/ArgsEnvVar.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/tools/launcher/ArgsEnvVar.java	Wed Jul 05 22:52:01 2017 +0200
@@ -40,7 +40,7 @@
     private static File testJar = null;
     private static Map<String, String> env = new HashMap<>();
 
-    private static String JAVA_OPTIONS = "JAVA_OPTIONS";
+    private static String JDK_JAVA_OPTIONS = "JDK_JAVA_OPTIONS";
 
     static void init() throws IOException {
         if  (testJar != null) {
@@ -105,7 +105,7 @@
         File argFile2 = createArgFile("argFile2", List.of("-Darg.file2=TWO"));
         File argFile3 = createArgFile("argFile3", List.of("-Darg.file3=THREE"));
 
-        env.put(JAVA_OPTIONS, "@argFile1\n-Xint\r-cp @@escaped\t@argFile2");
+        env.put(JDK_JAVA_OPTIONS, "@argFile1\n-Xint\r-cp @@escaped\t@argFile2");
 
         TestResult tr = doExec(env, javaCmd, "@argFile3", "-cp", "test.jar", "Foo", "uarg1", "@uarg2");
 
@@ -133,13 +133,13 @@
     }
 
     private TestResult testInEnv(List<String> options) {
-        env.put(JAVA_OPTIONS, String.join(" ", options));
+        env.put(JDK_JAVA_OPTIONS, String.join(" ", options));
         return doExec(env, javaCmd, "-jar", "test.jar");
     }
 
     private TestResult testInEnvAsArgFile(List<String> options) throws IOException {
         File argFile = createArgFile("argFile", options);
-        env.put(JAVA_OPTIONS, "@argFile");
+        env.put(JDK_JAVA_OPTIONS, "@argFile");
         TestResult tr = doExec(env, javaCmd, "-jar", "test.jar");
         argFile.delete();
         return tr;
@@ -187,7 +187,7 @@
         File argFile1 = createArgFile("arg File 1", List.of("-Xint"));
         File argFile2 = createArgFile("arg File 2", List.of("-Dprop='value with spaces'"));
         File argFile3 = createArgFile("arg File 3", List.of("-Xmx32m"));
-        env.put(JAVA_OPTIONS, "'@arg File 1' @\"arg File 2\" @'arg File'\" 3\"");
+        env.put(JDK_JAVA_OPTIONS, "'@arg File 1' @\"arg File 2\" @'arg File'\" 3\"");
 
         TestResult tr = doExec(env, javaCmd, "-jar", "test.jar");
         List<String> options = new ArrayList<>();
@@ -204,7 +204,7 @@
 
     @Test
     public void openQuoteShouldFail() {
-        env.put(JAVA_OPTIONS, "-Dprop='value missing close quote");
+        env.put(JDK_JAVA_OPTIONS, "-Dprop='value missing close quote");
         TestResult tr = doExec(env, javaCmd, "-version");
         tr.checkNegative();
         if (!tr.testStatus) {
@@ -215,11 +215,11 @@
 
     @Test
     public void noWildcard() {
-        env.put(JAVA_OPTIONS, "-cp *");
+        env.put(JDK_JAVA_OPTIONS, "-cp *");
         TestResult tr = doExec(env, javaCmd, "-jar", "test.jar");
         verifyOptions(List.of("-cp", "*", "-jar", "test.jar"), tr);
 
-        env.put(JAVA_OPTIONS, "-p ?");
+        env.put(JDK_JAVA_OPTIONS, "-p ?");
         tr = doExec(env, javaCmd, "-jar", "test.jar", "one", "two");
         verifyOptions(List.of("-p", "?", "-jar", "test.jar", "one", "two"), tr);
     }
--- a/jdk/test/tools/launcher/I18NArgTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/tools/launcher/I18NArgTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -95,21 +95,19 @@
             throw new RuntimeException("test fails");
         }
 
-        // Test via JAVA_OPTIONS
-/*
+        // Test via JDK_JAVA_OPTIONS
         Map<String, String> env = new HashMap<>();
         String cmd = "-Dtest.src=" + TEST_SOURCES_DIR.getAbsolutePath() +
                 " -Dtest.classes=" + TEST_CLASSES_DIR.getAbsolutePath() +
                 " -cp " + TEST_CLASSES_DIR.getAbsolutePath() +
                 " I18NArgTest " + unicodeStr + " " + hexValue;
-        env.put("JAVA_OPTIONS", cmd);
+        env.put("JDK_JAVA_OPTIONS", cmd);
         tr = doExec(env, javaCmd);
         System.out.println(tr.testOutput);
         if (!tr.isOK()) {
             System.err.println(tr);
             throw new RuntimeException("test fails");
         }
-*/
     }
 
     static void testCharacters(String... args) {
--- a/jdk/test/tools/launcher/ToolsOpts.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/tools/launcher/ToolsOpts.java	Wed Jul 05 22:52:01 2017 +0200
@@ -87,11 +87,16 @@
         contents.add("       }\n");
         contents.add("    }\n");
         contents.add("}\n");
-        createFile(new File(mainJava), contents);
+        String mainJavaPath = "patch-src/com/sun/tools/javac/" + mainJava;
+        File mainJavaFile = new File(mainJavaPath.replace('/', File.separatorChar));
+        mainJavaFile.getParentFile().mkdirs();
+        createFile(mainJavaFile, contents);
 
         // compile Main.java into directory to override classes in jdk.compiler
         new File("jdk.compiler").mkdir();
-        compile("-Xmodule:jdk.compiler", "-d", "jdk.compiler", mainJava);
+        compile("--patch-module", "jdk.compiler=patch-src",
+                "-d", "jdk.compiler",
+                mainJavaFile.toString());
     }
 
     static void pass(String msg) {
--- a/jdk/test/tools/launcher/modules/patch/basic/PatchTest.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/tools/launcher/modules/patch/basic/PatchTest.java	Wed Jul 05 22:52:01 2017 +0200
@@ -105,22 +105,24 @@
                                                 MODS_DIR.resolve("test"));
         assertTrue(compiled, "classes did not compile");
 
-        // javac -Xmodule:$MODULE -d patches1/$MODULE patches1/$MODULE/**
+        // javac --patch-module $MODULE=patches1/$MODULE -d patches1/$MODULE patches1/$MODULE/**
         // jar cf patches/$MODULE-1.jar -C patches1/$MODULE .
         for (Path src : Files.newDirectoryStream(SRC1_DIR)) {
             Path output = PATCHES1_DIR.resolve(src.getFileName());
             String mn = src.getFileName().toString();
-            compiled  = CompilerUtils.compile(src, output, "-Xmodule:" + mn);
+            compiled  = CompilerUtils.compile(src, output,
+                                              "--patch-module", mn + "=" + src.toString());
             assertTrue(compiled, "classes did not compile");
             JarUtils.createJarFile(PATCHES_DIR.resolve(mn + "-1.jar"), output);
         }
 
-        // javac -Xmodule:$MODULE -d patches2/$MODULE patches2/$MODULE/**
+        // javac --patch-module $MODULE=patches2/$MODULE -d patches2/$MODULE patches2/$MODULE/**
         // jar cf patches/$MODULE-2.jar -C patches2/$MODULE .
         for (Path src : Files.newDirectoryStream(SRC2_DIR)) {
             Path output = PATCHES2_DIR.resolve(src.getFileName());
             String mn = src.getFileName().toString();
-            compiled  = CompilerUtils.compile(src, output, "-Xmodule:" + mn);
+            compiled  = CompilerUtils.compile(src, output,
+                                              "--patch-module", mn + "=" + src.toString());
             assertTrue(compiled, "classes did not compile");
             JarUtils.createJarFile(PATCHES_DIR.resolve(mn + "-2.jar"), output);
         }
--- a/jdk/test/tools/launcher/modules/patch/basic/PatchTestWarningError.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/tools/launcher/modules/patch/basic/PatchTestWarningError.java	Wed Jul 05 22:52:01 2017 +0200
@@ -93,20 +93,22 @@
                                                 MODS_DIR.resolve("test"));
         assertTrue(compiled, "classes did not compile");
 
-        // javac -Xmodule:$MODULE -d patches1/$MODULE patches1/$MODULE/**
+        // javac --patch-module $MODULE=patches1/$MODULE -d patches1/$MODULE patches1/$MODULE/**
         Path src = SRC1_DIR.resolve("java.base");
         Path output = PATCHES1_DIR.resolve(src.getFileName());
         Files.createDirectories(output);
         String mn = src.getFileName().toString();
-        compiled  = CompilerUtils.compile(src, output, "-Xmodule:" + mn);
+        compiled  = CompilerUtils.compile(src, output,
+                                          "--patch-module", mn + "=" + src.toString());
         assertTrue(compiled, "classes did not compile");
 
-        // javac -Xmodule:$MODULE -d patches2/$MODULE patches2/$MODULE/**
+        // javac --patch-module $MODULE=patches2/$MODULE -d patches2/$MODULE patches2/$MODULE/**
         src = SRC2_DIR.resolve("java.base");
         output = PATCHES2_DIR.resolve(src.getFileName());
         Files.createDirectories(output);
         mn = src.getFileName().toString();
-        compiled  = CompilerUtils.compile(src, output, "-Xmodule:" + mn);
+        compiled  = CompilerUtils.compile(src, output,
+                                          "--patch-module", mn + "=" + src.toString());
         assertTrue(compiled, "classes did not compile");
 
     }
--- a/jdk/test/tools/launcher/modules/patch/systemmodules/PatchSystemModules.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/tools/launcher/modules/patch/systemmodules/PatchSystemModules.java	Wed Jul 05 22:52:01 2017 +0200
@@ -73,9 +73,10 @@
         }
 
         // compile patched source
+        String patchDir = PATCH_SRC_DIR.resolve(JAVA_BASE).toString();
         assertTrue(CompilerUtils.compile(PATCH_SRC_DIR.resolve(JAVA_BASE),
                                          PATCH_DIR.resolve(JAVA_BASE),
-                                         "-Xmodule:java.base"));
+                                         "--patch-module", "java.base=" + patchDir));
         assertTrue(CompilerUtils.compile(PATCH_SRC_DIR.resolve("m2"),
                                          PATCH_DIR.resolve("m2")));
 
--- a/jdk/test/tools/launcher/modules/patch/systemmodules/src1/java.base/jdk/internal/modules/SystemModules.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/jdk/test/tools/launcher/modules/patch/systemmodules/src1/java.base/jdk/internal/modules/SystemModules.java	Wed Jul 05 22:52:01 2017 +0200
@@ -30,6 +30,8 @@
 public final class SystemModules {
     public static final String[] MODULE_NAMES = new String[0];
 
+    public static int PACKAGES_IN_BOOT_LAYER = 1024;
+
     public static boolean hasSplitPackages() {
         return true;
     }
--- a/make/Init.gmk	Mon Feb 13 11:57:56 2017 +0100
+++ b/make/Init.gmk	Wed Jul 05 22:52:01 2017 +0200
@@ -66,7 +66,7 @@
   ifeq ($(CALLED_SPEC_TARGETS), )
     ONLY_GLOBAL_TARGETS := true
   endif
-  ifneq ($(findstring qp, $(MAKEFLAGS)),)
+  ifeq ($(findstring p, $(MAKEFLAGS))$(findstring q, $(MAKEFLAGS)), pq)
     ONLY_GLOBAL_TARGETS := true
   endif
 
--- a/make/Main.gmk	Mon Feb 13 11:57:56 2017 +0100
+++ b/make/Main.gmk	Wed Jul 05 22:52:01 2017 +0200
@@ -654,8 +654,7 @@
   # When creating a BUILDJDK, we don't need to add hashes to java.base, thus
   # we don't need to depend on all other jmods
   ifneq ($(CREATING_BUILDJDK), true)
-    java.base-jmod: jrtfs-jar $(filter-out java.base-jmod \
-        $(addsuffix -jmod, $(call FindAllUpgradeableModules)), $(JMOD_TARGETS))
+    java.base-jmod: jrtfs-jar $(filter-out java.base-jmod, $(JMOD_TARGETS))
   endif
 
   # Building java.base-jmod requires all of hotspot to be built.
--- a/make/common/Modules.gmk	Mon Feb 13 11:57:56 2017 +0100
+++ b/make/common/Modules.gmk	Wed Jul 05 22:52:01 2017 +0200
@@ -107,7 +107,6 @@
     jdk.charsets \
     jdk.crypto.ec \
     jdk.crypto.cryptoki \
-    jdk.desktop \
     jdk.dynalink \
     jdk.jsobject \
     jdk.localedata \
@@ -115,6 +114,7 @@
     jdk.scripting.nashorn \
     jdk.security.auth \
     jdk.security.jgss \
+    jdk.vm.compiler \
     jdk.xml.dom \
     jdk.zipfs \
     #
--- a/nashorn/.hgtags	Mon Feb 13 11:57:56 2017 +0100
+++ b/nashorn/.hgtags	Wed Jul 05 22:52:01 2017 +0200
@@ -389,3 +389,4 @@
 19aaaf2d02b7d6986538cd9a8c46901ecb50eebf jdk-9+153
 a84b49cfee63716975535abae2865ffef4dd6474 jdk-9+154
 f9bb37a817b3cd3b758a60f3c68258a6554eb382 jdk-9+155
+d577398d31111be4bdaa08008247cf4242eaea94 jdk-9+156
--- a/nashorn/src/jdk.dynalink/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/nashorn/src/jdk.dynalink/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -216,6 +216,8 @@
  * language runtime B gets passed to code from language runtime A, the linker
  * from B will get a chance to link the call site in A when it encounters the
  * object from B.
+ *
+ * @since 9
  */
 module jdk.dynalink {
     requires java.logging;
--- a/nashorn/src/jdk.scripting.nashorn.shell/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/nashorn/src/jdk.scripting.nashorn.shell/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -25,6 +25,8 @@
 
 /**
  * Nashorn shell module
+ *
+ * @since 9
  */
 module jdk.scripting.nashorn.shell {
     requires java.desktop;
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/Context.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/Context.java	Wed Jul 05 22:52:01 2017 +0200
@@ -1372,7 +1372,7 @@
         };
 
         final Configuration cf = parent.configuration()
-                .resolveRequires(finder, ModuleFinder.of(), Set.of(mn));
+                .resolve(finder, ModuleFinder.of(), Set.of(mn));
 
         final PrivilegedAction<Layer> pa = () -> parent.defineModules(cf, name -> loader);
         final Layer layer = AccessController.doPrivileged(pa, GET_LOADER_ACC_CTXT);
@@ -1798,7 +1798,7 @@
 
         final Layer boot = Layer.boot();
         final Configuration conf = boot.configuration().
-            resolveRequires(mf, ModuleFinder.of(), rootMods);
+            resolve(mf, ModuleFinder.of(), rootMods);
         final String firstMod = rootMods.iterator().next();
         return boot.defineModulesWithOneLoader(conf, cl).findLoader(firstMod);
     }
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/ScriptLoader.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/ScriptLoader.java	Wed Jul 05 22:52:01 2017 +0200
@@ -26,9 +26,11 @@
 package jdk.nashorn.internal.runtime;
 
 import java.lang.module.ModuleDescriptor;
+import java.lang.module.ModuleDescriptor.Modifier;
 import java.lang.reflect.Module;
 import java.security.CodeSource;
 import java.util.Objects;
+import java.util.Set;
 
 /**
  * Responsible for loading script generated classes.
@@ -69,12 +71,11 @@
     private Module createModule(final String moduleName) {
         final Module structMod = context.getStructLoader().getModule();
         final ModuleDescriptor.Builder builder =
-            ModuleDescriptor.module(moduleName)
-                    .requires("java.base")
+            ModuleDescriptor.newModule(moduleName, Set.of(Modifier.SYNTHETIC))
                     .requires("java.logging")
                     .requires(NASHORN_MODULE.getName())
                     .requires(structMod.getName())
-                    .contains(SCRIPTS_PKG);
+                    .packages(Set.of(SCRIPTS_PKG));
 
         if (Context.javaSqlFound) {
             builder.requires("java.sql");
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/StructureLoader.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/StructureLoader.java	Wed Jul 05 22:52:01 2017 +0200
@@ -31,8 +31,10 @@
 import static jdk.nashorn.internal.codegen.CompilerConstants.JS_OBJECT_SINGLE_FIELD_PREFIX;
 
 import java.lang.module.ModuleDescriptor;
+import java.lang.module.ModuleDescriptor.Modifier;
 import java.lang.reflect.Module;
 import java.security.ProtectionDomain;
+import java.util.Set;
 import jdk.nashorn.internal.codegen.ObjectClassGenerator;
 
 /**
@@ -62,12 +64,11 @@
     }
 
     private Module createModule(final String moduleName) {
-        final ModuleDescriptor descriptor
-                = ModuleDescriptor.module(moduleName)
-                    .requires("java.base")
-                    .requires(NASHORN_MODULE.getName())
-                    .contains(SCRIPTS_PKG)
-                    .build();
+        final ModuleDescriptor descriptor =
+            ModuleDescriptor.newModule(moduleName, Set.of(Modifier.SYNTHETIC))
+                            .requires(NASHORN_MODULE.getName())
+                            .packages(Set.of(SCRIPTS_PKG))
+                            .build();
 
         final Module mod = Context.createModuleTrusted(descriptor, this);
         loadModuleManipulator();
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/module-info.java	Mon Feb 13 11:57:56 2017 +0100
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/module-info.java	Wed Jul 05 22:52:01 2017 +0200
@@ -89,6 +89,8 @@
 <h2>Other non-standard built-in objects</h2>
 In addition to {@code Java}, Nashorn also exposes some other non-standard built-in objects:
 {@code JSAdapter}, {@code JavaImporter}, {@code Packages}
+
+@since 9
  */
 module jdk.scripting.nashorn {
     requires java.logging;