Merge
authorduke
Wed, 05 Jul 2017 20:42:36 +0200
changeset 31759 709a4f0dbb56
parent 31758 ca2d747bbf94 (current diff)
parent 31748 49f3bd7b27a4 (diff)
child 31760 7c577fda1855
Merge
jdk/src/java.base/share/classes/jdk/internal/jimage/ImageFile.java
jdk/src/java.base/share/classes/jdk/internal/jimage/ImageModules.java
jdk/src/java.base/share/classes/jdk/internal/jimage/PReader.java
jdk/src/java.base/share/classes/jdk/internal/jimage/PackageModuleMap.java
jdk/src/java.base/share/classes/jdk/internal/jimage/Resource.java
jdk/src/java.base/share/classes/jdk/internal/jimage/concurrent/ConcurrentPReader.java
jdk/src/java.base/share/classes/sun/text/normalizer/ICUData.java
jdk/src/java.base/share/classes/sun/text/normalizer/IntTrie.java
jdk/src/java.base/share/classes/sun/text/normalizer/NormalizerDataReader.java
jdk/src/java.base/share/classes/sun/text/normalizer/RangeValueIterator.java
jdk/src/java.base/share/classes/sun/text/normalizer/RuleCharacterIterator.java
jdk/src/java.base/share/classes/sun/text/normalizer/SymbolTable.java
jdk/src/java.base/share/classes/sun/text/normalizer/TrieIterator.java
jdk/src/java.base/share/classes/sun/text/normalizer/UCharacterPropertyReader.java
jdk/src/java.base/share/classes/sun/text/normalizer/UnicodeMatcher.java
jdk/src/java.base/share/classes/sun/text/normalizer/UnicodeSetIterator.java
jdk/src/java.base/share/classes/sun/text/resources/unorm.icu
jdk/src/java.base/unix/native/libjava/ConcurrentPReader_md.c
jdk/src/java.base/windows/native/libjava/ConcurrentPReader_md.c
jdk/src/java.desktop/share/classes/sun/net/www/content/audio/aiff.java
jdk/src/java.desktop/share/classes/sun/net/www/content/audio/basic.java
jdk/src/java.desktop/share/classes/sun/net/www/content/audio/wav.java
jdk/src/java.desktop/share/classes/sun/net/www/content/audio/x_aiff.java
jdk/src/java.desktop/share/classes/sun/net/www/content/audio/x_wav.java
jdk/src/java.desktop/share/classes/sun/net/www/content/image/gif.java
jdk/src/java.desktop/share/classes/sun/net/www/content/image/jpeg.java
jdk/src/java.desktop/share/classes/sun/net/www/content/image/png.java
jdk/src/java.desktop/share/classes/sun/net/www/content/image/x_xbitmap.java
jdk/src/java.desktop/share/classes/sun/net/www/content/image/x_xpixmap.java
--- a/.hgtags-top-repo	Thu Jul 16 19:31:01 2015 -0700
+++ b/.hgtags-top-repo	Wed Jul 05 20:42:36 2017 +0200
@@ -315,3 +315,4 @@
 eed77fcd77711fcdba05f18fc22f37d86efb243c jdk9-b70
 c706ef5ea5da00078dc5e4334660315f7d99c15b jdk9-b71
 8582c35016fb6211b373810b6b172feccf9c483b jdk9-b72
+4c2cbaae528bce970dabbb5676005d379357f4b6 jdk9-b73
--- a/corba/.hgtags	Thu Jul 16 19:31:01 2015 -0700
+++ b/corba/.hgtags	Wed Jul 05 20:42:36 2017 +0200
@@ -315,3 +315,4 @@
 e7cf01990ed366bd493080663259281e91ce223b jdk9-b70
 cd39ed501fb0504554a7f58ac6cf3dd2b64afec0 jdk9-b71
 f9f3706bd24c42c07cb260fe05730a749b8e52f4 jdk9-b72
+29096b78d93b01a2f8882509cd40755e3d6b8cd9 jdk9-b73
--- a/corba/src/java.corba/share/classes/com/sun/corba/se/impl/io/IIOPInputStream.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/corba/src/java.corba/share/classes/com/sun/corba/se/impl/io/IIOPInputStream.java	Wed Jul 05 20:42:36 2017 +0200
@@ -2430,8 +2430,8 @@
     private void throwAwayData(ValueMember[] fields,
                                com.sun.org.omg.SendingContext.CodeBase sender)
         throws InvalidClassException, StreamCorruptedException,
-               ClassNotFoundException, IOException
-    {
+               ClassNotFoundException, IOException {
+
         for (int i = 0; i < fields.length; ++i) {
 
             try {
@@ -2566,8 +2566,7 @@
 
     }
 
-    private static void setObjectField(Object o, Class c, String fieldName, Object v)
-    {
+    private static void setObjectField(Object o, Class c, String fieldName, Object v) {
         try {
             Field fld = c.getDeclaredField( fieldName ) ;
             Class fieldCl = fld.getType();
@@ -2577,9 +2576,15 @@
             long key = bridge.objectFieldOffset( fld ) ;
             bridge.putObject( o, key, v ) ;
         } catch (Exception e) {
-            throw utilWrapper.errorSetObjectField( e, fieldName,
-                o.toString(),
-                v.toString() ) ;
+            if (o != null) {
+                throw utilWrapper.errorSetObjectField( e, fieldName,
+                    o.toString(),
+                    v.toString() ) ;
+            } else {
+                throw utilWrapper.errorSetObjectField( e, fieldName,
+                    "null " + c.getName() + " object",
+                    v.toString() ) ;
+            }
         }
     }
 
@@ -2587,12 +2592,22 @@
     {
         try {
             Field fld = c.getDeclaredField( fieldName ) ;
-            long key = bridge.objectFieldOffset( fld ) ;
-            bridge.putBoolean( o, key, v ) ;
+            if ((fld != null) && (fld.getType() == Boolean.TYPE)) {
+                long key = bridge.objectFieldOffset( fld ) ;
+                bridge.putBoolean( o, key, v ) ;
+            } else {
+                throw new InvalidObjectException("Field Type mismatch");
+            }
         } catch (Exception e) {
+            if (o != null) {
             throw utilWrapper.errorSetBooleanField( e, fieldName,
                 o.toString(),
                 new Boolean(v) ) ;
+            } else {
+                throw utilWrapper.errorSetBooleanField( e, fieldName,
+                    "null " + c.getName() + " object",
+                    new Boolean(v) ) ;
+            }
         }
     }
 
@@ -2600,12 +2615,22 @@
     {
         try {
             Field fld = c.getDeclaredField( fieldName ) ;
-            long key = bridge.objectFieldOffset( fld ) ;
-            bridge.putByte( o, key, v ) ;
+            if ((fld != null) && (fld.getType() == Byte.TYPE)) {
+                long key = bridge.objectFieldOffset( fld ) ;
+                bridge.putByte( o, key, v ) ;
+            } else {
+                throw new InvalidObjectException("Field Type mismatch");
+            }
         } catch (Exception e) {
-            throw utilWrapper.errorSetByteField( e, fieldName,
-                o.toString(),
-                new Byte(v) ) ;
+            if (o != null) {
+                throw utilWrapper.errorSetByteField( e, fieldName,
+                    o.toString(),
+                    new Byte(v) ) ;
+            } else {
+                throw utilWrapper.errorSetByteField( e, fieldName,
+                    "null " + c.getName() + " object",
+                    new Byte(v) ) ;
+            }
         }
     }
 
@@ -2613,12 +2638,22 @@
     {
         try {
             Field fld = c.getDeclaredField( fieldName ) ;
-            long key = bridge.objectFieldOffset( fld ) ;
-            bridge.putChar( o, key, v ) ;
+            if ((fld != null) && (fld.getType() == Character.TYPE)) {
+                long key = bridge.objectFieldOffset( fld ) ;
+                bridge.putChar( o, key, v ) ;
+            } else {
+                throw new InvalidObjectException("Field Type mismatch");
+            }
         } catch (Exception e) {
-            throw utilWrapper.errorSetCharField( e, fieldName,
-                o.toString(),
-                new Character(v) ) ;
+            if (o != null) {
+                throw utilWrapper.errorSetCharField( e, fieldName,
+                    o.toString(),
+                    new Character(v) ) ;
+            } else {
+                throw utilWrapper.errorSetCharField( e, fieldName,
+                    "null " + c.getName() + " object",
+                    new Character(v) ) ;
+            }
         }
     }
 
@@ -2626,12 +2661,22 @@
     {
         try {
             Field fld = c.getDeclaredField( fieldName ) ;
-            long key = bridge.objectFieldOffset( fld ) ;
-            bridge.putShort( o, key, v ) ;
+            if ((fld != null) && (fld.getType() == Short.TYPE)) {
+                long key = bridge.objectFieldOffset( fld ) ;
+                bridge.putShort( o, key, v ) ;
+            } else {
+                throw new InvalidObjectException("Field Type mismatch");
+            }
         } catch (Exception e) {
+            if (o != null) {
             throw utilWrapper.errorSetShortField( e, fieldName,
                 o.toString(),
                 new Short(v) ) ;
+            } else {
+                throw utilWrapper.errorSetShortField( e, fieldName,
+                    "null " + c.getName() + " object",
+                    new Short(v) ) ;
+            }
         }
     }
 
@@ -2639,12 +2684,22 @@
     {
         try {
             Field fld = c.getDeclaredField( fieldName ) ;
-            long key = bridge.objectFieldOffset( fld ) ;
-            bridge.putInt( o, key, v ) ;
+            if ((fld != null) && (fld.getType() == Integer.TYPE)) {
+                long key = bridge.objectFieldOffset( fld ) ;
+                bridge.putInt( o, key, v ) ;
+            } else {
+                throw new InvalidObjectException("Field Type mismatch");
+            }
         } catch (Exception e) {
-            throw utilWrapper.errorSetIntField( e, fieldName,
-                o.toString(),
-                new Integer(v) ) ;
+            if (o != null) {
+                throw utilWrapper.errorSetIntField( e, fieldName,
+                    o.toString(),
+                    new Integer(v) ) ;
+            } else {
+                throw utilWrapper.errorSetIntField( e, fieldName,
+                    "null " + c.getName() + " object",
+                    new Integer(v) ) ;
+            }
         }
     }
 
@@ -2652,12 +2707,22 @@
     {
         try {
             Field fld = c.getDeclaredField( fieldName ) ;
-            long key = bridge.objectFieldOffset( fld ) ;
-            bridge.putLong( o, key, v ) ;
+            if ((fld != null) && (fld.getType() == Long.TYPE)) {
+                long key = bridge.objectFieldOffset( fld ) ;
+                bridge.putLong( o, key, v ) ;
+            } else {
+                throw new InvalidObjectException("Field Type mismatch");
+            }
         } catch (Exception e) {
-            throw utilWrapper.errorSetLongField( e, fieldName,
-                o.toString(),
-                new Long(v) ) ;
+            if (o != null) {
+                throw utilWrapper.errorSetLongField( e, fieldName,
+                    o.toString(),
+                    new Long(v) ) ;
+            } else {
+                throw utilWrapper.errorSetLongField( e, fieldName,
+                    "null " + c.getName() + " object",
+                    new Long(v) ) ;
+            }
         }
     }
 
@@ -2665,12 +2730,22 @@
     {
         try {
             Field fld = c.getDeclaredField( fieldName ) ;
-            long key = bridge.objectFieldOffset( fld ) ;
-            bridge.putFloat( o, key, v ) ;
+            if ((fld != null) && (fld.getType() == Float.TYPE)) {
+                long key = bridge.objectFieldOffset( fld ) ;
+                bridge.putFloat( o, key, v ) ;
+            } else {
+                throw new InvalidObjectException("Field Type mismatch");
+            }
         } catch (Exception e) {
-            throw utilWrapper.errorSetFloatField( e, fieldName,
-                o.toString(),
-                new Float(v) ) ;
+            if (o != null) {
+                throw utilWrapper.errorSetFloatField( e, fieldName,
+                    o.toString(),
+                    new Float(v) ) ;
+            } else {
+                throw utilWrapper.errorSetFloatField( e, fieldName,
+                    "null " + c.getName() + " object",
+                    new Float(v) ) ;
+            }
         }
     }
 
@@ -2678,12 +2753,22 @@
     {
         try {
             Field fld = c.getDeclaredField( fieldName ) ;
-            long key = bridge.objectFieldOffset( fld ) ;
-            bridge.putDouble( o, key, v ) ;
+            if ((fld != null) && (fld.getType() == Double.TYPE)) {
+                long key = bridge.objectFieldOffset( fld ) ;
+                bridge.putDouble( o, key, v ) ;
+            } else {
+                throw new InvalidObjectException("Field Type mismatch");
+            }
         } catch (Exception e) {
-            throw utilWrapper.errorSetDoubleField( e, fieldName,
-                o.toString(),
-                new Double(v) ) ;
+            if (o != null) {
+                throw utilWrapper.errorSetDoubleField( e, fieldName,
+                    o.toString(),
+                    new Double(v) ) ;
+            } else {
+                throw utilWrapper.errorSetDoubleField( e, fieldName,
+                    "null " + c.getName() + " object",
+                    new Double(v) ) ;
+            }
         }
     }
 
--- a/hotspot/.hgtags	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/.hgtags	Wed Jul 05 20:42:36 2017 +0200
@@ -475,3 +475,4 @@
 8672e9264db30c21504063932dbc374eabc287a1 jdk9-b70
 07c6b035d68b0c41b1dcd442157b50b41a2551e9 jdk9-b71
 c1b2825ef47e75cb34dd18450d1c4280b7c5853c jdk9-b72
+e37d432868be0aa7cb5e0f3d7caff1e825d8ead3 jdk9-b73
--- a/hotspot/agent/src/share/classes/sun/jvm/hotspot/code/CodeCache.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/agent/src/share/classes/sun/jvm/hotspot/code/CodeCache.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 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
@@ -48,8 +48,13 @@
     Type type = db.lookupType("CodeCache");
 
     // Get array of CodeHeaps
+    // Note: CodeHeap may be subclassed with optional private heap mechanisms.
+    Type codeHeapType = db.lookupType("CodeHeap");
+    VirtualBaseConstructor heapConstructor =
+        new VirtualBaseConstructor(db, codeHeapType, "sun.jvm.hotspot.memory", CodeHeap.class);
+
     AddressField heapsField = type.getAddressField("_heaps");
-    heapArray = GrowableArray.create(heapsField.getValue(), new StaticBaseConstructor<CodeHeap>(CodeHeap.class));
+    heapArray = GrowableArray.create(heapsField.getValue(), heapConstructor);
 
     scavengeRootNMethodsField = type.getAddressField("_scavenge_root_nmethods");
 
@@ -180,31 +185,9 @@
 
   public void iterate(CodeCacheVisitor visitor) {
     visitor.prologue(lowBound(), highBound());
-    CodeBlob lastBlob = null;
-
     for (int i = 0; i < heapArray.length(); ++i) {
       CodeHeap current_heap = heapArray.at(i);
-      Address ptr = current_heap.begin();
-      while (ptr != null && ptr.lessThan(current_heap.end())) {
-        try {
-          // Use findStart to get a pointer inside blob other findBlob asserts
-          CodeBlob blob = findBlobUnsafe(current_heap.findStart(ptr));
-          if (blob != null) {
-            visitor.visit(blob);
-            if (blob == lastBlob) {
-              throw new InternalError("saw same blob twice");
-            }
-            lastBlob = blob;
-          }
-        } catch (RuntimeException e) {
-          e.printStackTrace();
-        }
-        Address next = current_heap.nextBlock(ptr);
-        if (next != null && next.lessThan(ptr)) {
-          throw new InternalError("pointer moved backwards");
-        }
-        ptr = next;
-      }
+      current_heap.iterate(visitor, this);
     }
     visitor.epilogue();
   }
--- a/hotspot/agent/src/share/classes/sun/jvm/hotspot/memory/CodeHeap.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/agent/src/share/classes/sun/jvm/hotspot/memory/CodeHeap.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2004, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 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
@@ -25,6 +25,7 @@
 package sun.jvm.hotspot.memory;
 
 import java.util.*;
+import sun.jvm.hotspot.code.*;
 import sun.jvm.hotspot.debugger.*;
 import sun.jvm.hotspot.runtime.*;
 import sun.jvm.hotspot.types.*;
@@ -90,7 +91,7 @@
     return h.getAllocatedSpace();
   }
 
-  public Address nextBlock(Address ptr) {
+  private Address nextBlock(Address ptr) {
     Address base = blockBase(ptr);
     if (base == null) {
       return null;
@@ -99,6 +100,31 @@
     return base.addOffsetTo(block.getLength() * (1 << getLog2SegmentSize()));
   }
 
+  public void iterate(CodeCacheVisitor visitor, CodeCache cache) {
+    CodeBlob lastBlob = null;
+    Address ptr = begin();
+    while (ptr != null && ptr.lessThan(end())) {
+      try {
+        // Use findStart to get a pointer inside blob other findBlob asserts
+        CodeBlob blob = cache.createCodeBlobWrapper(findStart(ptr));
+        if (blob != null) {
+          visitor.visit(blob);
+          if (blob == lastBlob) {
+            throw new InternalError("saw same blob twice");
+          }
+          lastBlob = blob;
+        }
+      } catch (RuntimeException e) {
+        e.printStackTrace();
+      }
+      Address next = nextBlock(ptr);
+      if (next != null && next.lessThan(ptr)) {
+        throw new InternalError("pointer moved backwards");
+      }
+      ptr = next;
+    }
+  }
+
   //--------------------------------------------------------------------------------
   // Internals only below this point
   //
--- a/hotspot/make/aix/makefiles/mapfile-vers-debug	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/make/aix/makefiles/mapfile-vers-debug	Wed Jul 05 20:42:36 2017 +0200
@@ -141,6 +141,18 @@
                 JVM_Halt;
                 JVM_HoldsLock;
                 JVM_IHashCode;
+                JVM_ImageAttributeOffsets;
+                JVM_ImageAttributeOffsetsLength;
+                JVM_ImageClose;
+                JVM_ImageFindAttributes;
+                JVM_ImageGetAttributes;
+                JVM_ImageGetAttributesCount;
+                JVM_ImageGetDataAddress;
+                JVM_ImageGetIndexAddress;
+                JVM_ImageGetStringBytes;
+                JVM_ImageOpen;
+                JVM_ImageRead;
+                JVM_ImageReadCompressed;
                 JVM_InitAgentProperties;
                 JVM_InitProperties;
                 JVM_InternString;
--- a/hotspot/make/aix/makefiles/mapfile-vers-product	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/make/aix/makefiles/mapfile-vers-product	Wed Jul 05 20:42:36 2017 +0200
@@ -139,6 +139,18 @@
                 JVM_Halt;
                 JVM_HoldsLock;
                 JVM_IHashCode;
+                JVM_ImageAttributeOffsets;
+                JVM_ImageAttributeOffsetsLength;
+                JVM_ImageClose;
+                JVM_ImageFindAttributes;
+                JVM_ImageGetAttributes;
+                JVM_ImageGetAttributesCount;
+                JVM_ImageGetDataAddress;
+                JVM_ImageGetIndexAddress;
+                JVM_ImageGetStringBytes;
+                JVM_ImageOpen;
+                JVM_ImageRead;
+                JVM_ImageReadCompressed;
                 JVM_InitAgentProperties;
                 JVM_InitProperties;
                 JVM_InternString;
--- a/hotspot/make/bsd/makefiles/mapfile-vers-darwin-debug	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/make/bsd/makefiles/mapfile-vers-darwin-debug	Wed Jul 05 20:42:36 2017 +0200
@@ -139,6 +139,18 @@
                 _JVM_Halt
                 _JVM_HoldsLock
                 _JVM_IHashCode
+                _JVM_ImageAttributeOffsets
+                _JVM_ImageAttributeOffsetsLength
+                _JVM_ImageClose
+                _JVM_ImageFindAttributes
+                _JVM_ImageGetAttributes
+                _JVM_ImageGetAttributesCount
+                _JVM_ImageGetDataAddress
+                _JVM_ImageGetIndexAddress
+                _JVM_ImageGetStringBytes
+                _JVM_ImageOpen
+                _JVM_ImageRead
+                _JVM_ImageReadCompressed
                 _JVM_InitAgentProperties
                 _JVM_InitProperties
                 _JVM_InternString
@@ -188,7 +200,7 @@
                 _JVM_Yield
                 _JVM_handle_bsd_signal
 
-                # miscellaneous functions
+				# miscellaneous functions
                 _jio_fprintf
                 _jio_printf
                 _jio_snprintf
--- a/hotspot/make/bsd/makefiles/mapfile-vers-darwin-product	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/make/bsd/makefiles/mapfile-vers-darwin-product	Wed Jul 05 20:42:36 2017 +0200
@@ -139,6 +139,18 @@
                 _JVM_Halt
                 _JVM_HoldsLock
                 _JVM_IHashCode
+                _JVM_ImageAttributeOffsets
+                _JVM_ImageAttributeOffsetsLength
+                _JVM_ImageClose
+                _JVM_ImageFindAttributes
+                _JVM_ImageGetAttributes
+                _JVM_ImageGetAttributesCount
+                _JVM_ImageGetDataAddress
+                _JVM_ImageGetIndexAddress
+                _JVM_ImageGetStringBytes
+                _JVM_ImageOpen
+                _JVM_ImageRead
+                _JVM_ImageReadCompressed
                 _JVM_InitAgentProperties
                 _JVM_InitProperties
                 _JVM_InternString
--- a/hotspot/make/bsd/makefiles/mapfile-vers-debug	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/make/bsd/makefiles/mapfile-vers-debug	Wed Jul 05 20:42:36 2017 +0200
@@ -141,6 +141,18 @@
                 JVM_Halt;
                 JVM_HoldsLock;
                 JVM_IHashCode;
+                JVM_ImageAttributeOffsets;
+                JVM_ImageAttributeOffsetsLength;
+                JVM_ImageClose;
+                JVM_ImageFindAttributes;
+                JVM_ImageGetAttributes;
+                JVM_ImageGetAttributesCount;
+                JVM_ImageGetDataAddress;
+                JVM_ImageGetIndexAddress;
+                JVM_ImageGetStringBytes;
+                JVM_ImageOpen;
+                JVM_ImageRead;
+                JVM_ImageReadCompressed;
                 JVM_InitAgentProperties;
                 JVM_InitProperties;
                 JVM_InternString;
--- a/hotspot/make/bsd/makefiles/mapfile-vers-product	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/make/bsd/makefiles/mapfile-vers-product	Wed Jul 05 20:42:36 2017 +0200
@@ -141,6 +141,18 @@
                 JVM_Halt;
                 JVM_HoldsLock;
                 JVM_IHashCode;
+                JVM_ImageAttributeOffsets;
+                JVM_ImageAttributeOffsetsLength;
+                JVM_ImageClose;
+                JVM_ImageFindAttributes;
+                JVM_ImageGetAttributes;
+                JVM_ImageGetAttributesCount;
+                JVM_ImageGetDataAddress;
+                JVM_ImageGetIndexAddress;
+                JVM_ImageGetStringBytes;
+                JVM_ImageOpen;
+                JVM_ImageRead;
+                JVM_ImageReadCompressed;
                 JVM_InitAgentProperties;
                 JVM_InitProperties;
                 JVM_InternString;
--- a/hotspot/make/linux/makefiles/buildtree.make	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/make/linux/makefiles/buildtree.make	Wed Jul 05 20:42:36 2017 +0200
@@ -118,7 +118,8 @@
 	$(PLATFORM_DIR)/generated/dependencies \
 	$(PLATFORM_DIR)/generated/adfiles \
 	$(PLATFORM_DIR)/generated/jvmtifiles \
-	$(PLATFORM_DIR)/generated/tracefiles
+	$(PLATFORM_DIR)/generated/tracefiles \
+	$(PLATFORM_DIR)/generated/extensions
 
 TARGETS      = debug fastdebug optimized product
 SUBMAKE_DIRS = $(addprefix $(PLATFORM_DIR)/,$(TARGETS))
--- a/hotspot/make/linux/makefiles/mapfile-vers-debug	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/make/linux/makefiles/mapfile-vers-debug	Wed Jul 05 20:42:36 2017 +0200
@@ -141,6 +141,18 @@
                 JVM_Halt;
                 JVM_HoldsLock;
                 JVM_IHashCode;
+                JVM_ImageAttributeOffsets;
+                JVM_ImageAttributeOffsetsLength;
+                JVM_ImageClose;
+                JVM_ImageFindAttributes;
+                JVM_ImageGetAttributes;
+                JVM_ImageGetAttributesCount;
+                JVM_ImageGetDataAddress;
+                JVM_ImageGetIndexAddress;
+                JVM_ImageGetStringBytes;
+                JVM_ImageOpen;
+                JVM_ImageRead;
+                JVM_ImageReadCompressed;
                 JVM_InitAgentProperties;
                 JVM_InitProperties;
                 JVM_InternString;
--- a/hotspot/make/linux/makefiles/mapfile-vers-product	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/make/linux/makefiles/mapfile-vers-product	Wed Jul 05 20:42:36 2017 +0200
@@ -141,6 +141,18 @@
                 JVM_Halt;
                 JVM_HoldsLock;
                 JVM_IHashCode;
+                JVM_ImageAttributeOffsets;
+                JVM_ImageAttributeOffsetsLength;
+                JVM_ImageClose;
+                JVM_ImageFindAttributes;
+                JVM_ImageGetAttributes;
+                JVM_ImageGetAttributesCount;
+                JVM_ImageGetDataAddress;
+                JVM_ImageGetIndexAddress;
+                JVM_ImageGetStringBytes;
+                JVM_ImageOpen;
+                JVM_ImageRead;
+                JVM_ImageReadCompressed;
                 JVM_InitAgentProperties;
                 JVM_InitProperties;
                 JVM_InternString;
--- a/hotspot/make/linux/makefiles/rules.make	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/make/linux/makefiles/rules.make	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2003, 2014, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2003, 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
@@ -34,7 +34,7 @@
 CC_COMPILE       = $(CC) $(CXXFLAGS) $(CFLAGS)
 CXX_COMPILE      = $(CXX) $(CXXFLAGS) $(CFLAGS)
 
-AS.S            = $(AS) $(ASFLAGS)
+AS.S             = $(AS) $(ASFLAGS)
 
 COMPILE.CC       = $(CC_COMPILE) -c
 GENASM.CC        = $(CC_COMPILE) -S
@@ -170,6 +170,12 @@
 	$(QUIETLY) $(REMOVE_TARGET)
 	$(QUIETLY) $(AS.S) $(DEPFLAGS) -o $@ $< $(COMPILE_DONE)
 
+# gcc applies preprocessing if the file extension is .S instead of .s
+%.o: %.S
+	@echo $(LOG_INFO) Preprocessing and assembling $<
+	$(QUIETLY) $(REMOVE_TARGET)
+	$(QUIETLY) $(AS.S) $(DEPFLAGS) -o $@ $< $(COMPILE_DONE) 
+
 %.s: %.cpp
 	@echo $(LOG_INFO) Generating assembly for $<
 	$(QUIETLY) $(GENASM.CXX) -o $@ $<
--- a/hotspot/make/linux/makefiles/vm.make	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/make/linux/makefiles/vm.make	Wed Jul 05 20:42:36 2017 +0200
@@ -54,7 +54,7 @@
 # Src_Dirs_V is everything in src/share/vm/*, plus the right os/*/vm and cpu/*/vm
 # The adfiles directory contains ad_<arch>.[ch]pp.
 # The jvmtifiles directory contains jvmti*.[ch]pp
-Src_Dirs_V += $(GENERATED)/adfiles $(GENERATED)/jvmtifiles $(GENERATED)/tracefiles
+Src_Dirs_V += $(GENERATED)/adfiles $(GENERATED)/jvmtifiles $(GENERATED)/tracefiles $(GENERATED)/extensions
 VPATH += $(Src_Dirs_V:%=%:)
 
 # set INCLUDES for C preprocessor.
@@ -161,6 +161,8 @@
   fi)
 endif
 
+CORE_PATHS+=$(GENERATED)/extensions
+
 COMPILER1_PATHS := $(call altsrc,$(HS_COMMON_SRC)/share/vm/c1)
 COMPILER1_PATHS += $(HS_COMMON_SRC)/share/vm/c1
 
@@ -207,6 +209,8 @@
 Src_Files_EXCLUDE += \*x86_32\*
 endif
 
+Src_Files_BASE += \*.c \*.cpp \*.s 
+
 # Alternate vm.make
 # This has to be included here to allow changes to the source
 # directories and excluded files before they are expanded
@@ -216,13 +220,13 @@
 # Locate all source files in the given directory, excluding files in Src_Files_EXCLUDE.
 define findsrc
 	$(notdir $(shell find $(1)/. ! -name . -prune \
-		-a \( -name \*.c -o -name \*.cpp -o -name \*.s \) \
+		-a \( -name DUMMY $(addprefix -o -name ,$(Src_Files_BASE)) \) \
 		-a ! \( -name DUMMY $(addprefix -o -name ,$(Src_Files_EXCLUDE)) \)))
 endef
 
 Src_Files := $(foreach e,$(Src_Dirs),$(call findsrc,$(e)))
 
-Obj_Files = $(sort $(addsuffix .o,$(basename $(Src_Files))))
+Obj_Files = $(sort $(addsuffix .o,$(basename $(Src_Files))) $(EXTENDED_JVM_OBJ_FILES))
 
 JVM_OBJ_FILES = $(Obj_Files)
 
@@ -244,10 +248,16 @@
 VMDEF_PAT := ^gHotSpotVM|$(VMDEF_PAT)
 VMDEF_PAT := ^UseSharedSpaces$$|$(VMDEF_PAT)
 VMDEF_PAT := ^_ZN9Arguments17SharedArchivePathE$$|$(VMDEF_PAT)
+ifneq ($(VMDEF_PAT_EXT),)
+  VMDEF_PAT := $(VMDEF_PAT_EXT)|$(VMDEF_PAT)
+endif        
 
-vm.def: $(Res_Files) $(Obj_Files)
+vm.def: $(Res_Files) $(Obj_Files) $(VM_DEF_EXT)
 	$(QUIETLY) $(NM) --defined-only $(Obj_Files) | sort -k3 -u | \
 	awk '$$3 ~ /$(VMDEF_PAT)/ { print "\t" $$3 ";" }' > $@
+ifneq ($(VM_DEF_EXT),)
+	cat $(VM_DEF_EXT) >> $@
+endif        
 
 mapfile_ext:
 	rm -f $@
--- a/hotspot/make/solaris/makefiles/mapfile-vers	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/make/solaris/makefiles/mapfile-vers	Wed Jul 05 20:42:36 2017 +0200
@@ -141,6 +141,18 @@
                 JVM_Halt;
                 JVM_HoldsLock;
                 JVM_IHashCode;
+                JVM_ImageAttributeOffsets;
+                JVM_ImageAttributeOffsetsLength;
+                JVM_ImageClose;
+                JVM_ImageFindAttributes;
+                JVM_ImageGetAttributes;
+                JVM_ImageGetAttributesCount;
+                JVM_ImageGetDataAddress;
+                JVM_ImageGetIndexAddress;
+                JVM_ImageGetStringBytes;
+                JVM_ImageOpen;
+                JVM_ImageRead;
+                JVM_ImageReadCompressed;
                 JVM_InitAgentProperties;
                 JVM_InitProperties;
                 JVM_InternString;
--- a/hotspot/make/solaris/makefiles/vm.make	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/make/solaris/makefiles/vm.make	Wed Jul 05 20:42:36 2017 +0200
@@ -143,7 +143,7 @@
 LIBS += -lsocket -lsched -ldl $(LIBM) -lthread -lc -ldemangle
 endif # sparcWorks
 
-LIBS += -lkstat
+LIBS += -lkstat -lrt
 
 # By default, link the *.o into the library, not the executable.
 LINK_INTO$(LINK_INTO) = LIBJVM
--- a/hotspot/src/cpu/aarch64/vm/assembler_aarch64.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/aarch64/vm/assembler_aarch64.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -2270,17 +2270,21 @@
   }
 
   // CRC32 instructions
-#define INSN(NAME, sf, sz)                                                \
+#define INSN(NAME, c, sf, sz)                                             \
   void NAME(Register Rd, Register Rn, Register Rm) {                      \
     starti;                                                               \
-    f(sf, 31), f(0b0011010110, 30, 21), f(0b0100, 15, 12), f(sz, 11, 10); \
-    rf(Rm, 16), rf(Rn, 5), rf(Rd, 0);                                     \
+    f(sf, 31), f(0b0011010110, 30, 21), f(0b010, 15, 13), f(c, 12);       \
+    f(sz, 11, 10), rf(Rm, 16), rf(Rn, 5), rf(Rd, 0);                      \
   }
 
-  INSN(crc32b, 0, 0b00);
-  INSN(crc32h, 0, 0b01);
-  INSN(crc32w, 0, 0b10);
-  INSN(crc32x, 1, 0b11);
+  INSN(crc32b,  0, 0, 0b00);
+  INSN(crc32h,  0, 0, 0b01);
+  INSN(crc32w,  0, 0, 0b10);
+  INSN(crc32x,  0, 1, 0b11);
+  INSN(crc32cb, 1, 0, 0b00);
+  INSN(crc32ch, 1, 0, 0b01);
+  INSN(crc32cw, 1, 0, 0b10);
+  INSN(crc32cx, 1, 1, 0b11);
 
 #undef INSN
 
--- a/hotspot/src/cpu/aarch64/vm/globalDefinitions_aarch64.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/aarch64/vm/globalDefinitions_aarch64.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1,6 +1,6 @@
 /*
- * Copyright (c) 1999, 2010, Oracle and/or its affiliates. All rights reserved.
- * Copyright (c) 2014, Red Hat Inc. All rights reserved.
+ * Copyright (c) 1999, 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2014, 2015, Red Hat Inc. 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,12 +28,6 @@
 
 const int StackAlignmentInBytes  = 16;
 
-// Indicates whether the C calling conventions require that
-// 32-bit integer argument values are properly extended to 64 bits.
-// If set, SharedRuntime::c_calling_convention() must adapt
-// signatures accordingly.
-const bool CCallingConventionRequiresIntsAsLongs = true;
-
 #define SUPPORTS_NATIVE_CX8
 
 // The maximum B/BL offset range on AArch64 is 128MB.
--- a/hotspot/src/cpu/aarch64/vm/macroAssembler_aarch64.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/aarch64/vm/macroAssembler_aarch64.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -2914,6 +2914,65 @@
     ornw(crc, zr, crc);
 }
 
+/**
+ * @param crc   register containing existing CRC (32-bit)
+ * @param buf   register pointing to input byte buffer (byte*)
+ * @param len   register containing number of bytes
+ * @param table register that will contain address of CRC table
+ * @param tmp   scratch register
+ */
+void MacroAssembler::kernel_crc32c(Register crc, Register buf, Register len,
+        Register table0, Register table1, Register table2, Register table3,
+        Register tmp, Register tmp2, Register tmp3) {
+  Label L_exit;
+  Label CRC_by64_loop, CRC_by4_loop, CRC_by1_loop;
+
+    subs(len, len, 64);
+    br(Assembler::GE, CRC_by64_loop);
+    adds(len, len, 64-4);
+    br(Assembler::GE, CRC_by4_loop);
+    adds(len, len, 4);
+    br(Assembler::GT, CRC_by1_loop);
+    b(L_exit);
+
+  BIND(CRC_by4_loop);
+    ldrw(tmp, Address(post(buf, 4)));
+    subs(len, len, 4);
+    crc32cw(crc, crc, tmp);
+    br(Assembler::GE, CRC_by4_loop);
+    adds(len, len, 4);
+    br(Assembler::LE, L_exit);
+  BIND(CRC_by1_loop);
+    ldrb(tmp, Address(post(buf, 1)));
+    subs(len, len, 1);
+    crc32cb(crc, crc, tmp);
+    br(Assembler::GT, CRC_by1_loop);
+    b(L_exit);
+
+    align(CodeEntryAlignment);
+  BIND(CRC_by64_loop);
+    subs(len, len, 64);
+    ldp(tmp, tmp3, Address(post(buf, 16)));
+    crc32cx(crc, crc, tmp);
+    crc32cx(crc, crc, tmp3);
+    ldp(tmp, tmp3, Address(post(buf, 16)));
+    crc32cx(crc, crc, tmp);
+    crc32cx(crc, crc, tmp3);
+    ldp(tmp, tmp3, Address(post(buf, 16)));
+    crc32cx(crc, crc, tmp);
+    crc32cx(crc, crc, tmp3);
+    ldp(tmp, tmp3, Address(post(buf, 16)));
+    crc32cx(crc, crc, tmp);
+    crc32cx(crc, crc, tmp3);
+    br(Assembler::GE, CRC_by64_loop);
+    adds(len, len, 64-4);
+    br(Assembler::GE, CRC_by4_loop);
+    adds(len, len, 4);
+    br(Assembler::GT, CRC_by1_loop);
+  BIND(L_exit);
+    return;
+}
+
 SkipIfEqual::SkipIfEqual(
     MacroAssembler* masm, const bool* flag_addr, bool value) {
   _masm = masm;
--- a/hotspot/src/cpu/aarch64/vm/macroAssembler_aarch64.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/aarch64/vm/macroAssembler_aarch64.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -967,6 +967,10 @@
   void kernel_crc32(Register crc, Register buf, Register len,
         Register table0, Register table1, Register table2, Register table3,
         Register tmp, Register tmp2, Register tmp3);
+  // CRC32 code for java.util.zip.CRC32C::updateBytes() instrinsic.
+  void kernel_crc32c(Register crc, Register buf, Register len,
+        Register table0, Register table1, Register table2, Register table3,
+        Register tmp, Register tmp2, Register tmp3);
 
 #undef VIRTUAL
 
--- a/hotspot/src/cpu/aarch64/vm/stubGenerator_aarch64.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/aarch64/vm/stubGenerator_aarch64.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -2359,6 +2359,47 @@
   /**
    *  Arguments:
    *
+   * Inputs:
+   *   c_rarg0   - int crc
+   *   c_rarg1   - byte* buf
+   *   c_rarg2   - int length
+   *   c_rarg3   - int* table
+   *
+   * Ouput:
+   *       rax   - int crc result
+   */
+  address generate_updateBytesCRC32C() {
+    assert(UseCRC32CIntrinsics, "what are we doing here?");
+
+    __ align(CodeEntryAlignment);
+    StubCodeMark mark(this, "StubRoutines", "updateBytesCRC32C");
+
+    address start = __ pc();
+
+    const Register crc   = c_rarg0;  // crc
+    const Register buf   = c_rarg1;  // source java byte array address
+    const Register len   = c_rarg2;  // length
+    const Register table0 = c_rarg3; // crc_table address
+    const Register table1 = c_rarg4;
+    const Register table2 = c_rarg5;
+    const Register table3 = c_rarg6;
+    const Register tmp3 = c_rarg7;
+
+    BLOCK_COMMENT("Entry:");
+    __ enter(); // required for proper stackwalking of RuntimeStub frame
+
+    __ kernel_crc32c(crc, buf, len,
+              table0, table1, table2, table3, rscratch1, rscratch2, tmp3);
+
+    __ leave(); // required for proper stackwalking of RuntimeStub frame
+    __ ret(lr);
+
+    return start;
+  }
+
+  /**
+   *  Arguments:
+   *
    *  Input:
    *    c_rarg0   - x address
    *    c_rarg1   - x length
@@ -2579,6 +2620,10 @@
       StubRoutines::_sha256_implCompressMB = generate_sha256_implCompress(true,  "sha256_implCompressMB");
     }
 
+    if (UseCRC32CIntrinsics) {
+      StubRoutines::_updateBytesCRC32C = generate_updateBytesCRC32C();
+    }
+
     // Safefetch stubs.
     generate_safefetch("SafeFetch32", sizeof(int),     &StubRoutines::_safefetch32_entry,
                                                        &StubRoutines::_safefetch32_fault_pc,
--- a/hotspot/src/cpu/aarch64/vm/vm_version_aarch64.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/aarch64/vm/vm_version_aarch64.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -199,9 +199,12 @@
     UseCRC32Intrinsics = true;
   }
 
-  if (UseCRC32CIntrinsics) {
-    if (!FLAG_IS_DEFAULT(UseCRC32CIntrinsics))
-      warning("CRC32C intrinsics are not available on this CPU");
+  if (auxv & HWCAP_CRC32) {
+    if (FLAG_IS_DEFAULT(UseCRC32CIntrinsics)) {
+      FLAG_SET_DEFAULT(UseCRC32CIntrinsics, true);
+    }
+  } else if (UseCRC32CIntrinsics) {
+    warning("CRC32C is not available on the CPU");
     FLAG_SET_DEFAULT(UseCRC32CIntrinsics, false);
   }
 
@@ -214,34 +217,31 @@
     FLAG_SET_DEFAULT(UseSHA, false);
   }
 
-  if (!UseSHA) {
+  if (UseSHA && (auxv & HWCAP_SHA1)) {
+    if (FLAG_IS_DEFAULT(UseSHA1Intrinsics)) {
+      FLAG_SET_DEFAULT(UseSHA1Intrinsics, true);
+    }
+  } else if (UseSHA1Intrinsics) {
+    warning("Intrinsics for SHA-1 crypto hash functions not available on this CPU.");
     FLAG_SET_DEFAULT(UseSHA1Intrinsics, false);
-    FLAG_SET_DEFAULT(UseSHA256Intrinsics, false);
-    FLAG_SET_DEFAULT(UseSHA512Intrinsics, false);
-  } else {
-    if (auxv & HWCAP_SHA1) {
-      if (FLAG_IS_DEFAULT(UseSHA1Intrinsics)) {
-        FLAG_SET_DEFAULT(UseSHA1Intrinsics, true);
-      }
-    } else if (UseSHA1Intrinsics) {
-      warning("SHA1 instruction is not available on this CPU.");
-      FLAG_SET_DEFAULT(UseSHA1Intrinsics, false);
+  }
+
+  if (UseSHA && (auxv & HWCAP_SHA2)) {
+    if (FLAG_IS_DEFAULT(UseSHA256Intrinsics)) {
+      FLAG_SET_DEFAULT(UseSHA256Intrinsics, true);
     }
-    if (auxv & HWCAP_SHA2) {
-      if (FLAG_IS_DEFAULT(UseSHA256Intrinsics)) {
-        FLAG_SET_DEFAULT(UseSHA256Intrinsics, true);
-      }
-    } else if (UseSHA256Intrinsics) {
-      warning("SHA256 instruction (for SHA-224 and SHA-256) is not available on this CPU.");
-      FLAG_SET_DEFAULT(UseSHA256Intrinsics, false);
-    }
-    if (UseSHA512Intrinsics) {
-      warning("SHA512 instruction (for SHA-384 and SHA-512) is not available on this CPU.");
-      FLAG_SET_DEFAULT(UseSHA512Intrinsics, false);
-    }
-    if (!(UseSHA1Intrinsics || UseSHA256Intrinsics || UseSHA512Intrinsics)) {
-      FLAG_SET_DEFAULT(UseSHA, false);
-    }
+  } else if (UseSHA256Intrinsics) {
+    warning("Intrinsics for SHA-224 and SHA-256 crypto hash functions not available on this CPU.");
+    FLAG_SET_DEFAULT(UseSHA1Intrinsics, false);
+  }
+
+  if (UseSHA512Intrinsics) {
+    warning("Intrinsics for SHA-384 and SHA-512 crypto hash functions not available on this CPU.");
+    FLAG_SET_DEFAULT(UseSHA512Intrinsics, false);
+  }
+
+  if (!(UseSHA1Intrinsics || UseSHA256Intrinsics || UseSHA512Intrinsics)) {
+    FLAG_SET_DEFAULT(UseSHA, false);
   }
 
   // This machine allows unaligned memory accesses
--- a/hotspot/src/cpu/aarch64/vm/vtableStubs_aarch64.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/aarch64/vm/vtableStubs_aarch64.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -105,7 +105,7 @@
   __ flush();
 
   if (PrintMiscellaneous && (WizardMode || Verbose)) {
-    tty->print_cr("vtable #%d at "PTR_FORMAT"[%d] left over: %d",
+    tty->print_cr("vtable #%d at " PTR_FORMAT "[%d] left over: %d",
                   vtable_index, p2i(s->entry_point()),
                   (int)(s->code_end() - s->entry_point()),
                   (int)(s->code_end() - __ pc()));
@@ -184,7 +184,7 @@
   __ flush();
 
   if (PrintMiscellaneous && (WizardMode || Verbose)) {
-    tty->print_cr("itable #%d at "PTR_FORMAT"[%d] left over: %d",
+    tty->print_cr("itable #%d at " PTR_FORMAT "[%d] left over: %d",
                   itable_index, p2i(s->entry_point()),
                   (int)(s->code_end() - s->entry_point()),
                   (int)(s->code_end() - __ pc()));
--- a/hotspot/src/cpu/ppc/vm/globalDefinitions_ppc.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/ppc/vm/globalDefinitions_ppc.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1,6 +1,6 @@
 /*
- * Copyright (c) 1999, 2013, Oracle and/or its affiliates. All rights reserved.
- * Copyright 2012, 2013 SAP AG. All rights reserved.
+ * Copyright (c) 1999, 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright 2012, 2015 SAP AG. 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,12 +31,6 @@
 
 const int StackAlignmentInBytes = 16;
 
-// Indicates whether the C calling conventions require that
-// 32-bit integer argument values are properly extended to 64 bits.
-// If set, SharedRuntime::c_calling_convention() must adapt
-// signatures accordingly.
-const bool CCallingConventionRequiresIntsAsLongs = true;
-
 #define SUPPORTS_NATIVE_CX8
 
 // The PPC CPUs are NOT multiple-copy-atomic.
--- a/hotspot/src/cpu/ppc/vm/methodHandles_ppc.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/ppc/vm/methodHandles_ppc.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -465,7 +465,7 @@
   bool has_mh = (strstr(adaptername, "/static") == NULL &&
                  strstr(adaptername, "linkTo") == NULL);    // static linkers don't have MH
   const char* mh_reg_name = has_mh ? "R23_method_handle" : "G23";
-  tty->print_cr("MH %s %s="INTPTR_FORMAT " sp=" INTPTR_FORMAT,
+  tty->print_cr("MH %s %s=" INTPTR_FORMAT " sp=" INTPTR_FORMAT,
                 adaptername, mh_reg_name, p2i(mh), p2i(entry_sp));
 
   if (Verbose) {
--- a/hotspot/src/cpu/ppc/vm/sharedRuntime_ppc.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/ppc/vm/sharedRuntime_ppc.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -731,23 +731,8 @@
     case T_SHORT:
     case T_INT:
       // We must cast ints to longs and use full 64 bit stack slots
-      // here. We do the cast in GraphKit::gen_stub() and just guard
-      // here against loosing that change.
-      assert(CCallingConventionRequiresIntsAsLongs,
-             "argument of type int should be promoted to type long");
-      guarantee(i > 0 && sig_bt[i-1] == T_LONG,
-                "argument of type (bt) should have been promoted to type (T_LONG,bt) for bt in "
-                "{T_BOOLEAN, T_CHAR, T_BYTE, T_SHORT, T_INT}");
-      // Do not count halves.
-      regs[i].set_bad();
-      --arg;
-      break;
+      // here.  Thus fall through, handle as long.
     case T_LONG:
-      guarantee(sig_bt[i+1] == T_VOID    ||
-                sig_bt[i+1] == T_BOOLEAN || sig_bt[i+1] == T_CHAR  ||
-                sig_bt[i+1] == T_BYTE    || sig_bt[i+1] == T_SHORT ||
-                sig_bt[i+1] == T_INT,
-                "expecting type (T_LONG,half) or type (T_LONG,bt) with bt in {T_BOOLEAN, T_CHAR, T_BYTE, T_SHORT, T_INT}");
     case T_OBJECT:
     case T_ARRAY:
     case T_ADDRESS:
@@ -1273,7 +1258,7 @@
 static void int_move(MacroAssembler*masm,
                      VMRegPair src, VMRegPair dst,
                      Register r_caller_sp, Register r_temp) {
-  assert(src.first()->is_valid() && src.second() == src.first()->next(), "incoming must be long-int");
+  assert(src.first()->is_valid(), "incoming must be int");
   assert(dst.first()->is_valid() && dst.second() == dst.first()->next(), "outgoing must be long");
 
   if (src.first()->is_stack()) {
@@ -1762,13 +1747,6 @@
   // the jni function will expect them. To figure out where they go
   // we convert the java signature to a C signature by inserting
   // the hidden arguments as arg[0] and possibly arg[1] (static method)
-  //
-  // Additionally, on ppc64 we must convert integers to longs in the C
-  // signature. We do this in advance in order to have no trouble with
-  // indexes into the bt-arrays.
-  // So convert the signature and registers now, and adjust the total number
-  // of in-arguments accordingly.
-  int i2l_argcnt = convert_ints_to_longints_argcnt(total_in_args, in_sig_bt); // PPC64: pass ints as longs.
 
   // Calculate the total number of C arguments and create arrays for the
   // signature and the outgoing registers.
@@ -1776,7 +1754,7 @@
   // some floating-point arguments must be passed in registers _and_
   // in stack locations.
   bool method_is_static = method->is_static();
-  int  total_c_args     = i2l_argcnt;
+  int  total_c_args     = total_in_args;
 
   if (!is_critical_native) {
     int n_hidden_args = method_is_static ? 2 : 1;
@@ -1785,7 +1763,7 @@
     // No JNIEnv*, no this*, but unpacked arrays (base+length).
     for (int i = 0; i < total_in_args; i++) {
       if (in_sig_bt[i] == T_ARRAY) {
-        total_c_args += 2; // PPC64: T_LONG, T_INT, T_ADDRESS (see convert_ints_to_longints and c_calling_convention)
+        total_c_args++;
       }
     }
   }
@@ -1803,8 +1781,6 @@
 
   int argc = 0;
   if (!is_critical_native) {
-    convert_ints_to_longints(i2l_argcnt, total_in_args, in_sig_bt, in_regs); // PPC64: pass ints as longs.
-
     out_sig_bt[argc++] = T_ADDRESS;
     if (method->is_static()) {
       out_sig_bt[argc++] = T_OBJECT;
@@ -1815,7 +1791,7 @@
     }
   } else {
     Thread* THREAD = Thread::current();
-    in_elem_bt = NEW_RESOURCE_ARRAY(BasicType, i2l_argcnt);
+    in_elem_bt = NEW_RESOURCE_ARRAY(BasicType, total_c_args);
     SignatureStream ss(method->signature());
     int o = 0;
     for (int i = 0; i < total_in_args ; i++, o++) {
@@ -1839,28 +1815,16 @@
         }
       } else {
         in_elem_bt[o] = T_VOID;
-        switch(in_sig_bt[i]) { // PPC64: pass ints as longs.
-          case T_BOOLEAN:
-          case T_CHAR:
-          case T_BYTE:
-          case T_SHORT:
-          case T_INT: in_elem_bt[++o] = T_VOID; break;
-          default: break;
-        }
       }
       if (in_sig_bt[i] != T_VOID) {
         assert(in_sig_bt[i] == ss.type(), "must match");
         ss.next();
       }
     }
-    assert(i2l_argcnt==o, "must match");
-
-    convert_ints_to_longints(i2l_argcnt, total_in_args, in_sig_bt, in_regs); // PPC64: pass ints as longs.
 
     for (int i = 0; i < total_in_args ; i++ ) {
       if (in_sig_bt[i] == T_ARRAY) {
         // Arrays are passed as int, elem* pair.
-        out_sig_bt[argc++] = T_LONG; // PPC64: pass ints as longs.
         out_sig_bt[argc++] = T_INT;
         out_sig_bt[argc++] = T_ADDRESS;
       } else {
@@ -1921,7 +1885,8 @@
           case T_BYTE:
           case T_SHORT:
           case T_CHAR:
-          case T_INT:  /*single_slots++;*/ break; // PPC64: pass ints as longs.
+          case T_INT:
+          // Fall through.
           case T_ARRAY:
           case T_LONG: double_slots++; break;
           default:  ShouldNotReachHere();
@@ -2019,7 +1984,7 @@
 
   __ save_LR_CR(r_temp_1);
   __ generate_stack_overflow_check(frame_size_in_bytes); // Check before creating frame.
-  __ mr(r_callers_sp, R1_SP);                       // Remember frame pointer.
+  __ mr(r_callers_sp, R1_SP);                            // Remember frame pointer.
   __ push_frame(frame_size_in_bytes, r_temp_1);          // Push the c2n adapter's frame.
   frame_done_pc = (intptr_t)__ pc();
 
@@ -2098,24 +2063,16 @@
       case T_BYTE:
       case T_SHORT:
       case T_INT:
-        guarantee(in > 0 && in_sig_bt[in-1] == T_LONG,
-                  "expecting type (T_LONG,bt) for bt in {T_BOOLEAN, T_CHAR, T_BYTE, T_SHORT, T_INT}");
+        // Move int and do sign extension.
+        int_move(masm, in_regs[in], out_regs[out], r_callers_sp, r_temp_1);
         break;
       case T_LONG:
-        if (in_sig_bt[in+1] == T_VOID) {
-          long_move(masm, in_regs[in], out_regs[out], r_callers_sp, r_temp_1);
-        } else {
-          guarantee(in_sig_bt[in+1] == T_BOOLEAN || in_sig_bt[in+1] == T_CHAR  ||
-                    in_sig_bt[in+1] == T_BYTE    || in_sig_bt[in+1] == T_SHORT ||
-                    in_sig_bt[in+1] == T_INT,
-                 "expecting type (T_LONG,bt) for bt in {T_BOOLEAN, T_CHAR, T_BYTE, T_SHORT, T_INT}");
-          int_move(masm, in_regs[in], out_regs[out], r_callers_sp, r_temp_1);
-        }
+        long_move(masm, in_regs[in], out_regs[out], r_callers_sp, r_temp_1);
         break;
       case T_ARRAY:
         if (is_critical_native) {
           int body_arg = out;
-          out -= 2; // Point to length arg. PPC64: pass ints as longs.
+          out -= 1; // Point to length arg.
           unpack_array_argument(masm, in_regs[in], in_elem_bt[in], out_regs[body_arg], out_regs[out],
                                 r_callers_sp, r_temp_1, r_temp_2);
           break;
@@ -2187,7 +2144,6 @@
   // Make sure that thread is non-volatile; it crosses a bunch of VM calls below.
   assert(R16_thread->is_nonvolatile(), "thread must be in non-volatile register");
 
-
 # if 0
   // DTrace method entry
 # endif
--- a/hotspot/src/cpu/sparc/vm/globalDefinitions_sparc.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/sparc/vm/globalDefinitions_sparc.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1999, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1999, 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
@@ -30,12 +30,6 @@
 
 const int StackAlignmentInBytes = (2*wordSize);
 
-// Indicates whether the C calling conventions require that
-// 32-bit integer argument values are properly extended to 64 bits.
-// If set, SharedRuntime::c_calling_convention() must adapt
-// signatures accordingly.
-const bool CCallingConventionRequiresIntsAsLongs = false;
-
 #define SUPPORTS_NATIVE_CX8
 
 // The expected size in bytes of a cache line, used to pad data structures.
--- a/hotspot/src/cpu/sparc/vm/methodHandles_sparc.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/sparc/vm/methodHandles_sparc.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -483,7 +483,7 @@
   bool has_mh = (strstr(adaptername, "/static") == NULL &&
                  strstr(adaptername, "linkTo") == NULL);    // static linkers don't have MH
   const char* mh_reg_name = has_mh ? "G3_mh" : "G3";
-  tty->print_cr("MH %s %s="INTPTR_FORMAT " saved_sp=" INTPTR_FORMAT " args=" INTPTR_FORMAT,
+  tty->print_cr("MH %s %s=" INTPTR_FORMAT " saved_sp=" INTPTR_FORMAT " args=" INTPTR_FORMAT,
                 adaptername, mh_reg_name,
                 p2i(mh), p2i(saved_sp), p2i(args));
 
--- a/hotspot/src/cpu/sparc/vm/vm_version_sparc.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/sparc/vm/vm_version_sparc.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -329,39 +329,35 @@
     FLAG_SET_DEFAULT(UseSHA, false);
   }
 
-  if (!UseSHA) {
+  if (UseSHA && has_sha1()) {
+    if (FLAG_IS_DEFAULT(UseSHA1Intrinsics)) {
+      FLAG_SET_DEFAULT(UseSHA1Intrinsics, true);
+    }
+  } else if (UseSHA1Intrinsics) {
+    warning("Intrinsics for SHA-1 crypto hash functions not available on this CPU.");
     FLAG_SET_DEFAULT(UseSHA1Intrinsics, false);
-    FLAG_SET_DEFAULT(UseSHA256Intrinsics, false);
-    FLAG_SET_DEFAULT(UseSHA512Intrinsics, false);
-  } else {
-    if (has_sha1()) {
-      if (FLAG_IS_DEFAULT(UseSHA1Intrinsics)) {
-        FLAG_SET_DEFAULT(UseSHA1Intrinsics, true);
-      }
-    } else if (UseSHA1Intrinsics) {
-      warning("SHA1 instruction is not available on this CPU.");
-      FLAG_SET_DEFAULT(UseSHA1Intrinsics, false);
+  }
+
+  if (UseSHA && has_sha256()) {
+    if (FLAG_IS_DEFAULT(UseSHA256Intrinsics)) {
+      FLAG_SET_DEFAULT(UseSHA256Intrinsics, true);
     }
-    if (has_sha256()) {
-      if (FLAG_IS_DEFAULT(UseSHA256Intrinsics)) {
-        FLAG_SET_DEFAULT(UseSHA256Intrinsics, true);
-      }
-    } else if (UseSHA256Intrinsics) {
-      warning("SHA256 instruction (for SHA-224 and SHA-256) is not available on this CPU.");
-      FLAG_SET_DEFAULT(UseSHA256Intrinsics, false);
-    }
+  } else if (UseSHA256Intrinsics) {
+    warning("Intrinsics for SHA-224 and SHA-256 crypto hash functions not available on this CPU.");
+    FLAG_SET_DEFAULT(UseSHA256Intrinsics, false);
+  }
 
-    if (has_sha512()) {
-      if (FLAG_IS_DEFAULT(UseSHA512Intrinsics)) {
-        FLAG_SET_DEFAULT(UseSHA512Intrinsics, true);
-      }
-    } else if (UseSHA512Intrinsics) {
-      warning("SHA512 instruction (for SHA-384 and SHA-512) is not available on this CPU.");
-      FLAG_SET_DEFAULT(UseSHA512Intrinsics, false);
+  if (UseSHA && has_sha512()) {
+    if (FLAG_IS_DEFAULT(UseSHA512Intrinsics)) {
+      FLAG_SET_DEFAULT(UseSHA512Intrinsics, true);
     }
-    if (!(UseSHA1Intrinsics || UseSHA256Intrinsics || UseSHA512Intrinsics)) {
-      FLAG_SET_DEFAULT(UseSHA, false);
-    }
+  } else if (UseSHA512Intrinsics) {
+    warning("Intrinsics for SHA-384 and SHA-512 crypto hash functions not available on this CPU.");
+    FLAG_SET_DEFAULT(UseSHA512Intrinsics, false);
+  }
+
+  if (!(UseSHA1Intrinsics || UseSHA256Intrinsics || UseSHA512Intrinsics)) {
+    FLAG_SET_DEFAULT(UseSHA, false);
   }
 
   // SPARC T4 and above should have support for CRC32C instruction
--- a/hotspot/src/cpu/sparc/vm/vtableStubs_sparc.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/sparc/vm/vtableStubs_sparc.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -110,7 +110,7 @@
   masm->flush();
 
   if (PrintMiscellaneous && (WizardMode || Verbose)) {
-    tty->print_cr("vtable #%d at "PTR_FORMAT"[%d] left over: %d",
+    tty->print_cr("vtable #%d at " PTR_FORMAT "[%d] left over: %d",
                   vtable_index, p2i(s->entry_point()),
                   (int)(s->code_end() - s->entry_point()),
                   (int)(s->code_end() - __ pc()));
@@ -205,7 +205,7 @@
   masm->flush();
 
   if (PrintMiscellaneous && (WizardMode || Verbose)) {
-    tty->print_cr("itable #%d at "PTR_FORMAT"[%d] left over: %d",
+    tty->print_cr("itable #%d at " PTR_FORMAT "[%d] left over: %d",
                   itable_index, p2i(s->entry_point()),
                   (int)(s->code_end() - s->entry_point()),
                   (int)(s->code_end() - __ pc()));
--- a/hotspot/src/cpu/x86/vm/globalDefinitions_x86.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/globalDefinitions_x86.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -27,12 +27,6 @@
 
 const int StackAlignmentInBytes  = 16;
 
-// Indicates whether the C calling conventions require that
-// 32-bit integer argument values are properly extended to 64 bits.
-// If set, SharedRuntime::c_calling_convention() must adapt
-// signatures accordingly.
-const bool CCallingConventionRequiresIntsAsLongs = false;
-
 #define SUPPORTS_NATIVE_CX8
 
 // The expected size in bytes of a cache line, used to pad data structures.
--- a/hotspot/src/cpu/x86/vm/macroAssembler_x86.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/macroAssembler_x86.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -5152,7 +5152,7 @@
       {
         ResourceMark rm;
         stringStream ss;
-        ss.print("DelayedValue="INTPTR_FORMAT, delayed_value_addr[1]);
+        ss.print("DelayedValue=" INTPTR_FORMAT, delayed_value_addr[1]);
         buf = code_string(ss.as_string());
       }
       jcc(Assembler::notZero, L);
--- a/hotspot/src/cpu/x86/vm/methodHandles_x86.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/methodHandles_x86.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -484,7 +484,7 @@
   bool has_mh = (strstr(adaptername, "/static") == NULL &&
                  strstr(adaptername, "linkTo") == NULL);    // static linkers don't have MH
   const char* mh_reg_name = has_mh ? "rcx_mh" : "rcx";
-  tty->print_cr("MH %s %s="PTR_FORMAT" sp="PTR_FORMAT,
+  tty->print_cr("MH %s %s=" PTR_FORMAT " sp=" PTR_FORMAT,
                 adaptername, mh_reg_name,
                 (void *)mh, entry_sp);
 
--- a/hotspot/src/cpu/x86/vm/sharedRuntime_x86_64.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/sharedRuntime_x86_64.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -23,6 +23,9 @@
  */
 
 #include "precompiled.hpp"
+#ifndef _WINDOWS
+#include "alloca.h"
+#endif
 #include "asm/macroAssembler.hpp"
 #include "asm/macroAssembler.inline.hpp"
 #include "code/debugInfoRec.hpp"
@@ -3511,6 +3514,250 @@
 }
 
 
+//------------------------------Montgomery multiplication------------------------
+//
+
+#ifndef _WINDOWS
+
+#define ASM_SUBTRACT
+
+#ifdef ASM_SUBTRACT
+// Subtract 0:b from carry:a.  Return carry.
+static unsigned long
+sub(unsigned long a[], unsigned long b[], unsigned long carry, long len) {
+  long i = 0, cnt = len;
+  unsigned long tmp;
+  asm volatile("clc; "
+               "0: ; "
+               "mov (%[b], %[i], 8), %[tmp]; "
+               "sbb %[tmp], (%[a], %[i], 8); "
+               "inc %[i]; dec %[cnt]; "
+               "jne 0b; "
+               "mov %[carry], %[tmp]; sbb $0, %[tmp]; "
+               : [i]"+r"(i), [cnt]"+r"(cnt), [tmp]"=&r"(tmp)
+               : [a]"r"(a), [b]"r"(b), [carry]"r"(carry)
+               : "memory");
+  return tmp;
+}
+#else // ASM_SUBTRACT
+typedef int __attribute__((mode(TI))) int128;
+
+// Subtract 0:b from carry:a.  Return carry.
+static unsigned long
+sub(unsigned long a[], unsigned long b[], unsigned long carry, int len) {
+  int128 tmp = 0;
+  int i;
+  for (i = 0; i < len; i++) {
+    tmp += a[i];
+    tmp -= b[i];
+    a[i] = tmp;
+    tmp >>= 64;
+    assert(-1 <= tmp && tmp <= 0, "invariant");
+  }
+  return tmp + carry;
+}
+#endif // ! ASM_SUBTRACT
+
+// Multiply (unsigned) Long A by Long B, accumulating the double-
+// length result into the accumulator formed of T0, T1, and T2.
+#define MACC(A, B, T0, T1, T2)                                  \
+do {                                                            \
+  unsigned long hi, lo;                                         \
+  __asm__ ("mul %5; add %%rax, %2; adc %%rdx, %3; adc $0, %4"   \
+           : "=&d"(hi), "=a"(lo), "+r"(T0), "+r"(T1), "+g"(T2)  \
+           : "r"(A), "a"(B) : "cc");                            \
+ } while(0)
+
+// As above, but add twice the double-length result into the
+// accumulator.
+#define MACC2(A, B, T0, T1, T2)                                 \
+do {                                                            \
+  unsigned long hi, lo;                                         \
+  __asm__ ("mul %5; add %%rax, %2; adc %%rdx, %3; adc $0, %4; " \
+           "add %%rax, %2; adc %%rdx, %3; adc $0, %4"           \
+           : "=&d"(hi), "=a"(lo), "+r"(T0), "+r"(T1), "+g"(T2)  \
+           : "r"(A), "a"(B) : "cc");                            \
+ } while(0)
+
+// Fast Montgomery multiplication.  The derivation of the algorithm is
+// in  A Cryptographic Library for the Motorola DSP56000,
+// Dusse and Kaliski, Proc. EUROCRYPT 90, pp. 230-237.
+
+static void __attribute__((noinline))
+montgomery_multiply(unsigned long a[], unsigned long b[], unsigned long n[],
+                    unsigned long m[], unsigned long inv, int len) {
+  unsigned long t0 = 0, t1 = 0, t2 = 0; // Triple-precision accumulator
+  int i;
+
+  assert(inv * n[0] == -1UL, "broken inverse in Montgomery multiply");
+
+  for (i = 0; i < len; i++) {
+    int j;
+    for (j = 0; j < i; j++) {
+      MACC(a[j], b[i-j], t0, t1, t2);
+      MACC(m[j], n[i-j], t0, t1, t2);
+    }
+    MACC(a[i], b[0], t0, t1, t2);
+    m[i] = t0 * inv;
+    MACC(m[i], n[0], t0, t1, t2);
+
+    assert(t0 == 0, "broken Montgomery multiply");
+
+    t0 = t1; t1 = t2; t2 = 0;
+  }
+
+  for (i = len; i < 2*len; i++) {
+    int j;
+    for (j = i-len+1; j < len; j++) {
+      MACC(a[j], b[i-j], t0, t1, t2);
+      MACC(m[j], n[i-j], t0, t1, t2);
+    }
+    m[i-len] = t0;
+    t0 = t1; t1 = t2; t2 = 0;
+  }
+
+  while (t0)
+    t0 = sub(m, n, t0, len);
+}
+
+// Fast Montgomery squaring.  This uses asymptotically 25% fewer
+// multiplies so it should be up to 25% faster than Montgomery
+// multiplication.  However, its loop control is more complex and it
+// may actually run slower on some machines.
+
+static void __attribute__((noinline))
+montgomery_square(unsigned long a[], unsigned long n[],
+                  unsigned long m[], unsigned long inv, int len) {
+  unsigned long t0 = 0, t1 = 0, t2 = 0; // Triple-precision accumulator
+  int i;
+
+  assert(inv * n[0] == -1UL, "broken inverse in Montgomery multiply");
+
+  for (i = 0; i < len; i++) {
+    int j;
+    int end = (i+1)/2;
+    for (j = 0; j < end; j++) {
+      MACC2(a[j], a[i-j], t0, t1, t2);
+      MACC(m[j], n[i-j], t0, t1, t2);
+    }
+    if ((i & 1) == 0) {
+      MACC(a[j], a[j], t0, t1, t2);
+    }
+    for (; j < i; j++) {
+      MACC(m[j], n[i-j], t0, t1, t2);
+    }
+    m[i] = t0 * inv;
+    MACC(m[i], n[0], t0, t1, t2);
+
+    assert(t0 == 0, "broken Montgomery square");
+
+    t0 = t1; t1 = t2; t2 = 0;
+  }
+
+  for (i = len; i < 2*len; i++) {
+    int start = i-len+1;
+    int end = start + (len - start)/2;
+    int j;
+    for (j = start; j < end; j++) {
+      MACC2(a[j], a[i-j], t0, t1, t2);
+      MACC(m[j], n[i-j], t0, t1, t2);
+    }
+    if ((i & 1) == 0) {
+      MACC(a[j], a[j], t0, t1, t2);
+    }
+    for (; j < len; j++) {
+      MACC(m[j], n[i-j], t0, t1, t2);
+    }
+    m[i-len] = t0;
+    t0 = t1; t1 = t2; t2 = 0;
+  }
+
+  while (t0)
+    t0 = sub(m, n, t0, len);
+}
+
+// Swap words in a longword.
+static unsigned long swap(unsigned long x) {
+  return (x << 32) | (x >> 32);
+}
+
+// Copy len longwords from s to d, word-swapping as we go.  The
+// destination array is reversed.
+static void reverse_words(unsigned long *s, unsigned long *d, int len) {
+  d += len;
+  while(len-- > 0) {
+    d--;
+    *d = swap(*s);
+    s++;
+  }
+}
+
+// The threshold at which squaring is advantageous was determined
+// experimentally on an i7-3930K (Ivy Bridge) CPU @ 3.5GHz.
+#define MONTGOMERY_SQUARING_THRESHOLD 64
+
+void SharedRuntime::montgomery_multiply(jint *a_ints, jint *b_ints, jint *n_ints,
+                                        jint len, jlong inv,
+                                        jint *m_ints) {
+  assert(len % 2 == 0, "array length in montgomery_multiply must be even");
+  int longwords = len/2;
+
+  // Make very sure we don't use so much space that the stack might
+  // overflow.  512 jints corresponds to an 16384-bit integer and
+  // will use here a total of 8k bytes of stack space.
+  int total_allocation = longwords * sizeof (unsigned long) * 4;
+  guarantee(total_allocation <= 8192, "must be");
+  unsigned long *scratch = (unsigned long *)alloca(total_allocation);
+
+  // Local scratch arrays
+  unsigned long
+    *a = scratch + 0 * longwords,
+    *b = scratch + 1 * longwords,
+    *n = scratch + 2 * longwords,
+    *m = scratch + 3 * longwords;
+
+  reverse_words((unsigned long *)a_ints, a, longwords);
+  reverse_words((unsigned long *)b_ints, b, longwords);
+  reverse_words((unsigned long *)n_ints, n, longwords);
+
+  ::montgomery_multiply(a, b, n, m, (unsigned long)inv, longwords);
+
+  reverse_words(m, (unsigned long *)m_ints, longwords);
+}
+
+void SharedRuntime::montgomery_square(jint *a_ints, jint *n_ints,
+                                      jint len, jlong inv,
+                                      jint *m_ints) {
+  assert(len % 2 == 0, "array length in montgomery_square must be even");
+  int longwords = len/2;
+
+  // Make very sure we don't use so much space that the stack might
+  // overflow.  512 jints corresponds to an 16384-bit integer and
+  // will use here a total of 6k bytes of stack space.
+  int total_allocation = longwords * sizeof (unsigned long) * 3;
+  guarantee(total_allocation <= 8192, "must be");
+  unsigned long *scratch = (unsigned long *)alloca(total_allocation);
+
+  // Local scratch arrays
+  unsigned long
+    *a = scratch + 0 * longwords,
+    *n = scratch + 1 * longwords,
+    *m = scratch + 2 * longwords;
+
+  reverse_words((unsigned long *)a_ints, a, longwords);
+  reverse_words((unsigned long *)n_ints, n, longwords);
+
+  if (len >= MONTGOMERY_SQUARING_THRESHOLD) {
+    ::montgomery_square(a, n, m, (unsigned long)inv, longwords);
+  } else {
+    ::montgomery_multiply(a, a, n, m, (unsigned long)inv, longwords);
+  }
+
+  reverse_words(m, (unsigned long *)m_ints, longwords);
+}
+
+#endif // WINDOWS
+
 #ifdef COMPILER2
 // This is here instead of runtime_x86_64.cpp because it uses SimpleRuntimeFrame
 //
--- a/hotspot/src/cpu/x86/vm/stubGenerator_x86_64.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/stubGenerator_x86_64.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -4318,7 +4318,18 @@
     if (UseMulAddIntrinsic) {
       StubRoutines::_mulAdd = generate_mulAdd();
     }
-#endif
+
+#ifndef _WINDOWS
+    if (UseMontgomeryMultiplyIntrinsic) {
+      StubRoutines::_montgomeryMultiply
+        = CAST_FROM_FN_PTR(address, SharedRuntime::montgomery_multiply);
+    }
+    if (UseMontgomerySquareIntrinsic) {
+      StubRoutines::_montgomerySquare
+        = CAST_FROM_FN_PTR(address, SharedRuntime::montgomery_square);
+    }
+#endif // WINDOWS
+#endif // COMPILER2
   }
 
  public:
--- a/hotspot/src/cpu/x86/vm/vm_version_x86.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/vm_version_x86.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -692,10 +692,19 @@
     warning("SHA instructions are not available on this CPU");
     FLAG_SET_DEFAULT(UseSHA, false);
   }
-  if (UseSHA1Intrinsics || UseSHA256Intrinsics || UseSHA512Intrinsics) {
-    warning("SHA intrinsics are not available on this CPU");
+
+  if (UseSHA1Intrinsics) {
+    warning("Intrinsics for SHA-1 crypto hash functions not available on this CPU.");
     FLAG_SET_DEFAULT(UseSHA1Intrinsics, false);
+  }
+
+  if (UseSHA256Intrinsics) {
+    warning("Intrinsics for SHA-224 and SHA-256 crypto hash functions not available on this CPU.");
     FLAG_SET_DEFAULT(UseSHA256Intrinsics, false);
+  }
+
+  if (UseSHA512Intrinsics) {
+    warning("Intrinsics for SHA-384 and SHA-512 crypto hash functions not available on this CPU.");
     FLAG_SET_DEFAULT(UseSHA512Intrinsics, false);
   }
 
@@ -813,6 +822,12 @@
   if (FLAG_IS_DEFAULT(UseMulAddIntrinsic)) {
     UseMulAddIntrinsic = true;
   }
+  if (FLAG_IS_DEFAULT(UseMontgomeryMultiplyIntrinsic)) {
+    UseMontgomeryMultiplyIntrinsic = true;
+  }
+  if (FLAG_IS_DEFAULT(UseMontgomerySquareIntrinsic)) {
+    UseMontgomerySquareIntrinsic = true;
+  }
 #else
   if (UseMultiplyToLenIntrinsic) {
     if (!FLAG_IS_DEFAULT(UseMultiplyToLenIntrinsic)) {
@@ -820,6 +835,18 @@
     }
     FLAG_SET_DEFAULT(UseMultiplyToLenIntrinsic, false);
   }
+  if (UseMontgomeryMultiplyIntrinsic) {
+    if (!FLAG_IS_DEFAULT(UseMontgomeryMultiplyIntrinsic)) {
+      warning("montgomeryMultiply intrinsic is not available in 32-bit VM");
+    }
+    FLAG_SET_DEFAULT(UseMontgomeryMultiplyIntrinsic, false);
+  }
+  if (UseMontgomerySquareIntrinsic) {
+    if (!FLAG_IS_DEFAULT(UseMontgomerySquareIntrinsic)) {
+      warning("montgomerySquare intrinsic is not available in 32-bit VM");
+    }
+    FLAG_SET_DEFAULT(UseMontgomerySquareIntrinsic, false);
+  }
   if (UseSquareToLenIntrinsic) {
     if (!FLAG_IS_DEFAULT(UseSquareToLenIntrinsic)) {
       warning("squareToLen intrinsic is not available in 32-bit VM");
--- a/hotspot/src/cpu/x86/vm/vtableStubs_x86_32.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/vtableStubs_x86_32.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -117,7 +117,7 @@
   masm->flush();
 
   if (PrintMiscellaneous && (WizardMode || Verbose)) {
-    tty->print_cr("vtable #%d at "PTR_FORMAT"[%d] left over: %d",
+    tty->print_cr("vtable #%d at " PTR_FORMAT "[%d] left over: %d",
                   vtable_index, p2i(s->entry_point()),
                   (int)(s->code_end() - s->entry_point()),
                   (int)(s->code_end() - __ pc()));
@@ -198,7 +198,7 @@
   masm->flush();
 
   if (PrintMiscellaneous && (WizardMode || Verbose)) {
-    tty->print_cr("itable #%d at "PTR_FORMAT"[%d] left over: %d",
+    tty->print_cr("itable #%d at " PTR_FORMAT "[%d] left over: %d",
                   itable_index, p2i(s->entry_point()),
                   (int)(s->code_end() - s->entry_point()),
                   (int)(s->code_end() - __ pc()));
--- a/hotspot/src/cpu/x86/vm/vtableStubs_x86_64.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/vtableStubs_x86_64.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -112,7 +112,7 @@
   __ flush();
 
   if (PrintMiscellaneous && (WizardMode || Verbose)) {
-    tty->print_cr("vtable #%d at "PTR_FORMAT"[%d] left over: %d",
+    tty->print_cr("vtable #%d at " PTR_FORMAT "[%d] left over: %d",
                   vtable_index, s->entry_point(),
                   (int)(s->code_end() - s->entry_point()),
                   (int)(s->code_end() - __ pc()));
@@ -205,7 +205,7 @@
   __ flush();
 
   if (PrintMiscellaneous && (WizardMode || Verbose)) {
-    tty->print_cr("itable #%d at "PTR_FORMAT"[%d] left over: %d",
+    tty->print_cr("itable #%d at " PTR_FORMAT "[%d] left over: %d",
                   itable_index, s->entry_point(),
                   (int)(s->code_end() - s->entry_point()),
                   (int)(s->code_end() - __ pc()));
--- a/hotspot/src/cpu/zero/vm/globalDefinitions_zero.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/cpu/zero/vm/globalDefinitions_zero.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1,6 +1,6 @@
 /*
- * Copyright (c) 1997, 2010, Oracle and/or its affiliates. All rights reserved.
- * Copyright 2009 Red Hat, Inc.
+ * Copyright (c) 1997, 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright 2009, 2015, Red Hat, Inc.
  * 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,10 +28,4 @@
 
 #include <ffi.h>
 
-// Indicates whether the C calling conventions require that
-// 32-bit integer argument values are properly extended to 64 bits.
-// If set, SharedRuntime::c_calling_convention() must adapt
-// signatures accordingly.
-const bool CCallingConventionRequiresIntsAsLongs = false;
-
 #endif // CPU_ZERO_VM_GLOBALDEFINITIONS_ZERO_HPP
--- a/hotspot/src/os/bsd/vm/jsig.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/os/bsd/vm/jsig.c	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2001, 2010, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2001, 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
@@ -42,6 +42,7 @@
 
 static struct sigaction sact[MAXSIGNUM]; /* saved signal handlers */
 static unsigned int jvmsigs = 0; /* signals used by jvm */
+static __thread bool reentry = false; /* prevent reentry deadlock (per-thread) */
 
 /* used to synchronize the installation of signal handlers */
 static pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
@@ -76,6 +77,8 @@
 
 static sa_handler_t call_os_signal(int sig, sa_handler_t disp,
                                    bool is_sigset) {
+  sa_handler_t res;
+
   if (os_signal == NULL) {
     if (!is_sigset) {
       os_signal = (signal_t)dlsym(RTLD_NEXT, "signal");
@@ -87,7 +90,10 @@
       exit(0);
     }
   }
-  return (*os_signal)(sig, disp);
+  reentry = true;
+  res = (*os_signal)(sig, disp);
+  reentry = false;
+  return res;
 }
 
 static void save_signal_handler(int sig, sa_handler_t disp) {
@@ -161,6 +167,10 @@
   bool sigused;
   struct sigaction oldAct;
 
+  if (reentry) {
+    return call_os_sigaction(sig, act, oact);
+  }
+
   signal_lock();
 
   sigused = (MASK(sig) & jvmsigs) != 0;
--- a/hotspot/src/os/bsd/vm/os_bsd.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/os/bsd/vm/os_bsd.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -59,6 +59,7 @@
 #include "runtime/thread.inline.hpp"
 #include "runtime/threadCritical.hpp"
 #include "runtime/timer.hpp"
+#include "semaphore_bsd.hpp"
 #include "services/attachListener.hpp"
 #include "services/memTracker.hpp"
 #include "services/runtimeService.hpp"
@@ -1940,47 +1941,54 @@
   #define SEM_DESTROY(sem)        sem_destroy(&sem)
 #endif
 
-class Semaphore : public StackObj {
- public:
-  Semaphore();
-  ~Semaphore();
-  void signal();
-  void wait();
-  bool trywait();
-  bool timedwait(unsigned int sec, int nsec);
- private:
-  jlong currenttime() const;
-  os_semaphore_t _semaphore;
-};
-
-Semaphore::Semaphore() : _semaphore(0) {
-  SEM_INIT(_semaphore, 0);
+#ifdef __APPLE__
+// OS X doesn't support unamed POSIX semaphores, so the implementation in os_posix.cpp can't be used.
+
+static const char* sem_init_strerror(kern_return_t value) {
+  switch (value) {
+    case KERN_INVALID_ARGUMENT:  return "Invalid argument";
+    case KERN_RESOURCE_SHORTAGE: return "Resource shortage";
+    default:                     return "Unknown";
+  }
 }
 
-Semaphore::~Semaphore() {
+OSXSemaphore::OSXSemaphore(uint value) {
+  kern_return_t ret = SEM_INIT(_semaphore, value);
+
+  guarantee(ret == KERN_SUCCESS, err_msg("Failed to create semaphore: %s", sem_init_strerror(ret)));
+}
+
+OSXSemaphore::~OSXSemaphore() {
   SEM_DESTROY(_semaphore);
 }
 
-void Semaphore::signal() {
-  SEM_POST(_semaphore);
+void OSXSemaphore::signal(uint count) {
+  for (uint i = 0; i < count; i++) {
+    kern_return_t ret = SEM_POST(_semaphore);
+
+    assert(ret == KERN_SUCCESS, "Failed to signal semaphore");
+  }
 }
 
-void Semaphore::wait() {
-  SEM_WAIT(_semaphore);
+void OSXSemaphore::wait() {
+  kern_return_t ret;
+  while ((ret = SEM_WAIT(_semaphore)) == KERN_ABORTED) {
+    // Semaphore was interrupted. Retry.
+  }
+  assert(ret == KERN_SUCCESS, "Failed to wait on semaphore");
 }
 
-jlong Semaphore::currenttime() const {
+jlong OSXSemaphore::currenttime() {
   struct timeval tv;
   gettimeofday(&tv, NULL);
   return (tv.tv_sec * NANOSECS_PER_SEC) + (tv.tv_usec * 1000);
 }
 
-#ifdef __APPLE__
-bool Semaphore::trywait() {
+bool OSXSemaphore::trywait() {
   return timedwait(0, 0);
 }
 
-bool Semaphore::timedwait(unsigned int sec, int nsec) {
+bool OSXSemaphore::timedwait(unsigned int sec, int nsec) {
   kern_return_t kr = KERN_ABORTED;
   mach_timespec_t waitspec;
   waitspec.tv_sec = sec;
@@ -2011,33 +2019,24 @@
 }
 
 #else
-
-bool Semaphore::trywait() {
-  return sem_trywait(&_semaphore) == 0;
-}
-
-bool Semaphore::timedwait(unsigned int sec, int nsec) {
+// Use POSIX implementation of semaphores.
+
+struct timespec PosixSemaphore::create_timespec(unsigned int sec, int nsec) {
   struct timespec ts;
   unpackTime(&ts, false, (sec * NANOSECS_PER_SEC) + nsec);
 
-  while (1) {
-    int result = sem_timedwait(&_semaphore, &ts);
-    if (result == 0) {
-      return true;
-    } else if (errno == EINTR) {
-      continue;
-    } else if (errno == ETIMEDOUT) {
-      return false;
-    } else {
-      return false;
-    }
-  }
+  return ts;
 }
 
 #endif // __APPLE__
 
 static os_semaphore_t sig_sem;
-static Semaphore sr_semaphore;
+
+#ifdef __APPLE__
+static OSXSemaphore sr_semaphore;
+#else
+static PosixSemaphore sr_semaphore;
+#endif
 
 void os::signal_init_pd() {
   // Initialize signal structures
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/os/bsd/vm/semaphore_bsd.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,63 @@
+/*
+ * 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.
+ *
+ */
+
+#ifndef OS_BSD_VM_SEMAPHORE_BSD_HPP
+#define OS_BSD_VM_SEMAPHORE_BSD_HPP
+
+#ifndef __APPLE__
+// Use POSIX semaphores.
+# include "semaphore_posix.hpp"
+
+#else
+// OS X doesn't support unamed POSIX semaphores, so the implementation in os_posix.cpp can't be used.
+# include "memory/allocation.hpp"
+# include <mach/semaphore.h>
+
+class OSXSemaphore : public CHeapObj<mtInternal>{
+  semaphore_t _semaphore;
+
+  // Prevent copying and assignment.
+  OSXSemaphore(const OSXSemaphore&);
+  OSXSemaphore& operator=(const OSXSemaphore&);
+
+ public:
+  OSXSemaphore(uint value = 0);
+  ~OSXSemaphore();
+
+  void signal(uint count = 1);
+
+  void wait();
+
+  bool trywait();
+  bool timedwait(unsigned int sec, int nsec);
+
+ private:
+  static jlong currenttime();
+};
+
+typedef OSXSemaphore SemaphoreImpl;
+
+#endif // __APPLE__
+
+#endif // OS_BSD_VM_SEMAPHORE_BSD_HPP
--- a/hotspot/src/os/linux/vm/os_linux.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/os/linux/vm/os_linux.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -60,6 +60,7 @@
 #include "runtime/thread.inline.hpp"
 #include "runtime/threadCritical.hpp"
 #include "runtime/timer.hpp"
+#include "semaphore_posix.hpp"
 #include "services/attachListener.hpp"
 #include "services/memTracker.hpp"
 #include "services/runtimeService.hpp"
@@ -2315,40 +2316,7 @@
   return CAST_FROM_FN_PTR(void*, UserHandler);
 }
 
-class Semaphore : public StackObj {
- public:
-  Semaphore();
-  ~Semaphore();
-  void signal();
-  void wait();
-  bool trywait();
-  bool timedwait(unsigned int sec, int nsec);
- private:
-  sem_t _semaphore;
-};
-
-Semaphore::Semaphore() {
-  sem_init(&_semaphore, 0, 0);
-}
-
-Semaphore::~Semaphore() {
-  sem_destroy(&_semaphore);
-}
-
-void Semaphore::signal() {
-  sem_post(&_semaphore);
-}
-
-void Semaphore::wait() {
-  sem_wait(&_semaphore);
-}
-
-bool Semaphore::trywait() {
-  return sem_trywait(&_semaphore) == 0;
-}
-
-bool Semaphore::timedwait(unsigned int sec, int nsec) {
-
+struct timespec PosixSemaphore::create_timespec(unsigned int sec, int nsec) {
   struct timespec ts;
   // Semaphore's are always associated with CLOCK_REALTIME
   os::Linux::clock_gettime(CLOCK_REALTIME, &ts);
@@ -2365,18 +2333,7 @@
     }
   }
 
-  while (1) {
-    int result = sem_timedwait(&_semaphore, &ts);
-    if (result == 0) {
-      return true;
-    } else if (errno == EINTR) {
-      continue;
-    } else if (errno == ETIMEDOUT) {
-      return false;
-    } else {
-      return false;
-    }
-  }
+  return ts;
 }
 
 extern "C" {
@@ -2416,7 +2373,7 @@
 
 // Linux(POSIX) specific hand shaking semaphore.
 static sem_t sig_sem;
-static Semaphore sr_semaphore;
+static PosixSemaphore sr_semaphore;
 
 void os::signal_init_pd() {
   // Initialize signal structures
--- a/hotspot/src/os/posix/vm/os_posix.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/os/posix/vm/os_posix.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -24,6 +24,7 @@
 
 #include "utilities/globalDefinitions.hpp"
 #include "prims/jvm.h"
+#include "semaphore_posix.hpp"
 #include "runtime/frame.inline.hpp"
 #include "runtime/interfaceSupport.hpp"
 #include "runtime/os.hpp"
@@ -34,6 +35,7 @@
 #include <sys/resource.h>
 #include <sys/utsname.h>
 #include <pthread.h>
+#include <semaphore.h>
 #include <signal.h>
 
 PRAGMA_FORMAT_MUTE_WARNINGS_FOR_GCC
@@ -1015,3 +1017,73 @@
     }
   }
 }
+
+#define check_with_errno(check_type, cond, msg)                                      \
+  do {                                                                               \
+    int err = errno;                                                                 \
+    check_type(cond, err_msg("%s; error='%s' (errno=%d)", msg, strerror(err), err)); \
+} while (false)
+
+#define assert_with_errno(cond, msg)    check_with_errno(assert, cond, msg)
+#define guarantee_with_errno(cond, msg) check_with_errno(guarantee, cond, msg)
+
+// POSIX unamed semaphores are not supported on OS X.
+#ifndef __APPLE__
+
+PosixSemaphore::PosixSemaphore(uint value) {
+  int ret = sem_init(&_semaphore, 0, value);
+
+  guarantee_with_errno(ret == 0, "Failed to initialize semaphore");
+}
+
+PosixSemaphore::~PosixSemaphore() {
+  sem_destroy(&_semaphore);
+}
+
+void PosixSemaphore::signal(uint count) {
+  for (uint i = 0; i < count; i++) {
+    int ret = sem_post(&_semaphore);
+
+    assert_with_errno(ret == 0, "sem_post failed");
+  }
+}
+
+void PosixSemaphore::wait() {
+  int ret;
+
+  do {
+    ret = sem_wait(&_semaphore);
+  } while (ret != 0 && errno == EINTR);
+
+  assert_with_errno(ret == 0, "sem_wait failed");
+}
+
+bool PosixSemaphore::trywait() {
+  int ret;
+
+  do {
+    ret = sem_trywait(&_semaphore);
+  } while (ret != 0 && errno == EINTR);
+
+  assert_with_errno(ret == 0 || errno == EAGAIN, "trywait failed");
+
+  return ret == 0;
+}
+
+bool PosixSemaphore::timedwait(const struct timespec ts) {
+  while (true) {
+    int result = sem_timedwait(&_semaphore, &ts);
+    if (result == 0) {
+      return true;
+    } else if (errno == EINTR) {
+      continue;
+    } else if (errno == ETIMEDOUT) {
+      return false;
+    } else {
+      assert_with_errno(false, "timedwait failed");
+      return false;
+    }
+  }
+}
+
+#endif // __APPLE__
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/os/posix/vm/semaphore_posix.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,61 @@
+/*
+ * 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.
+ *
+ */
+
+#ifndef OS_POSIX_VM_SEMAPHORE_POSIX_HPP
+#define OS_POSIX_VM_SEMAPHORE_POSIX_HPP
+
+#include "memory/allocation.hpp"
+
+#include <semaphore.h>
+
+class PosixSemaphore : public CHeapObj<mtInternal> {
+  sem_t _semaphore;
+
+  // Prevent copying and assignment.
+  PosixSemaphore(const PosixSemaphore&);
+  PosixSemaphore& operator=(const PosixSemaphore&);
+
+ public:
+  PosixSemaphore(uint value = 0);
+  ~PosixSemaphore();
+
+  void signal(uint count = 1);
+
+  void wait();
+
+  bool trywait();
+  bool timedwait(unsigned int sec, int nsec) {
+    return timedwait(create_timespec(sec, nsec));
+  }
+
+ private:
+  bool timedwait(struct timespec ts);
+
+  // OS specific implementation to create a timespec suitable for semaphores.
+  struct timespec create_timespec(unsigned int set, int nsec);
+};
+
+typedef PosixSemaphore SemaphoreImpl;
+
+#endif // OS_POSIX_VM_SEMAPHORE_POSIX_HPP
--- a/hotspot/src/os/solaris/vm/os_solaris.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/os/solaris/vm/os_solaris.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -60,6 +60,7 @@
 #include "runtime/threadCritical.hpp"
 #include "runtime/timer.hpp"
 #include "runtime/vm_version.hpp"
+#include "semaphore_posix.hpp"
 #include "services/attachListener.hpp"
 #include "services/memTracker.hpp"
 #include "services/runtimeService.hpp"
@@ -2263,55 +2264,11 @@
   return CAST_FROM_FN_PTR(void*, UserHandler);
 }
 
-class Semaphore : public StackObj {
- public:
-  Semaphore();
-  ~Semaphore();
-  void signal();
-  void wait();
-  bool trywait();
-  bool timedwait(unsigned int sec, int nsec);
- private:
-  sema_t _semaphore;
-};
-
-
-Semaphore::Semaphore() {
-  sema_init(&_semaphore, 0, NULL, NULL);
-}
-
-Semaphore::~Semaphore() {
-  sema_destroy(&_semaphore);
-}
-
-void Semaphore::signal() {
-  sema_post(&_semaphore);
-}
-
-void Semaphore::wait() {
-  sema_wait(&_semaphore);
-}
-
-bool Semaphore::trywait() {
-  return sema_trywait(&_semaphore) == 0;
-}
-
-bool Semaphore::timedwait(unsigned int sec, int nsec) {
+struct timespec PosixSemaphore::create_timespec(unsigned int sec, int nsec) {
   struct timespec ts;
   unpackTime(&ts, false, (sec * NANOSECS_PER_SEC) + nsec);
 
-  while (1) {
-    int result = sema_timedwait(&_semaphore, &ts);
-    if (result == 0) {
-      return true;
-    } else if (errno == EINTR) {
-      continue;
-    } else if (errno == ETIME) {
-      return false;
-    } else {
-      return false;
-    }
-  }
+  return ts;
 }
 
 extern "C" {
@@ -3711,7 +3668,7 @@
   osthread->set_ucontext(context);
 }
 
-static Semaphore sr_semaphore;
+static PosixSemaphore sr_semaphore;
 
 void os::Solaris::SR_handler(Thread* thread, ucontext_t* uc) {
   // Save and restore errno to avoid confusing native code with EINTR
--- a/hotspot/src/os/windows/vm/os_windows.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/os/windows/vm/os_windows.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -63,6 +63,7 @@
 #include "runtime/threadCritical.hpp"
 #include "runtime/timer.hpp"
 #include "runtime/vm_version.hpp"
+#include "semaphore_windows.hpp"
 #include "services/attachListener.hpp"
 #include "services/memTracker.hpp"
 #include "services/runtimeService.hpp"
@@ -1901,6 +1902,30 @@
   return (int)error;
 }
 
+WindowsSemaphore::WindowsSemaphore(uint value) {
+  _semaphore = ::CreateSemaphore(NULL, value, LONG_MAX, NULL);
+
+  guarantee(_semaphore != NULL, err_msg("CreateSemaphore failed with error code: %lu", GetLastError()));
+}
+
+WindowsSemaphore::~WindowsSemaphore() {
+  ::CloseHandle(_semaphore);
+}
+
+void WindowsSemaphore::signal(uint count) {
+  if (count > 0) {
+    BOOL ret = ::ReleaseSemaphore(_semaphore, count, NULL);
+
+    assert(ret != 0, err_msg("ReleaseSemaphore failed with error code: %lu", GetLastError()));
+  }
+}
+
+void WindowsSemaphore::wait() {
+  DWORD ret = ::WaitForSingleObject(_semaphore, INFINITE);
+  assert(ret != WAIT_FAILED,   err_msg("WaitForSingleObject failed with error code: %lu", GetLastError()));
+  assert(ret == WAIT_OBJECT_0, err_msg("WaitForSingleObject failed with return value: %lu", ret));
+}
+
 // sun.misc.Signal
 // NOTE that this is a workaround for an apparent kernel bug where if
 // a signal handler for SIGBREAK is installed then that signal handler
@@ -5890,7 +5915,7 @@
   char* result = os::reserve_memory_special(large_allocation_size, os::large_page_size(), NULL, false);
   if (result == NULL) {
     if (VerboseInternalVMTests) {
-      gclog_or_tty->print("Failed to allocate control block with size "SIZE_FORMAT". Skipping remainder of test.",
+      gclog_or_tty->print("Failed to allocate control block with size " SIZE_FORMAT ". Skipping remainder of test.",
                           large_allocation_size);
     }
   } else {
@@ -5903,7 +5928,7 @@
     char* actual_location = os::reserve_memory_special(expected_allocation_size, os::large_page_size(), expected_location, false);
     if (actual_location == NULL) {
       if (VerboseInternalVMTests) {
-        gclog_or_tty->print("Failed to allocate any memory at "PTR_FORMAT" size "SIZE_FORMAT". Skipping remainder of test.",
+        gclog_or_tty->print("Failed to allocate any memory at " PTR_FORMAT " size " SIZE_FORMAT ". Skipping remainder of test.",
                             expected_location, large_allocation_size);
       }
     } else {
@@ -5911,7 +5936,7 @@
       os::release_memory_special(actual_location, expected_allocation_size);
       // only now check, after releasing any memory to avoid any leaks.
       assert(actual_location == expected_location,
-             err_msg("Failed to allocate memory at requested location "PTR_FORMAT" of size "SIZE_FORMAT", is "PTR_FORMAT" instead",
+             err_msg("Failed to allocate memory at requested location " PTR_FORMAT " of size " SIZE_FORMAT ", is " PTR_FORMAT " instead",
              expected_location, expected_allocation_size, actual_location));
     }
   }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/os/windows/vm/semaphore_windows.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,50 @@
+/*
+ * 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.
+ *
+ */
+
+#ifndef OS_WINDOWS_VM_SEMAPHORE_WINDOWS_HPP
+#define OS_WINDOWS_VM_SEMAPHORE_WINDOWS_HPP
+
+#include "memory/allocation.hpp"
+
+#include <windef.h>
+
+class WindowsSemaphore : public CHeapObj<mtInternal> {
+  HANDLE _semaphore;
+
+  // Prevent copying and assignment.
+  WindowsSemaphore(const WindowsSemaphore&);
+  WindowsSemaphore& operator=(const WindowsSemaphore&);
+
+ public:
+  WindowsSemaphore(uint value = 0);
+  ~WindowsSemaphore();
+
+  void signal(uint count = 1);
+
+  void wait();
+};
+
+typedef WindowsSemaphore SemaphoreImpl;
+
+#endif // OS_WINDOWS_VM_SEMAPHORE_WINDOWS_HPP
--- a/hotspot/src/os_cpu/solaris_sparc/vm/vm_version_solaris_sparc.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/os_cpu/solaris_sparc/vm/vm_version_solaris_sparc.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -191,7 +191,7 @@
     return CPUVisitor::visit(nodeh, state);
   }
 
-  PICL(bool is_fujitsu) : _L1_data_cache_line_size(0), _L2_data_cache_line_size(0), _dl_handle(NULL) {
+  PICL(bool is_fujitsu, bool is_sun4v) : _L1_data_cache_line_size(0), _L2_data_cache_line_size(0), _dl_handle(NULL) {
     if (!open_library()) {
       return;
     }
@@ -203,7 +203,7 @@
         if (is_fujitsu) {
           cpu_class = "core";
         }
-        CPUVisitor cpu_visitor(this, os::processor_count());
+        CPUVisitor cpu_visitor(this, (is_sun4v && !is_fujitsu) ? 1 : os::processor_count());
         _picl_walk_tree_by_class(rooth, cpu_class, &cpu_visitor, PICL_visit_cpu_helper);
         if (cpu_visitor.l1_visitor()->is_assigned()) { // Is there a value?
           _L1_data_cache_line_size = cpu_visitor.l1_visitor()->value();
@@ -447,7 +447,7 @@
   }
 
   // Figure out cache line sizes using PICL
-  PICL picl((features & sparc64_family_m) != 0);
+  PICL picl((features & sparc64_family_m) != 0, (features & sun4v_m) != 0);
   _L1_data_cache_line_size = picl.L1_data_cache_line_size();
   _L2_data_cache_line_size = picl.L2_data_cache_line_size();
 
--- a/hotspot/src/share/tools/hsdis/Makefile	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/tools/hsdis/Makefile	Wed Jul 05 20:42:36 2017 +0200
@@ -70,7 +70,8 @@
 else   #linux
 CPU             = $(shell uname -m)
 ARCH1=$(CPU:x86_64=amd64)
-ARCH=$(ARCH1:i686=i386)
+ARCH2=$(ARCH1:i686=i386)
+ARCH=$(ARCH2:ppc64le=ppc64)
 ifdef LP64
 CFLAGS/sparcv9	+= -m64
 CFLAGS/amd64	+= -m64
--- a/hotspot/src/share/vm/asm/codeBuffer.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/asm/codeBuffer.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1093,9 +1093,11 @@
 
 void CodeStrings::assign(CodeStrings& other) {
   other.check_valid();
-  // Cannot do following because CodeStrings constructor is not alway run!
   assert(is_null(), "Cannot assign onto non-empty CodeStrings");
   _strings = other._strings;
+#ifdef ASSERT
+  _defunct = false;
+#endif
   other.set_null_and_invalidate();
 }
 
@@ -1115,13 +1117,15 @@
   }
 }
 
+const char* CodeStrings::_prefix = " ;; ";  // default: can be changed via set_prefix
+
 void CodeStrings::print_block_comment(outputStream* stream, intptr_t offset) const {
     check_valid();
     if (_strings != NULL) {
     CodeString* c = find(offset);
     while (c && c->offset() == offset) {
       stream->bol();
-      stream->print("  ;; ");
+      stream->print("%s", _prefix);
       stream->print_cr("%s", c->string());
       c = c->next_comment();
     }
--- a/hotspot/src/share/vm/asm/codeBuffer.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/asm/codeBuffer.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 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
@@ -249,6 +249,7 @@
   // Becomes true after copy-out, forbids further use.
   bool _defunct; // Zero bit pattern is "valid", see memset call in decode_env::decode_env
 #endif
+  static const char* _prefix; // defaults to " ;; "
 #endif
 
   CodeString* find(intptr_t offset) const;
@@ -289,13 +290,20 @@
   void assign(CodeStrings& other)  PRODUCT_RETURN;
   // COPY strings from other to this; leave other valid.
   void copy(CodeStrings& other)  PRODUCT_RETURN;
+  // FREE strings; invalidate this.
   void free() PRODUCT_RETURN;
-  // Guarantee that _strings are used at most once; assign invalidates a buffer.
+  // Guarantee that _strings are used at most once; assign and free invalidate a buffer.
   inline void check_valid() const {
 #ifdef ASSERT
     assert(!_defunct, "Use of invalid CodeStrings");
 #endif
   }
+
+  static void set_prefix(const char *prefix) {
+#ifndef PRODUCT
+    _prefix = prefix;
+#endif
+  }
 };
 
 // A CodeBuffer describes a memory space into which assembly
@@ -379,6 +387,7 @@
     _oop_recorder    = NULL;
     _decode_begin    = NULL;
     _overflow_arena  = NULL;
+    _code_strings    = CodeStrings();
   }
 
   void initialize(address code_start, csize_t code_size) {
@@ -495,6 +504,7 @@
 
   // Properties
   const char* name() const                  { return _name; }
+  void set_name(const char* name)           { _name = name; }
   CodeBuffer* before_expand() const         { return _before_expand; }
   BufferBlob* blob() const                  { return _blob; }
   void    set_blob(BufferBlob* blob);
--- a/hotspot/src/share/vm/c1/c1_CFGPrinter.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/c1/c1_CFGPrinter.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -161,7 +161,7 @@
 
   print("name \"%s\"", method_name(_compilation->method(), true));
   print("method \"%s\"", method_name(_compilation->method()));
-  print("date "INT64_FORMAT, (int64_t) os::javaTimeMillis());
+  print("date " INT64_FORMAT, (int64_t) os::javaTimeMillis());
 
   print_end("compilation");
 }
--- a/hotspot/src/share/vm/c1/c1_GraphBuilder.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/c1/c1_GraphBuilder.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -3157,6 +3157,9 @@
       // code for the inlined version will be different than the root
       // compiled version which could lead to monotonicity problems on
       // intel.
+      if (CheckIntrinsics && !scope->method()->intrinsic_candidate()) {
+        BAILOUT("failed to inline intrinsic, method not annotated");
+      }
 
       // Set up a stream so that appending instructions works properly.
       ciBytecodeStream s(scope->method());
@@ -3197,6 +3200,9 @@
         // result in the referent being marked live and the reference
         // object removed from the list of discovered references during
         // reference processing.
+        if (CheckIntrinsics && !scope->method()->intrinsic_candidate()) {
+          BAILOUT("failed to inline intrinsic, method not annotated");
+        }
 
         // Also we need intrinsic to prevent commoning reads from this field
         // across safepoint since GC can change its value.
@@ -3317,7 +3323,8 @@
   }
 
   // handle intrinsics
-  if (callee->intrinsic_id() != vmIntrinsics::_none) {
+  if (callee->intrinsic_id() != vmIntrinsics::_none &&
+      (CheckIntrinsics ? callee->intrinsic_candidate() : true)) {
     if (try_inline_intrinsics(callee)) {
       print_inlining(callee, "intrinsic");
       return true;
@@ -4278,7 +4285,7 @@
   assert(result_type->is_int(), "int result");
   Values* args = state()->pop_arguments(callee->arg_size());
 
-  // Pop off some args to speically handle, then push back
+  // Pop off some args to specially handle, then push back
   Value newval = args->pop();
   Value cmpval = args->pop();
   Value offset = args->pop();
--- a/hotspot/src/share/vm/c1/c1_LIRGenerator.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/c1/c1_LIRGenerator.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -2208,7 +2208,15 @@
   if (log2_scale != 0) {
     // temporary fix (platform dependent code without shift on Intel would be better)
     // TODO: ARM also allows embedded shift in the address
-    __ shift_left(index_op, log2_scale, index_op);
+    LIR_Opr tmp = new_pointer_register();
+    if (TwoOperandLIRForm) {
+      __ move(index_op, tmp);
+      index_op = tmp;
+    }
+    __ shift_left(index_op, log2_scale, tmp);
+    if (!TwoOperandLIRForm) {
+      index_op = tmp;
+    }
   }
 
   LIR_Address* addr = new LIR_Address(base_op, index_op, x->basic_type());
--- a/hotspot/src/share/vm/c1/c1_Runtime1.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/c1/c1_Runtime1.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -33,6 +33,7 @@
 #include "classfile/systemDictionary.hpp"
 #include "classfile/vmSymbols.hpp"
 #include "code/codeBlob.hpp"
+#include "code/codeCacheExtensions.hpp"
 #include "code/compiledIC.hpp"
 #include "code/pcDesc.hpp"
 #include "code/scopeDesc.hpp"
@@ -183,20 +184,25 @@
   // create code buffer for code storage
   CodeBuffer code(buffer_blob);
 
-  Compilation::setup_code_buffer(&code, 0);
+  OopMapSet* oop_maps;
+  int frame_size;
+  bool must_gc_arguments;
 
-  // create assembler for code generation
-  StubAssembler* sasm = new StubAssembler(&code, name_for(id), id);
-  // generate code for runtime stub
-  OopMapSet* oop_maps;
-  oop_maps = generate_code_for(id, sasm);
-  assert(oop_maps == NULL || sasm->frame_size() != no_frame_size,
-         "if stub has an oop map it must have a valid frame size");
+  if (!CodeCacheExtensions::skip_compiler_support()) {
+    // bypass useless code generation
+    Compilation::setup_code_buffer(&code, 0);
+
+    // create assembler for code generation
+    StubAssembler* sasm = new StubAssembler(&code, name_for(id), id);
+    // generate code for runtime stub
+    oop_maps = generate_code_for(id, sasm);
+    assert(oop_maps == NULL || sasm->frame_size() != no_frame_size,
+           "if stub has an oop map it must have a valid frame size");
 
 #ifdef ASSERT
-  // Make sure that stubs that need oopmaps have them
-  switch (id) {
-    // These stubs don't need to have an oopmap
+    // Make sure that stubs that need oopmaps have them
+    switch (id) {
+      // These stubs don't need to have an oopmap
     case dtrace_object_alloc_id:
     case g1_pre_barrier_slow_id:
     case g1_post_barrier_slow_id:
@@ -209,23 +215,32 @@
 #endif
       break;
 
-    // All other stubs should have oopmaps
+      // All other stubs should have oopmaps
     default:
       assert(oop_maps != NULL, "must have an oopmap");
-  }
+    }
 #endif
 
-  // align so printing shows nop's instead of random code at the end (SimpleStubs are aligned)
-  sasm->align(BytesPerWord);
-  // make sure all code is in code buffer
-  sasm->flush();
+    // align so printing shows nop's instead of random code at the end (SimpleStubs are aligned)
+    sasm->align(BytesPerWord);
+    // make sure all code is in code buffer
+    sasm->flush();
+
+    frame_size = sasm->frame_size();
+    must_gc_arguments = sasm->must_gc_arguments();
+  } else {
+    /* ignored values */
+    oop_maps = NULL;
+    frame_size = 0;
+    must_gc_arguments = false;
+  }
   // create blob - distinguish a few special cases
   CodeBlob* blob = RuntimeStub::new_runtime_stub(name_for(id),
                                                  &code,
                                                  CodeOffsets::frame_never_safe,
-                                                 sasm->frame_size(),
+                                                 frame_size,
                                                  oop_maps,
-                                                 sasm->must_gc_arguments());
+                                                 must_gc_arguments);
   // install blob
   assert(blob != NULL, "blob must exist");
   _blobs[id] = blob;
@@ -399,7 +414,7 @@
   CompLevel level = (CompLevel)nm->comp_level();
   int bci = InvocationEntryBci;
   if (branch_bci != InvocationEntryBci) {
-    // Compute desination bci
+    // Compute destination bci
     address pc = method()->code_base() + branch_bci;
     Bytecodes::Code branch = Bytecodes::code_at(method(), pc);
     int offset = 0;
--- a/hotspot/src/share/vm/ci/bcEscapeAnalyzer.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/ci/bcEscapeAnalyzer.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1185,7 +1185,6 @@
   vmIntrinsics::ID iid = method()->intrinsic_id();
 
   if (iid == vmIntrinsics::_getClass ||
-      iid ==  vmIntrinsics::_fillInStackTrace ||
       iid == vmIntrinsics::_hashCode)
     return iid;
   else
@@ -1199,10 +1198,6 @@
   case vmIntrinsics::_getClass:
     _return_local = false;
     break;
-  case vmIntrinsics::_fillInStackTrace:
-    arg.set(0); // 'this'
-    set_returned(arg);
-    break;
   case vmIntrinsics::_hashCode:
     // initialized state is correct
     break;
--- a/hotspot/src/share/vm/ci/ciMethod.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/ci/ciMethod.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -178,9 +178,10 @@
   // Code size for inlining decisions.
   int code_size_for_inlining();
 
-  bool caller_sensitive()   const { return get_Method()->caller_sensitive();   }
-  bool force_inline()       const { return get_Method()->force_inline();       }
-  bool dont_inline()        const { return get_Method()->dont_inline();        }
+  bool caller_sensitive()    const { return get_Method()->caller_sensitive();    }
+  bool force_inline()        const { return get_Method()->force_inline();        }
+  bool dont_inline()         const { return get_Method()->dont_inline();         }
+  bool intrinsic_candidate() const { return get_Method()->intrinsic_candidate(); }
 
   int comp_level();
   int highest_osr_comp_level();
--- a/hotspot/src/share/vm/classfile/classFileParser.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/classfile/classFileParser.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1751,6 +1751,10 @@
     if (_location != _in_method)  break;  // only allow for methods
     if (!privileged)              break;  // only allow in privileged code
     return _method_LambdaForm_Hidden;
+  case vmSymbols::VM_SYMBOL_ENUM_NAME(jdk_internal_HotSpotIntrinsicCandidate_signature):
+    if (_location != _in_method)  break;  // only allow for methods
+    if (!privileged)              break;  // only allow in privileged code
+    return _method_HotSpotIntrinsicCandidate;
   case vmSymbols::VM_SYMBOL_ENUM_NAME(java_lang_invoke_Stable_signature):
     if (_location != _in_field)   break;  // only allow for fields
     if (!privileged)              break;  // only allow in privileged code
@@ -1790,6 +1794,8 @@
     m->set_intrinsic_id(vmIntrinsics::_compiledLambdaForm);
   if (has_annotation(_method_LambdaForm_Hidden))
     m->set_hidden(true);
+  if (has_annotation(_method_HotSpotIntrinsicCandidate) && !m->is_synthetic())
+    m->set_intrinsic_candidate(true);
 }
 
 void ClassFileParser::ClassAnnotationCollector::apply_to(instanceKlassHandle k) {
@@ -4132,9 +4138,78 @@
     // (We used to do this lazily, but now we query it in Rewriter,
     // which is eagerly done for every method, so we might as well do it now,
     // when everything is fresh in memory.)
-    if (Method::klass_id_for_intrinsics(this_klass()) != vmSymbols::NO_SID) {
+    vmSymbols::SID klass_id = Method::klass_id_for_intrinsics(this_klass());
+    if (klass_id != vmSymbols::NO_SID) {
       for (int j = 0; j < methods->length(); j++) {
-        methods->at(j)->init_intrinsic_id();
+        Method* method = methods->at(j);
+        method->init_intrinsic_id();
+
+        if (CheckIntrinsics) {
+          // Check if an intrinsic is defined for method 'method',
+          // but the method is not annotated with @HotSpotIntrinsicCandidate.
+          if (method->intrinsic_id() != vmIntrinsics::_none &&
+              !method->intrinsic_candidate()) {
+            tty->print("Compiler intrinsic is defined for method [%s], "
+                       "but the method is not annotated with @HotSpotIntrinsicCandidate.%s",
+                       method->name_and_sig_as_C_string(),
+                       NOT_DEBUG(" Method will not be inlined.") DEBUG_ONLY(" Exiting.")
+                       );
+            tty->cr();
+            DEBUG_ONLY(vm_exit(1));
+          }
+          // Check is the method 'method' is annotated with @HotSpotIntrinsicCandidate,
+          // but there is no intrinsic available for it.
+          if (method->intrinsic_candidate() &&
+              method->intrinsic_id() == vmIntrinsics::_none) {
+            tty->print("Method [%s] is annotated with @HotSpotIntrinsicCandidate, "
+                       "but no compiler intrinsic is defined for the method.%s",
+                       method->name_and_sig_as_C_string(),
+                       NOT_DEBUG("") DEBUG_ONLY(" Exiting.")
+                       );
+            tty->cr();
+            DEBUG_ONLY(vm_exit(1));
+          }
+        }
+      }
+
+      if (CheckIntrinsics) {
+        // Check for orphan methods in the current class. A method m
+        // of a class C is orphan if an intrinsic is defined for method m,
+        // but class C does not declare m.
+
+        for (int id = vmIntrinsics::FIRST_ID; id < (int)vmIntrinsics::ID_LIMIT; id++) {
+          if (id == vmIntrinsics::_compiledLambdaForm) {
+            // The _compiledLamdbdaForm intrinsic is a special marker for bytecode
+            // generated for the JVM from a LambdaForm and therefore no method
+            // is defined for it.
+            continue;
+          }
+
+          if (vmIntrinsics::class_for(vmIntrinsics::ID_from(id)) == klass_id) {
+            // Check if the current class contains a method with the same
+            // name, flags, signature.
+            bool match = false;
+            for (int j = 0; j < methods->length(); j++) {
+              Method* method = methods->at(j);
+              if (id == method->intrinsic_id()) {
+                match = true;
+                break;
+              }
+            }
+
+            if (!match) {
+              char buf[1000];
+              tty->print("Compiler intrinsic is defined for method [%s], "
+                         "but the method is not available in class [%s].%s",
+                         vmIntrinsics::short_name_as_C_string(vmIntrinsics::ID_from(id), buf, sizeof(buf)),
+                         this_klass->name()->as_C_string(),
+                         NOT_DEBUG("") DEBUG_ONLY(" Exiting.")
+                         );
+              tty->cr();
+              DEBUG_ONLY(vm_exit(1));
+            }
+          }
+        }
       }
     }
 
--- a/hotspot/src/share/vm/classfile/classFileParser.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/classfile/classFileParser.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -130,6 +130,7 @@
       _method_InjectedProfile,
       _method_LambdaForm_Compiled,
       _method_LambdaForm_Hidden,
+      _method_HotSpotIntrinsicCandidate,
       _sun_misc_Contended,
       _field_Stable,
       _annotation_LIMIT
--- a/hotspot/src/share/vm/classfile/classLoader.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/classfile/classLoader.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -68,7 +68,6 @@
 #include "classfile/sharedPathsMiscInfo.hpp"
 #endif
 
-
 // Entry points in zip.dll for loading zip/jar file entries and image file entries
 
 typedef void * * (JNICALL *ZipOpen_t)(const char *name, char **pmsg);
@@ -157,17 +156,12 @@
 }
 
 
-bool ClassPathEntry::is_lazy() {
-  return false;
-}
-
 ClassPathDirEntry::ClassPathDirEntry(const char* dir) : ClassPathEntry() {
   char* copy = NEW_C_HEAP_ARRAY(char, strlen(dir)+1, mtClass);
   strcpy(copy, dir);
   _dir = copy;
 }
 
-
 ClassFileStream* ClassPathDirEntry::open_stream(const char* name, TRAPS) {
   // construct full path name
   char path[JVM_MAXPATHLEN];
@@ -278,90 +272,25 @@
   }
 }
 
-LazyClassPathEntry::LazyClassPathEntry(const char* path, const struct stat* st, bool throw_exception) : ClassPathEntry() {
-  _path = os::strdup_check_oom(path);
-  _st = *st;
-  _resolved_entry = NULL;
-  _has_error = false;
-  _throw_exception = throw_exception;
-}
-
-LazyClassPathEntry::~LazyClassPathEntry() {
-  os::free((void*)_path);
-}
-
-bool LazyClassPathEntry::is_jar_file() {
-  size_t len = strlen(_path);
-  if (len < 4 || strcmp(_path + len - 4, ".jar") != 0) return false;
-  return ((_st.st_mode & S_IFREG) == S_IFREG);
-}
-
-ClassPathEntry* LazyClassPathEntry::resolve_entry(TRAPS) {
-  if (_resolved_entry != NULL) {
-    return (ClassPathEntry*) _resolved_entry;
-  }
-  ClassPathEntry* new_entry = NULL;
-  new_entry = ClassLoader::create_class_path_entry(_path, &_st, false, _throw_exception, CHECK_NULL);
-  if (!_throw_exception && new_entry == NULL) {
-    assert(!HAS_PENDING_EXCEPTION, "must be");
-    return NULL;
-  }
-  {
-    ThreadCritical tc;
-    if (_resolved_entry == NULL) {
-      _resolved_entry = new_entry;
-      return new_entry;
-    }
-  }
-  assert(_resolved_entry != NULL, "bug in MT-safe resolution logic");
-  delete new_entry;
-  return (ClassPathEntry*) _resolved_entry;
-}
+ClassPathImageEntry::ClassPathImageEntry(ImageFileReader* image) :
+  ClassPathEntry(),
+  _image(image),
+  _module_data(NULL) {
+  guarantee(image != NULL, "image file is null");
 
-ClassFileStream* LazyClassPathEntry::open_stream(const char* name, TRAPS) {
-  if (_has_error) {
-    return NULL;
-  }
-  ClassPathEntry* cpe = resolve_entry(THREAD);
-  if (cpe == NULL) {
-    _has_error = true;
-    return NULL;
-  } else {
-    return cpe->open_stream(name, THREAD);
-  }
-}
-
-bool LazyClassPathEntry::is_lazy() {
-  return true;
-}
-
-u1* LazyClassPathEntry::open_entry(const char* name, jint* filesize, bool nul_terminate, TRAPS) {
-  if (_has_error) {
-    return NULL;
-  }
-  ClassPathEntry* cpe = resolve_entry(THREAD);
-  if (cpe == NULL) {
-    _has_error = true;
-    return NULL;
-  } else if (cpe->is_jar_file()) {
-    return ((ClassPathZipEntry*)cpe)->open_entry(name, filesize, nul_terminate,THREAD);
-  } else {
-    ShouldNotReachHere();
-    *filesize = 0;
-    return NULL;
-  }
-}
-
-ClassPathImageEntry::ClassPathImageEntry(char* name) : ClassPathEntry(), _image(new ImageFile(name)) {
-  bool opened = _image->open();
-  if (!opened) {
-    _image = NULL;
-  }
+  char module_data_name[JVM_MAXPATHLEN];
+  ImageModuleData::module_data_name(module_data_name, _image->name());
+  _module_data = new ImageModuleData(_image, module_data_name);
 }
 
 ClassPathImageEntry::~ClassPathImageEntry() {
-  if (_image) {
-    _image->close();
+  if (_module_data != NULL) {
+    delete _module_data;
+    _module_data = NULL;
+  }
+
+  if (_image != NULL) {
+    ImageFileReader::close(_image);
     _image = NULL;
   }
 }
@@ -371,15 +300,39 @@
 }
 
 ClassFileStream* ClassPathImageEntry::open_stream(const char* name, TRAPS) {
-  u1* buffer;
-  u8 size;
-  _image->get_resource(name, buffer, size);
+  ImageLocation location;
+  bool found = _image->find_location(name, location);
+
+  if (!found) {
+    const char *pslash = strrchr(name, '/');
+    int len = pslash - name;
+
+    // NOTE: IMAGE_MAX_PATH is used here since this path is internal to the jimage
+    // (effectively unlimited.)  There are several JCK tests that use paths over
+    // 1024 characters long, the limit on Windows systems.
+    if (pslash && 0 < len && len < IMAGE_MAX_PATH) {
 
-  if (buffer) {
+      char path[IMAGE_MAX_PATH];
+      strncpy(path, name, len);
+      path[len] = '\0';
+      const char* moduleName = _module_data->package_to_module(path);
+
+      if (moduleName != NULL && (len + strlen(moduleName) + 2) < IMAGE_MAX_PATH) {
+        jio_snprintf(path, IMAGE_MAX_PATH - 1, "/%s/%s", moduleName, name);
+        location.clear_data();
+        found = _image->find_location(path, location);
+      }
+    }
+  }
+
+  if (found) {
+    u8 size = location.get_attribute(ImageLocation::ATTRIBUTE_UNCOMPRESSED);
     if (UsePerfData) {
       ClassLoader::perf_sys_classfile_bytes_read()->inc(size);
     }
-    return new ClassFileStream(buffer, (int)size, (char*)name);  // Resource allocated
+    u1* data = NEW_RESOURCE_ARRAY(u1, size);
+    _image->get_resource(location, data);
+    return new ClassFileStream(data, (int)size, _image->name());  // Resource allocated
   }
 
   return NULL;
@@ -391,20 +344,14 @@
   tty->cr();
   const ImageStrings strings = _image->get_strings();
   // Retrieve each path component string.
-  u4 count = _image->get_location_count();
-  for (u4 i = 0; i < count; i++) {
+  u4 length = _image->table_length();
+  for (u4 i = 0; i < length; i++) {
     u1* location_data = _image->get_location_data(i);
 
-    if (location_data) {
+    if (location_data != NULL) {
        ImageLocation location(location_data);
-       const char* parent = location.get_attribute(ImageLocation::ATTRIBUTE_PARENT, strings);
-       const char* base = location.get_attribute(ImageLocation::ATTRIBUTE_BASE, strings);
-       const char* extension = location.get_attribute(ImageLocation::ATTRIBUTE_EXTENSION, strings);
-       assert((strlen(parent) + strlen(base) + strlen(extension)) < JVM_MAXPATHLEN, "path exceeds buffer");
-       char path[JVM_MAXPATHLEN];
-       strcpy(path, parent);
-       strcat(path, base);
-       strcat(path, extension);
+       char path[IMAGE_MAX_PATH];
+       _image->location_path(location, path, IMAGE_MAX_PATH);
        ClassLoader::compile_the_world_in(path, loader, CHECK);
     }
   }
@@ -420,7 +367,7 @@
 }
 
 bool ClassPathImageEntry::is_jrt() {
-  return string_ends_with(name(), "bootmodules.jimage");
+  return string_ends_with(name(), BOOT_IMAGE_NAME);
 }
 #endif
 
@@ -539,11 +486,8 @@
 }
 
 ClassPathEntry* ClassLoader::create_class_path_entry(const char *path, const struct stat* st,
-                                                     bool lazy, bool throw_exception, TRAPS) {
+                                                     bool throw_exception, TRAPS) {
   JavaThread* thread = JavaThread::current();
-  if (lazy) {
-    return new LazyClassPathEntry(path, st, throw_exception);
-  }
   ClassPathEntry* new_entry = NULL;
   if ((st->st_mode & S_IFREG) == S_IFREG) {
     // Regular file, should be a zip or image file
@@ -557,38 +501,38 @@
         return NULL;
       }
     }
-    // TODO - add proper criteria for selecting image file
-    ClassPathImageEntry* entry = new ClassPathImageEntry(canonical_path);
-    if (entry->is_open()) {
-      new_entry = entry;
-    } else {
-    char* error_msg = NULL;
-    jzfile* zip;
-    {
-      // enable call to C land
-      ThreadToNativeFromVM ttn(thread);
-      HandleMark hm(thread);
-      zip = (*ZipOpen)(canonical_path, &error_msg);
-    }
-    if (zip != NULL && error_msg == NULL) {
-      new_entry = new ClassPathZipEntry(zip, path);
+    ImageFileReader* image = ImageFileReader::open(canonical_path);
+    if (image != NULL) {
+      new_entry = new ClassPathImageEntry(image);
     } else {
-      ResourceMark rm(thread);
-      char *msg;
-      if (error_msg == NULL) {
-        msg = NEW_RESOURCE_ARRAY(char, strlen(path) + 128); ;
-        jio_snprintf(msg, strlen(path) + 127, "error in opening JAR file %s", path);
+      char* error_msg = NULL;
+      jzfile* zip;
+      {
+        // enable call to C land
+        ThreadToNativeFromVM ttn(thread);
+        HandleMark hm(thread);
+        zip = (*ZipOpen)(canonical_path, &error_msg);
+      }
+      if (zip != NULL && error_msg == NULL) {
+        new_entry = new ClassPathZipEntry(zip, path);
       } else {
-        int len = (int)(strlen(path) + strlen(error_msg) + 128);
-        msg = NEW_RESOURCE_ARRAY(char, len); ;
-        jio_snprintf(msg, len - 1, "error in opening JAR file <%s> %s", error_msg, path);
+        ResourceMark rm(thread);
+        char *msg;
+        if (error_msg == NULL) {
+          msg = NEW_RESOURCE_ARRAY(char, strlen(path) + 128); ;
+          jio_snprintf(msg, strlen(path) + 127, "error in opening JAR file %s", path);
+        } else {
+          int len = (int)(strlen(path) + strlen(error_msg) + 128);
+          msg = NEW_RESOURCE_ARRAY(char, len); ;
+          jio_snprintf(msg, len - 1, "error in opening JAR file <%s> %s", error_msg, path);
+        }
+        // Don't complain about bad jar files added via -Xbootclasspath/a:.
+        if (throw_exception && is_init_completed()) {
+          THROW_MSG_(vmSymbols::java_lang_ClassNotFoundException(), msg, NULL);
+        } else {
+          return NULL;
+        }
       }
-      if (throw_exception) {
-        THROW_MSG_(vmSymbols::java_lang_ClassNotFoundException(), msg, NULL);
-      } else {
-        return NULL;
-      }
-    }
     }
     if (TraceClassLoading || TraceClassPaths) {
       tty->print_cr("[Opened %s]", path);
@@ -666,7 +610,7 @@
     // File or directory found
     ClassPathEntry* new_entry = NULL;
     Thread* THREAD = Thread::current();
-    new_entry = create_class_path_entry(path, &st, LazyBootClassLoader, throw_exception, CHECK_(false));
+    new_entry = create_class_path_entry(path, &st, throw_exception, CHECK_(false));
     if (new_entry == NULL) {
       return false;
     }
@@ -1319,19 +1263,6 @@
   return false;
 }
 
-void LazyClassPathEntry::compile_the_world(Handle loader, TRAPS) {
-  ClassPathEntry* cpe = resolve_entry(THREAD);
-  if (cpe != NULL) {
-    cpe->compile_the_world(loader, CHECK);
-  }
-}
-
-bool LazyClassPathEntry::is_jrt() {
-  Thread* THREAD = Thread::current();
-  ClassPathEntry* cpe = resolve_entry(THREAD);
-  return (cpe != NULL) ? cpe->is_jar_file() : false;
-}
-
 void ClassLoader::compile_the_world() {
   EXCEPTION_MARK;
   HandleMark hm(THREAD);
--- a/hotspot/src/share/vm/classfile/classLoader.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/classfile/classLoader.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -32,9 +32,14 @@
 // The VM class loader.
 #include <sys/stat.h>
 
+// Name of boot module image
+#define  BOOT_IMAGE_NAME "bootmodules.jimage"
 
 // Class path entry (directory or zip file)
 
+class ImageFileReader;
+class ImageModuleData;
+
 class ClassPathEntry: public CHeapObj<mtClass> {
  private:
   ClassPathEntry* _next;
@@ -47,7 +52,7 @@
   }
   virtual bool is_jar_file() = 0;
   virtual const char* name() = 0;
-  virtual bool is_lazy();
+  virtual ImageFileReader* image() = 0;
   // Constructor
   ClassPathEntry();
   // Attempt to locate file_name through this class path entry.
@@ -63,8 +68,9 @@
  private:
   const char* _dir;           // Name of directory
  public:
-  bool is_jar_file()  { return false;  }
-  const char* name()  { return _dir; }
+  bool is_jar_file()       { return false;  }
+  const char* name()       { return _dir; }
+  ImageFileReader* image() { return NULL; }
   ClassPathDirEntry(const char* dir);
   ClassFileStream* open_stream(const char* name, TRAPS);
   // Debugging
@@ -92,8 +98,9 @@
   jzfile* _zip;              // The zip archive
   const char*   _zip_name;   // Name of zip archive
  public:
-  bool is_jar_file()  { return true;  }
-  const char* name()  { return _zip_name; }
+  bool is_jar_file()       { return true;  }
+  const char* name()       { return _zip_name; }
+  ImageFileReader* image() { return NULL; }
   ClassPathZipEntry(jzfile* zip, const char* zip_name);
   ~ClassPathZipEntry();
   u1* open_entry(const char* name, jint* filesize, bool nul_terminate, TRAPS);
@@ -105,39 +112,18 @@
 };
 
 
-// For lazier loading of boot class path entries
-class LazyClassPathEntry: public ClassPathEntry {
- private:
-  const char* _path; // dir or file
-  struct stat _st;
-  bool _has_error;
-  bool _throw_exception;
-  volatile ClassPathEntry* _resolved_entry;
-  ClassPathEntry* resolve_entry(TRAPS);
- public:
-  bool is_jar_file();
-  const char* name()  { return _path; }
-  LazyClassPathEntry(const char* path, const struct stat* st, bool throw_exception);
-  virtual ~LazyClassPathEntry();
-  u1* open_entry(const char* name, jint* filesize, bool nul_terminate, TRAPS);
-
-  ClassFileStream* open_stream(const char* name, TRAPS);
-  virtual bool is_lazy();
-  // Debugging
-  NOT_PRODUCT(void compile_the_world(Handle loader, TRAPS);)
-  NOT_PRODUCT(bool is_jrt();)
-};
-
 // For java image files
-class ImageFile;
 class ClassPathImageEntry: public ClassPathEntry {
 private:
-  ImageFile *_image;
+  ImageFileReader* _image;
+  ImageModuleData* _module_data;
 public:
   bool is_jar_file()  { return false;  }
   bool is_open()  { return _image != NULL; }
   const char* name();
-  ClassPathImageEntry(char* name);
+  ImageFileReader* image() { return _image; }
+  ImageModuleData* module_data() { return _module_data; }
+  ClassPathImageEntry(ImageFileReader* image);
   ~ClassPathImageEntry();
   ClassFileStream* open_stream(const char* name, TRAPS);
 
@@ -157,7 +143,6 @@
     package_hash_table_size = 31  // Number of buckets
   };
  protected:
-  friend class LazyClassPathEntry;
 
   // Performance counters
   static PerfCounter* _perf_accumulated_time;
@@ -222,7 +207,7 @@
 
   static void load_zip_library();
   static ClassPathEntry* create_class_path_entry(const char *path, const struct stat* st,
-                                                 bool lazy, bool throw_exception, TRAPS);
+                                                 bool throw_exception, TRAPS);
 
   // Canonicalizes path names, so strcmp will work properly. This is mainly
   // to avoid confusing the zip library
--- a/hotspot/src/share/vm/classfile/classLoaderData.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/classfile/classLoaderData.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -494,7 +494,7 @@
 
 void ClassLoaderData::dump(outputStream * const out) {
   ResourceMark rm;
-  out->print("ClassLoaderData CLD: "PTR_FORMAT", loader: "PTR_FORMAT", loader_klass: "PTR_FORMAT" %s {",
+  out->print("ClassLoaderData CLD: " PTR_FORMAT ", loader: " PTR_FORMAT ", loader_klass: " PTR_FORMAT " %s {",
       p2i(this), p2i((void *)class_loader()),
       p2i(class_loader() != NULL ? class_loader()->klass() : NULL), loader_name());
   if (claimed()) out->print(" claimed ");
@@ -513,7 +513,7 @@
     ResourceMark rm;
     Klass* k = _klasses;
     while (k != NULL) {
-      out->print_cr("klass "PTR_FORMAT", %s, CT: %d, MUT: %d", k, k->name()->as_C_string(),
+      out->print_cr("klass " PTR_FORMAT ", %s, CT: %d, MUT: %d", k, k->name()->as_C_string(),
           k->has_modified_oops(), k->has_accumulated_modified_oops());
       assert(k != k->next_link(), "no loops!");
       k = k->next_link();
--- a/hotspot/src/share/vm/classfile/dictionary.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/classfile/dictionary.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -557,7 +557,7 @@
 }
 
 void ProtectionDomainCacheEntry::print() {
-  tty->print_cr("entry "PTR_FORMAT" value "PTR_FORMAT" strongly_reachable %d next "PTR_FORMAT,
+  tty->print_cr("entry " PTR_FORMAT " value " PTR_FORMAT " strongly_reachable %d next " PTR_FORMAT,
                 this, (void*)literal(), _strongly_reachable, next());
 }
 #endif
--- a/hotspot/src/share/vm/classfile/dictionary.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/classfile/dictionary.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -370,7 +370,7 @@
 
   void print_on(outputStream* st) const {
     symbol()->print_value_on(st);
-    st->print("/mode="INTX_FORMAT, symbol_mode());
+    st->print("/mode=" INTX_FORMAT, symbol_mode());
     st->print(" -> ");
     bool printed = false;
     if (method() != NULL) {
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/vm/classfile/imageDecompressor.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,121 @@
+/*
+ * 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.
+ *
+ */
+
+#include "runtime/thread.inline.hpp"
+#include "precompiled.hpp"
+#include "classfile/imageDecompressor.hpp"
+#include "runtime/thread.hpp"
+#include "utilities/bytes.hpp"
+
+/*
+ * Allocate in C Heap not in resource area, otherwise JVM crashes.
+ * This array life time is the VM life time. Array is never freed and
+ * is not expected to contain more than few references.
+ */
+GrowableArray<ImageDecompressor*>* ImageDecompressor::_decompressors =
+  new(ResourceObj::C_HEAP, mtInternal) GrowableArray<ImageDecompressor*>(2, true);
+
+static Symbol* createSymbol(const char* str) {
+  Thread* THREAD = Thread::current();
+  Symbol* sym = SymbolTable::lookup(str, (int) strlen(str), THREAD);
+  if (HAS_PENDING_EXCEPTION) {
+    warning("can't create symbol\n");
+    CLEAR_PENDING_EXCEPTION;
+    return NULL;
+  }
+  return sym;
+}
+
+/*
+ * Initialize the array of decompressors.
+ */
+bool image_decompressor_init() {
+  Symbol* zipSymbol = createSymbol("zip");
+  if (zipSymbol == NULL) {
+    return false;
+  }
+  ImageDecompressor::add_decompressor(new ZipDecompressor(zipSymbol));
+
+  return true;
+}
+
+/*
+ * Decompression entry point. Called from ImageFileReader::get_resource.
+ */
+void ImageDecompressor::decompress_resource(u1* compressed, u1* uncompressed,
+        u4 uncompressed_size, const ImageStrings* strings, bool is_C_heap) {
+  bool has_header = false;
+  u1* decompressed_resource = compressed;
+  u1* compressed_resource = compressed;
+
+  // Resource could have been transformed by a stack of decompressors.
+  // Iterate and decompress resources until there is no more header.
+  do {
+    ResourceHeader _header;
+    memcpy(&_header, compressed_resource, sizeof (ResourceHeader));
+    has_header = _header._magic == ResourceHeader::resource_header_magic;
+    if (has_header) {
+      // decompressed_resource array contains the result of decompression
+      // when a resource content is terminal, it means that it is an actual resource,
+      // not an intermediate not fully uncompressed content. In this case
+      // the resource is allocated as an mtClass, otherwise as an mtOther
+      decompressed_resource = is_C_heap && _header._is_terminal ?
+              NEW_C_HEAP_ARRAY(u1, _header._uncompressed_size, mtClass) :
+              NEW_C_HEAP_ARRAY(u1, _header._uncompressed_size, mtOther);
+      // Retrieve the decompressor name
+      const char* decompressor_name = strings->get(_header._decompressor_name_offset);
+      if (decompressor_name == NULL) warning("image decompressor not found\n");
+      guarantee(decompressor_name, "image decompressor not found");
+      // Retrieve the decompressor instance
+      ImageDecompressor* decompressor = get_decompressor(decompressor_name);
+      if (decompressor == NULL) {
+        warning("image decompressor %s not found\n", decompressor_name);
+      }
+      guarantee(decompressor, "image decompressor not found");
+      u1* compressed_resource_base = compressed_resource;
+      compressed_resource += ResourceHeader::resource_header_length;
+      // Ask the decompressor to decompress the compressed content
+      decompressor->decompress_resource(compressed_resource, decompressed_resource,
+        &_header, strings);
+      if (compressed_resource_base != compressed) {
+        FREE_C_HEAP_ARRAY(char, compressed_resource_base);
+      }
+      compressed_resource = decompressed_resource;
+    }
+  } while (has_header);
+  memcpy(uncompressed, decompressed_resource, uncompressed_size);
+}
+
+// Zip decompressor
+
+void ZipDecompressor::decompress_resource(u1* data, u1* uncompressed,
+        ResourceHeader* header, const ImageStrings* strings) {
+  char* msg = NULL;
+  jboolean res = ClassLoader::decompress(data, header->_size, uncompressed,
+          header->_uncompressed_size, &msg);
+  if (!res) warning("decompression failed due to %s\n", msg);
+  guarantee(res, "decompression failed");
+}
+
+// END Zip Decompressor
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/vm/classfile/imageDecompressor.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,137 @@
+/*
+ * 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.
+ *
+ */
+
+#ifndef SHARE_VM_CLASSFILE_IMAGEDECOMPRESSOR_HPP
+#define SHARE_VM_CLASSFILE_IMAGEDECOMPRESSOR_HPP
+
+#include "runtime/thread.inline.hpp"
+#include "precompiled.hpp"
+#include "classfile/classLoader.hpp"
+#include "classfile/imageFile.hpp"
+#include "classfile/symbolTable.hpp"
+#include "oops/symbol.hpp"
+#include "utilities/growableArray.hpp"
+
+/*
+ * Compressed resources located in image have an header.
+ * This header contains:
+ * - _magic: A magic u4, required to retrieved the header in the compressed content
+ * - _size: The size of the compressed resource.
+ * - _uncompressed_size: The uncompressed size of the compressed resource.
+ * - _decompressor_name_offset: The ImageDecompressor instance name StringsTable offset.
+ * - _decompressor_config_offset: StringsTable offset of configuration that could be needed by
+ *   the decompressor in order to decompress.
+ * - _is_terminal: 1: the compressed content is terminal. Uncompressing it would
+ *   create the actual resource. 0: the compressed content is not terminal. Uncompressing it
+ *   will result in a compressed content to be decompressed (This occurs when a stack of compressors
+ *   have been used to compress the resource.
+ */
+struct ResourceHeader {
+  /* Length of header, needed to retrieve content offset */
+  static const u1 resource_header_length = 21;
+  /* magic bytes that identifies a compressed resource header*/
+  static const u4 resource_header_magic = 0xCAFEFAFA;
+  u4 _magic; // Resource header
+  u4 _size;  // Resource size
+  u4 _uncompressed_size;  // Expected uncompressed size
+  u4 _decompressor_name_offset;  // Strings table decompressor offset
+  u4 _decompressor_config_offset; // Strings table config offset
+  u1 _is_terminal; // Last decompressor 1, otherwise 0.
+};
+
+/*
+ * Resources located in jimage file can be compressed. Compression occurs at
+ * jimage file creation time. When compressed a resource is added an header that
+ * contains the name of the compressor that compressed it.
+ * Various compression strategies can be applied to compress a resource.
+ * The same resource can even be compressed multiple time by a stack of compressors.
+ * At runtime, a resource is decompressed in a loop until there is no more header
+ * meaning that the resource is equivalent to the not compressed resource.
+ * In each iteration, the name of the compressor located in the current header
+ * is used to retrieve the associated instance of ImageDecompressor.
+ * For example “zip” is the name of the compressor that compresses resources
+ * using the zip algorithm. The ZipDecompressor class name is also “zip”.
+ * ImageDecompressor instances are retrieved from a static array in which
+ * they are registered.
+ */
+class ImageDecompressor: public CHeapObj<mtClass> {
+
+private:
+  const Symbol* _name;
+
+  /*
+   * Array of concrete decompressors. This array is used to retrieve the decompressor
+   * that can handle resource decompression.
+   */
+  static GrowableArray<ImageDecompressor*>* _decompressors;
+
+  /*
+   * Identifier of a decompressor. This name is the identification key to retrieve
+   * decompressor from a resource header.
+   */
+  inline const Symbol* get_name() const { return _name; }
+
+protected:
+  ImageDecompressor(const Symbol* name) : _name(name) {
+  }
+  virtual void decompress_resource(u1* data, u1* uncompressed,
+    ResourceHeader* header, const ImageStrings* strings) = 0;
+
+public:
+  inline static void add_decompressor(ImageDecompressor* decompressor) {
+    _decompressors->append(decompressor);
+  }
+  inline static ImageDecompressor* get_decompressor(const char * decompressor_name) {
+    Thread* THREAD = Thread::current();
+    TempNewSymbol sym = SymbolTable::new_symbol(decompressor_name,
+            (int) strlen(decompressor_name), CHECK_NULL);
+    if (HAS_PENDING_EXCEPTION) {
+      warning("can't create symbol\n");
+      CLEAR_PENDING_EXCEPTION;
+      return NULL;
+    }
+    for (int i = 0; i < _decompressors->length(); i++) {
+      ImageDecompressor* decompressor = _decompressors->at(i);
+      if (decompressor->get_name()->fast_compare(sym) == 0) {
+        return decompressor;
+      }
+    }
+    guarantee(false, "No decompressor found.");
+    return NULL;
+  }
+  static void decompress_resource(u1* compressed, u1* uncompressed,
+    u4 uncompressed_size, const ImageStrings* strings, bool is_C_heap);
+};
+
+/**
+ * Zip decompressor.
+ */
+class ZipDecompressor : public ImageDecompressor {
+public:
+  ZipDecompressor(const Symbol* sym) : ImageDecompressor(sym) { }
+  void decompress_resource(u1* data, u1* uncompressed, ResourceHeader* header,
+    const ImageStrings* strings);
+};
+
+#endif // SHARE_VM_CLASSFILE_IMAGEDECOMPRESSOR_HPP
--- a/hotspot/src/share/vm/classfile/imageFile.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/classfile/imageFile.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * 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
@@ -23,77 +23,311 @@
  */
 
 #include "precompiled.hpp"
+#include "classfile/imageDecompressor.hpp"
 #include "classfile/imageFile.hpp"
+#include "memory/resourceArea.hpp"
+#include "runtime/mutex.hpp"
+#include "runtime/mutexLocker.hpp"
 #include "runtime/os.inline.hpp"
-#include "utilities/bytes.hpp"
-
+#include "utilities/endian.hpp"
+#include "utilities/growableArray.hpp"
 
-// Compute the Perfect Hashing hash code for the supplied string.
-u4 ImageStrings::hash_code(const char* string, u4 seed) {
+// Image files are an alternate file format for storing classes and resources. The
+// goal is to supply file access which is faster and smaller than the jar format.
+//
+// (More detailed nodes in the header.)
+//
+
+// Compute the Perfect Hashing hash code for the supplied UTF-8 string.
+s4 ImageStrings::hash_code(const char* string, s4 seed) {
+  // Access bytes as unsigned.
   u1* bytes = (u1*)string;
-
   // Compute hash code.
   for (u1 byte = *bytes++; byte; byte = *bytes++) {
     seed = (seed * HASH_MULTIPLIER) ^ byte;
   }
-
-  // Ensure the result is unsigned.
+  // Ensure the result is not signed.
   return seed & 0x7FFFFFFF;
 }
 
-// Test to see if string begins with start.  If so returns remaining portion
-// of string.  Otherwise, NULL.
+// Match up a string in a perfect hash table.  Result still needs validation
+// for precise match (false positive.)
+s4 ImageStrings::find(Endian* endian, const char* name, s4* redirect, u4 length) {
+  // If the table is empty, then short cut.
+  if (redirect == NULL || length == 0) {
+    return NOT_FOUND;
+  }
+  // Compute the basic perfect hash for name.
+  s4 hash_code = ImageStrings::hash_code(name);
+  // Modulo table size.
+  s4 index = hash_code % length;
+  // Get redirect entry.
+  //   value == 0 then not found
+  //   value < 0 then -1 - value is true index
+  //   value > 0 then value is seed for recomputing hash.
+  s4 value = endian->get(redirect[index]);
+  // if recompute is required.
+  if (value > 0) {
+    // Entry collision value, need to recompute hash.
+    hash_code = ImageStrings::hash_code(name, value);
+    // Modulo table size.
+    return hash_code % length;
+  } else if (value < 0) {
+    // Compute direct index.
+    return -1 - value;
+  }
+  // No entry found.
+  return NOT_FOUND;
+}
+
+// Test to see if UTF-8 string begins with the start UTF-8 string.  If so,
+// return non-NULL address of remaining portion of string.  Otherwise, return
+// NULL.  Used to test sections of a path without copying from image string
+// table.
 const char* ImageStrings::starts_with(const char* string, const char* start) {
   char ch1, ch2;
-
   // Match up the strings the best we can.
   while ((ch1 = *string) && (ch2 = *start)) {
     if (ch1 != ch2) {
       // Mismatch, return NULL.
       return NULL;
     }
-
+    // Next characters.
     string++, start++;
   }
-
   // Return remainder of string.
   return string;
 }
 
-ImageLocation::ImageLocation(u1* data) {
+// Inflates the attribute stream into individual values stored in the long
+// array _attributes. This allows an attribute value to be quickly accessed by
+// direct indexing.  Unspecified values default to zero (from constructor.)
+void ImageLocation::set_data(u1* data) {
   // Deflate the attribute stream into an array of attributes.
-  memset(_attributes, 0, sizeof(_attributes));
   u1 byte;
-
-  while ((byte = *data) != ATTRIBUTE_END) {
+  // Repeat until end header is found.
+  while ((byte = *data)) {
+    // Extract kind from header byte.
     u1 kind = attribute_kind(byte);
+    guarantee(kind < ATTRIBUTE_COUNT, "invalid image location attribute");
+    // Extract length of data (in bytes).
     u1 n = attribute_length(byte);
-    assert(kind < ATTRIBUTE_COUNT, "invalid image location attribute");
+    // Read value (most significant first.)
     _attributes[kind] = attribute_value(data + 1, n);
+    // Position to next attribute by skipping attribute header and data bytes.
     data += n + 1;
   }
 }
 
-ImageFile::ImageFile(const char* name) {
+// Zero all attribute values.
+void ImageLocation::clear_data() {
+  // Set defaults to zero.
+  memset(_attributes, 0, sizeof(_attributes));
+}
+
+// ImageModuleData constructor maps out sub-tables for faster access.
+ImageModuleData::ImageModuleData(const ImageFileReader* image_file,
+        const char* module_data_name) :
+    _image_file(image_file),
+    _endian(image_file->endian()),
+    _strings(image_file->get_strings()) {
+  // Retrieve the resource containing the module data for the image file.
+  ImageLocation location;
+  bool found = image_file->find_location(module_data_name, location);
+  guarantee(found, "missing module data");
+  u8 data_size = location.get_attribute(ImageLocation::ATTRIBUTE_UNCOMPRESSED);
+  _data = (u1*)NEW_C_HEAP_ARRAY(char, data_size, mtClass);
+  _image_file->get_resource(location, _data);
+  // Map out the header.
+  _header = (Header*)_data;
+  // Get the package to module entry count.
+  u4 ptm_count = _header->ptm_count(_endian);
+  // Get the module to package entry count.
+  u4 mtp_count = _header->mtp_count(_endian);
+  // Compute the offset of the package to module perfect hash redirect.
+  u4 ptm_redirect_offset = sizeof(Header);
+  // Compute the offset of the package to module data.
+  u4 ptm_data_offset = ptm_redirect_offset + ptm_count * sizeof(s4);
+  // Compute the offset of the module to package perfect hash redirect.
+  u4 mtp_redirect_offset = ptm_data_offset + ptm_count * sizeof(PTMData);
+  // Compute the offset of the module to package data.
+  u4 mtp_data_offset = mtp_redirect_offset + mtp_count * sizeof(s4);
+  // Compute the offset of the module to package tables.
+  u4 mtp_packages_offset = mtp_data_offset + mtp_count * sizeof(MTPData);
+  // Compute the address of the package to module perfect hash redirect.
+  _ptm_redirect = (s4*)(_data + ptm_redirect_offset);
+  // Compute the address of the package to module data.
+  _ptm_data = (PTMData*)(_data + ptm_data_offset);
+  // Compute the address of the module to package perfect hash redirect.
+  _mtp_redirect = (s4*)(_data + mtp_redirect_offset);
+  // Compute the address of the module to package data.
+  _mtp_data = (MTPData*)(_data + mtp_data_offset);
+  // Compute the address of the module to package tables.
+  _mtp_packages = (s4*)(_data + mtp_packages_offset);
+}
+
+// Release module data resource.
+ImageModuleData::~ImageModuleData() {
+  if (_data != NULL) {
+    FREE_C_HEAP_ARRAY(u1, _data);
+  }
+}
+
+// Return the name of the module data resource.  Ex. "./lib/modules/file.jimage"
+// yields "file.jdata"
+void ImageModuleData::module_data_name(char* buffer, const char* image_file_name) {
+  // Locate the last slash in the file name path.
+  const char* slash = strrchr(image_file_name, os::file_separator()[0]);
+  // Trim the path to name and extension.
+  const char* name = slash != NULL ? slash + 1 : (char *)image_file_name;
+  // Locate the extension period.
+  const char* dot = strrchr(name, '.');
+  guarantee(dot, "missing extension on jimage name");
+  // Trim to only base name.
+  int length = dot - name;
+  strncpy(buffer, name, length);
+  buffer[length] = '\0';
+  // Append extension.
+  strcat(buffer, ".jdata");
+}
+
+// Return the module in which a package resides.  Returns NULL if not found.
+const char* ImageModuleData::package_to_module(const char* package_name) {
+  // Search the package to module table.
+  s4 index = ImageStrings::find(_endian, package_name, _ptm_redirect,
+                                  _header->ptm_count(_endian));
+  // If entry is found.
+  if (index != ImageStrings::NOT_FOUND) {
+    // Retrieve the package to module entry.
+    PTMData* data = _ptm_data + index;
+    // Verify that it is the correct data.
+    if (strcmp(package_name, get_string(data->name_offset(_endian))) != 0) {
+      return NULL;
+    }
+    // Return the module name.
+    return get_string(data->module_name_offset(_endian));
+  }
+  return NULL;
+}
+
+// Returns all the package names in a module.  Returns NULL if module not found.
+GrowableArray<const char*>* ImageModuleData::module_to_packages(const char* module_name) {
+  // Search the module to package table.
+  s4 index = ImageStrings::find(_endian, module_name, _mtp_redirect,
+                                  _header->mtp_count(_endian));
+  // If entry is found.
+  if (index != ImageStrings::NOT_FOUND) {
+    // Retrieve the module to package entry.
+    MTPData* data = _mtp_data + index;
+    // Verify that it is the correct data.
+    if (strcmp(module_name, get_string(data->name_offset(_endian))) != 0) {
+      return NULL;
+    }
+    // Construct an array of all the package entries.
+    GrowableArray<const char*>* packages = new GrowableArray<const char*>();
+    s4 package_offset = data->package_offset(_endian);
+    for (u4 i = 0; i < data->package_count(_endian); i++) {
+      u4 package_name_offset = mtp_package(package_offset + i);
+      const char* package_name = get_string(package_name_offset);
+      packages->append(package_name);
+    }
+    return packages;
+  }
+  return NULL;
+}
+
+// Table to manage multiple opens of an image file.
+GrowableArray<ImageFileReader*>* ImageFileReader::_reader_table =
+  new(ResourceObj::C_HEAP, mtInternal) GrowableArray<ImageFileReader*>(2, true);
+
+// Open an image file, reuse structure if file already open.
+ImageFileReader* ImageFileReader::open(const char* name, bool big_endian) {
+  // Lock out _reader_table.
+  MutexLocker ml(ImageFileReaderTable_lock);
+  ImageFileReader* reader;
+  // Search for an exist image file.
+  for (int i = 0; i < _reader_table->length(); i++) {
+    // Retrieve table entry.
+    reader = _reader_table->at(i);
+    // If name matches, then reuse (bump up use count.)
+    if (strcmp(reader->name(), name) == 0) {
+      reader->inc_use();
+      return reader;
+    }
+  }
+  // Need a new image reader.
+  reader = new ImageFileReader(name, big_endian);
+  bool opened = reader->open();
+  // If failed to open.
+  if (!opened) {
+    delete reader;
+    return NULL;
+  }
+  // Bump use count and add to table.
+  reader->inc_use();
+  _reader_table->append(reader);
+  return reader;
+}
+
+// Close an image file if the file is not in use elsewhere.
+void ImageFileReader::close(ImageFileReader *reader) {
+  // Lock out _reader_table.
+  MutexLocker ml(ImageFileReaderTable_lock);
+  // If last use then remove from table and then close.
+  if (reader->dec_use()) {
+    _reader_table->remove(reader);
+    delete reader;
+  }
+}
+
+// Return an id for the specifed ImageFileReader.
+u8 ImageFileReader::readerToID(ImageFileReader *reader) {
+  // ID is just the cloaked reader address.
+  return (u8)reader;
+}
+
+// Validate the image id.
+bool ImageFileReader::idCheck(u8 id) {
+  // Make sure the ID is a managed (_reader_table) reader.
+  MutexLocker ml(ImageFileReaderTable_lock);
+  return _reader_table->contains((ImageFileReader*)id);
+}
+
+// Return an id for the specifed ImageFileReader.
+ImageFileReader* ImageFileReader::idToReader(u8 id) {
+#ifdef PRODUCT
+  // Fast convert.
+  return (ImageFileReader*)id;
+#else
+  // Do a slow check before fast convert.
+  return idCheck(id) ? (ImageFileReader*)id : NULL;
+#endif
+}
+
+// Constructor intializes to a closed state.
+ImageFileReader::ImageFileReader(const char* name, bool big_endian) {
   // Copy the image file name.
-  _name = NEW_C_HEAP_ARRAY(char, strlen(name)+1, mtClass);
+  _name = NEW_C_HEAP_ARRAY(char, strlen(name) + 1, mtClass);
   strcpy(_name, name);
-
   // Initialize for a closed file.
   _fd = -1;
-  _memory_mapped = true;
+  _endian = Endian::get_handler(big_endian);
   _index_data = NULL;
 }
 
-ImageFile::~ImageFile() {
+// Close image and free up data structures.
+ImageFileReader::~ImageFileReader() {
   // Ensure file is closed.
   close();
-
   // Free up name.
-  FREE_C_HEAP_ARRAY(char, _name);
+  if (_name != NULL) {
+    FREE_C_HEAP_ARRAY(char, _name);
+    _name = NULL;
+  }
 }
 
-bool ImageFile::open() {
+// Open image file for read access.
+bool ImageFileReader::open() {
   // If file exists open for reading.
   struct stat st;
   if (os::stat(_name, &st) != 0 ||
@@ -101,186 +335,212 @@
     (_fd = os::open(_name, 0, O_RDONLY)) == -1) {
     return false;
   }
-
-  // Read image file header and verify.
-  u8 header_size = sizeof(ImageHeader);
-  if (os::read(_fd, &_header, header_size) != header_size ||
-    _header._magic != IMAGE_MAGIC ||
-    _header._major_version != MAJOR_VERSION ||
-    _header._minor_version != MINOR_VERSION) {
+  // Retrieve the file size.
+  _file_size = (u8)st.st_size;
+  // Read image file header and verify it has a valid header.
+  size_t header_size = sizeof(ImageHeader);
+  if (_file_size < header_size ||
+    !read_at((u1*)&_header, header_size, 0) ||
+    _header.magic(_endian) != IMAGE_MAGIC ||
+    _header.major_version(_endian) != MAJOR_VERSION ||
+    _header.minor_version(_endian) != MINOR_VERSION) {
     close();
     return false;
   }
-
-  // Memory map index.
+  // Size of image index.
   _index_size = index_size();
-  _index_data = (u1*)os::map_memory(_fd, _name, 0, NULL, _index_size, true, false);
-
-  // Failing that, read index into C memory.
-  if (_index_data == NULL) {
-    _memory_mapped = false;
-    _index_data = NEW_RESOURCE_ARRAY(u1, _index_size);
-
-    if (os::seek_to_file_offset(_fd, 0) == -1) {
-      close();
-      return false;
-    }
-
-    if (os::read(_fd, _index_data, _index_size) != _index_size) {
-      close();
-      return false;
-    }
-
-    return true;
+  // Make sure file is large enough to contain the index.
+  if (_file_size < _index_size) {
+    return false;
   }
-
-// Used to advance a pointer, unstructured.
-#undef nextPtr
-#define nextPtr(base, fromType, count, toType) (toType*)((fromType*)(base) + (count))
-  // Pull tables out from the index.
-  _redirect_table = nextPtr(_index_data, u1, header_size, s4);
-  _offsets_table = nextPtr(_redirect_table, s4, _header._location_count, u4);
-  _location_bytes = nextPtr(_offsets_table, u4, _header._location_count, u1);
-  _string_bytes = nextPtr(_location_bytes, u1, _header._locations_size, u1);
-#undef nextPtr
-
+  // Determine how much of the image is memory mapped.
+  off_t map_size = (off_t)(MemoryMapImage ? _file_size : _index_size);
+  // Memory map image (minimally the index.)
+  _index_data = (u1*)os::map_memory(_fd, _name, 0, NULL, map_size, true, false);
+  guarantee(_index_data, "image file not memory mapped");
+  // Retrieve length of index perfect hash table.
+  u4 length = table_length();
+  // Compute offset of the perfect hash table redirect table.
+  u4 redirect_table_offset = (u4)header_size;
+  // Compute offset of index attribute offsets.
+  u4 offsets_table_offset = redirect_table_offset + length * sizeof(s4);
+  // Compute offset of index location attribute data.
+  u4 location_bytes_offset = offsets_table_offset + length * sizeof(u4);
+  // Compute offset of index string table.
+  u4 string_bytes_offset = location_bytes_offset + locations_size();
+  // Compute address of the perfect hash table redirect table.
+  _redirect_table = (s4*)(_index_data + redirect_table_offset);
+  // Compute address of index attribute offsets.
+  _offsets_table = (u4*)(_index_data + offsets_table_offset);
+  // Compute address of index location attribute data.
+  _location_bytes = _index_data + location_bytes_offset;
+  // Compute address of index string table.
+  _string_bytes = _index_data + string_bytes_offset;
   // Successful open.
   return true;
 }
 
-void ImageFile::close() {
+// Close image file.
+void ImageFileReader::close() {
   // Dealllocate the index.
-  if (_index_data) {
-    if (_memory_mapped) {
-      os::unmap_memory((char*)_index_data, _index_size);
-    } else {
-      FREE_RESOURCE_ARRAY(u1, _index_data, _index_size);
-    }
-
+  if (_index_data != NULL) {
+    os::unmap_memory((char*)_index_data, _index_size);
     _index_data = NULL;
   }
-
-  // close file.
+  // Close file.
   if (_fd != -1) {
     os::close(_fd);
     _fd = -1;
   }
+}
 
+// Read directly from the file.
+bool ImageFileReader::read_at(u1* data, u8 size, u8 offset) const {
+  return os::read_at(_fd, data, size, offset) == size;
 }
 
-// Return the attribute stream for a named resourced.
-u1* ImageFile::find_location_data(const char* path) const {
-  // Compute hash.
-  u4 hash = ImageStrings::hash_code(path) % _header._location_count;
-  s4 redirect = _redirect_table[hash];
-
-  if (!redirect) {
-    return NULL;
-  }
-
-  u4 index;
-
-  if (redirect < 0) {
-    // If no collision.
-    index = -redirect - 1;
-  } else {
-    // If collision, recompute hash code.
-    index = ImageStrings::hash_code(path, redirect) % _header._location_count;
+// Find the location attributes associated with the path.  Returns true if
+// the location is found, false otherwise.
+bool ImageFileReader::find_location(const char* path, ImageLocation& location) const {
+  // Locate the entry in the index perfect hash table.
+  s4 index = ImageStrings::find(_endian, path, _redirect_table, table_length());
+  // If is found.
+  if (index != ImageStrings::NOT_FOUND) {
+    // Get address of first byte of location attribute stream.
+    u1* data = get_location_data(index);
+    // Expand location attributes.
+    location.set_data(data);
+    // Make sure result is not a false positive.
+    return verify_location(location, path);
   }
-
-  assert(index < _header._location_count, "index exceeds location count");
-  u4 offset = _offsets_table[index];
-  assert(offset < _header._locations_size, "offset exceeds location attributes size");
-
-  if (offset == 0) {
-    return NULL;
-  }
-
-  return _location_bytes + offset;
-}
-
-// Verify that a found location matches the supplied path.
-bool ImageFile::verify_location(ImageLocation& location, const char* path) const {
-  // Retrieve each path component string.
-  ImageStrings strings(_string_bytes, _header._strings_size);
-  // Match a path with each subcomponent without concatenation (copy).
-  // Match up path parent.
-  const char* parent = location.get_attribute(ImageLocation::ATTRIBUTE_PARENT, strings);
-  const char* next = ImageStrings::starts_with(path, parent);
-  // Continue only if a complete match.
-  if (!next) return false;
-  // Match up path base.
-  const char* base = location.get_attribute(ImageLocation::ATTRIBUTE_BASE, strings);
-  next = ImageStrings::starts_with(next, base);
-  // Continue only if a complete match.
-  if (!next) return false;
-  // Match up path extension.
-  const char* extension = location.get_attribute(ImageLocation::ATTRIBUTE_EXTENSION, strings);
-  next = ImageStrings::starts_with(next, extension);
-
-  // True only if complete match and no more characters.
-  return next && *next == '\0';
+  return false;
 }
 
-// Return the resource for the supplied location.
-u1* ImageFile::get_resource(ImageLocation& location) const {
-  // Retrieve the byte offset and size of the resource.
-  u8 offset = _index_size + location.get_attribute(ImageLocation::ATTRIBUTE_OFFSET);
-  u8 size = location.get_attribute(ImageLocation::ATTRIBUTE_UNCOMPRESSED);
-  u8 compressed_size = location.get_attribute(ImageLocation::ATTRIBUTE_COMPRESSED);
-  u8 read_size = compressed_size ? compressed_size : size;
-
-  // Allocate space for the resource.
-  u1* data = NEW_RESOURCE_ARRAY(u1, read_size);
-
-  bool is_read = os::read_at(_fd, data, read_size, offset) == read_size;
-  guarantee(is_read, "error reading from image or short read");
-
-  // If not compressed, just return the data.
-  if (!compressed_size) {
-    return data;
+// Assemble the location path from the string fragments indicated in the location attributes.
+void ImageFileReader::location_path(ImageLocation& location, char* path, size_t max) const {
+  // Manage the image string table.
+  ImageStrings strings(_string_bytes, _header.strings_size(_endian));
+  // Position to first character of the path buffer.
+  char* next = path;
+  // Temp for string length.
+  size_t length;
+  // Get module string.
+  const char* module = location.get_attribute(ImageLocation::ATTRIBUTE_MODULE, strings);
+  // If module string is not empty string.
+  if (*module != '\0') {
+    // Get length of module name.
+    length = strlen(module);
+    // Make sure there is no buffer overflow.
+    guarantee(next - path + length + 2 < max, "buffer overflow");
+    // Append '/module/'.
+    *next++ = '/';
+    strcpy(next, module); next += length;
+    *next++ = '/';
   }
-
-  u1* uncompressed = NEW_RESOURCE_ARRAY(u1, size);
-  char* msg = NULL;
-  jboolean res = ClassLoader::decompress(data, compressed_size, uncompressed, size, &msg);
-  if (!res) warning("decompression failed due to %s\n", msg);
-  guarantee(res, "decompression failed");
-
-  return uncompressed;
+  // Get parent (package) string.
+  const char* parent = location.get_attribute(ImageLocation::ATTRIBUTE_PARENT, strings);
+  // If parent string is not empty string.
+  if (*parent != '\0') {
+    // Get length of module string.
+    length = strlen(parent);
+    // Make sure there is no buffer overflow.
+    guarantee(next - path + length + 1 < max, "buffer overflow");
+    // Append 'patent/' .
+    strcpy(next, parent); next += length;
+    *next++ = '/';
+  }
+  // Get base name string.
+  const char* base = location.get_attribute(ImageLocation::ATTRIBUTE_BASE, strings);
+  // Get length of base name.
+  length = strlen(base);
+  // Make sure there is no buffer overflow.
+  guarantee(next - path + length < max, "buffer overflow");
+  // Append base name.
+  strcpy(next, base); next += length;
+  // Get extension string.
+  const char* extension = location.get_attribute(ImageLocation::ATTRIBUTE_EXTENSION, strings);
+  // If extension string is not empty string.
+  if (*extension != '\0') {
+    // Get length of extension string.
+    length = strlen(extension);
+    // Make sure there is no buffer overflow.
+    guarantee(next - path + length + 1 < max, "buffer overflow");
+    // Append '.extension' .
+    *next++ = '.';
+    strcpy(next, extension); next += length;
+  }
+  // Make sure there is no buffer overflow.
+  guarantee((size_t)(next - path) < max, "buffer overflow");
+  // Terminate string.
+  *next = '\0';
 }
 
-void ImageFile::get_resource(const char* path, u1*& buffer, u8& size) const {
-  buffer = NULL;
-  size = 0;
-  u1* data = find_location_data(path);
-  if (data) {
-    ImageLocation location(data);
-    if (verify_location(location, path)) {
-      size = location.get_attribute(ImageLocation::ATTRIBUTE_UNCOMPRESSED);
-      buffer = get_resource(location);
-    }
+// Verify that a found location matches the supplied path (without copying.)
+bool ImageFileReader::verify_location(ImageLocation& location, const char* path) const {
+  // Manage the image string table.
+  ImageStrings strings(_string_bytes, _header.strings_size(_endian));
+  // Position to first character of the path string.
+  const char* next = path;
+  // Get module name string.
+  const char* module = location.get_attribute(ImageLocation::ATTRIBUTE_MODULE, strings);
+  // If module string is not empty.
+  if (*module != '\0') {
+    // Compare '/module/' .
+    if (*next++ != '/') return false;
+    if (!(next = ImageStrings::starts_with(next, module))) return false;
+    if (*next++ != '/') return false;
   }
+  // Get parent (package) string
+  const char* parent = location.get_attribute(ImageLocation::ATTRIBUTE_PARENT, strings);
+  // If parent string is not empty string.
+  if (*parent != '\0') {
+    // Compare 'parent/' .
+    if (!(next = ImageStrings::starts_with(next, parent))) return false;
+    if (*next++ != '/') return false;
+  }
+  // Get base name string.
+  const char* base = location.get_attribute(ImageLocation::ATTRIBUTE_BASE, strings);
+  // Compare with basne name.
+  if (!(next = ImageStrings::starts_with(next, base))) return false;
+  // Get extension string.
+  const char* extension = location.get_attribute(ImageLocation::ATTRIBUTE_EXTENSION, strings);
+  // If extension is not empty.
+  if (*extension != '\0') {
+    // Compare '.extension' .
+    if (*next++ != '.') return false;
+    if (!(next = ImageStrings::starts_with(next, extension))) return false;
+  }
+  // True only if complete match and no more characters.
+  return *next == '\0';
 }
 
-GrowableArray<const char*>* ImageFile::packages(const char* name) {
-  char entry[JVM_MAXPATHLEN];
-  bool overflow = jio_snprintf(entry, sizeof(entry), "%s/packages.offsets", name) == -1;
-  guarantee(!overflow, "package name overflow");
-
-  u1* buffer;
-  u8 size;
-
-  get_resource(entry, buffer, size);
-  guarantee(buffer, "missing module packages reource");
-  ImageStrings strings(_string_bytes, _header._strings_size);
-  GrowableArray<const char*>* pkgs = new GrowableArray<const char*>();
-  int count = size / 4;
-  for (int i = 0; i < count; i++) {
-    u4 offset = Bytes::get_Java_u4(buffer + (i*4));
-    const char* p = strings.get(offset);
-    pkgs->append(p);
+// Return the resource data for the supplied location.
+void ImageFileReader::get_resource(ImageLocation& location, u1* uncompressed_data) const {
+  // Retrieve the byte offset and size of the resource.
+  u8 offset = location.get_attribute(ImageLocation::ATTRIBUTE_OFFSET);
+  u8 uncompressed_size = location.get_attribute(ImageLocation::ATTRIBUTE_UNCOMPRESSED);
+  u8 compressed_size = location.get_attribute(ImageLocation::ATTRIBUTE_COMPRESSED);
+  if (compressed_size != 0) {
+    ResourceMark rm;
+    u1* compressed_data;
+    // If not memory mapped read in bytes.
+    if (!MemoryMapImage) {
+      // Allocate buffer for compression.
+      compressed_data = NEW_RESOURCE_ARRAY(u1, compressed_size);
+      // Read bytes from offset beyond the image index.
+      bool is_read = read_at(compressed_data, compressed_size, _index_size + offset);
+      guarantee(is_read, "error reading from image or short read");
+    } else {
+      compressed_data = get_data_address() + offset;
+    }
+    // Get image string table.
+    const ImageStrings strings = get_strings();
+    // Decompress resource.
+    ImageDecompressor::decompress_resource(compressed_data, uncompressed_data, uncompressed_size,
+            &strings, false);
+  } else {
+    // Read bytes from offset beyond the image index.
+    bool is_read = read_at(uncompressed_data, uncompressed_size, _index_size + offset);
+    guarantee(is_read, "error reading from image or short read");
   }
-
-  return pkgs;
 }
--- a/hotspot/src/share/vm/classfile/imageFile.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/classfile/imageFile.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -28,13 +28,15 @@
 #include "classfile/classLoader.hpp"
 #include "memory/allocation.hpp"
 #include "memory/allocation.inline.hpp"
+#include "utilities/endian.hpp"
 #include "utilities/globalDefinitions.hpp"
+#include "utilities/growableArray.hpp"
 
 // Image files are an alternate file format for storing classes and resources. The
-// goal is to supply file access which is faster and smaller that the jar format.
-// It should be noted that unlike jars information stored in an image is in native
-// endian format. This allows the image to be memory mapped into memory without
-// endian translation.  This also means that images are platform dependent.
+// goal is to supply file access which is faster and smaller than the jar format.
+// It should be noted that unlike jars, information stored in an image is in native
+// endian format. This allows the image to be mapped into memory without endian
+// translation.  This also means that images are platform dependent.
 //
 // Image files are structured as three sections;
 //
@@ -42,7 +44,7 @@
 //         |  Header   |
 //         +-----------+
 //         |           |
-//         | Directory |
+//         |   Index   |
 //         |           |
 //         +-----------+
 //         |           |
@@ -60,7 +62,11 @@
 //         +------------+------------+
 //         | Major Vers | Minor Vers |
 //         +------------+------------+
-//         |      Location Count     |
+//         |          Flags          |
+//         +-------------------------+
+//         |      Resource Count     |
+//         +-------------------------+
+//         |       Table Length      |
 //         +-------------------------+
 //         |      Attributes Size    |
 //         +-------------------------+
@@ -71,23 +77,24 @@
 //         special file extension.
 // Major vers, minor vers - differences in version numbers indicate structural
 //                          changes in the image.
-// Location count - number of locations/resources in the file.  This count is also
-//                  the length of lookup tables used in the directory.
+// Flags - various image wide flags (future).
+// Resource count - number of resources in the file.
+// Table length - the length of lookup tables used in the index.
 // Attributes size - number of bytes in the region used to store location attribute
 //                   streams.
 // Strings size - the size of the region used to store strings used by the
-//                directory and meta data.
+//                index and meta data.
 //
-// The directory contains information related to resource lookup. The algorithm
+// The index contains information related to resource lookup. The algorithm
 // used for lookup is "A Practical Minimal Perfect Hashing Method"
 // (http://homepages.dcc.ufmg.br/~nivio/papers/wea05.pdf). Given a path string
-// in the form <package>/<base>.<extension>  return the resource location
+// in the form /<module>/<package>/<base>.<extension>  return the resource location
 // information;
 //
-//     redirectIndex = hash(path, DEFAULT_SEED) % count;
+//     redirectIndex = hash(path, DEFAULT_SEED) % table_length;
 //     redirect = redirectTable[redirectIndex];
 //     if (redirect == 0) return not found;
-//     locationIndex = redirect < 0 ? -1 - redirect : hash(path, redirect) % count;
+//     locationIndex = redirect < 0 ? -1 - redirect : hash(path, redirect) % table_length;
 //     location = locationTable[locationIndex];
 //     if (!verify(location, path)) return not found;
 //     return location;
@@ -97,7 +104,7 @@
 // other seeds. The verify function guarantees the found resource location is
 // indeed the resource we are looking for.
 //
-// The following is the format of the directory;
+// The following is the format of the index;
 //
 //         +-------------------+
 //         |   Redirect Table  |
@@ -117,54 +124,74 @@
 //                  offsets.  Zero indicates not found.
 // Attribute Offsets - Array of 32-bit unsigned values representing offsets into
 //                     attribute data.  Attribute offsets can be iterated to do a
-//                     full survey of resources in the image.
+//                     full survey of resources in the image.  Offset of zero
+//                     indicates no attributes.
 // Attribute Data - Bytes representing compact attribute data for locations. (See
 //                  comments in ImageLocation.)
-// Strings - Collection of zero terminated UTF-8 strings used by the directory and
+// Strings - Collection of zero terminated UTF-8 strings used by the index and
 //           image meta data.  Each string is accessed by offset.  Each string is
 //           unique.  Offset zero is reserved for the empty string.
 //
-// Note that the memory mapped directory assumes 32 bit alignment of the image
-// header, the redirect table and the attribute offsets.
+// Note that the memory mapped index assumes 32 bit alignment of each component
+// in the index.
+//
+// Endianness of an image.
+// An image booted by hotspot is always in native endian.  However, it is possible
+// to read (by the JDK) in alternate endian format.  Primarily, this is during
+// cross platform scenarios.  Ex, where javac needs to read an embedded image
+// to access classes for crossing compilation.
 //
 
+class ImageFileReader; // forward declaration
 
 // Manage image file string table.
-class ImageStrings {
+class ImageStrings VALUE_OBJ_CLASS_SPEC {
 private:
-  // Data bytes for strings.
-  u1* _data;
-  // Number of bytes in the string table.
-  u4 _size;
-
+  u1* _data; // Data bytes for strings.
+  u4 _size; // Number of bytes in the string table.
 public:
-  // Prime used to generate hash for Perfect Hashing.
-  static const u4 HASH_MULTIPLIER = 0x01000193;
+  enum {
+    // Not found result from find routine.
+    NOT_FOUND = -1,
+    // Prime used to generate hash for Perfect Hashing.
+    HASH_MULTIPLIER = 0x01000193
+  };
 
   ImageStrings(u1* data, u4 size) : _data(data), _size(size) {}
 
   // Return the UTF-8 string beginning at offset.
   inline const char* get(u4 offset) const {
-    assert(offset < _size, "offset exceeds string table size");
+    guarantee(offset < _size, "offset exceeds string table size");
     return (const char*)(_data + offset);
   }
 
-  // Compute the Perfect Hashing hash code for the supplied string.
+  // Compute the Perfect Hashing hash code for the supplied UTF-8 string.
   inline static u4 hash_code(const char* string) {
     return hash_code(string, HASH_MULTIPLIER);
   }
 
   // Compute the Perfect Hashing hash code for the supplied string, starting at seed.
-  static u4 hash_code(const char* string, u4 seed);
+  static s4 hash_code(const char* string, s4 seed);
 
-  // Test to see if string begins with start.  If so returns remaining portion
-  // of string.  Otherwise, NULL.  Used to test sections of a path without
-  // copying.
+  // Match up a string in a perfect hash table.  Result still needs validation
+  // for precise match.
+  static s4 find(Endian* endian, const char* name, s4* redirect, u4 length);
+
+  // Test to see if UTF-8 string begins with the start UTF-8 string.  If so,
+  // return non-NULL address of remaining portion of string.  Otherwise, return
+  // NULL.  Used to test sections of a path without copying from image string
+  // table.
   static const char* starts_with(const char* string, const char* start);
 
+  // Test to see if UTF-8 string begins with start char.  If so, return non-NULL
+  // address of remaining portion of string.  Otherwise, return NULL.  Used
+  // to test a character of a path without copying.
+  inline static const char* starts_with(const char* string, const char ch) {
+    return *string == ch ? string + 1 : NULL;
+  }
 };
 
-// Manage image file location attribute streams.  Within an image, a location's
+// Manage image file location attribute data.  Within an image, a location's
 // attributes are compressed into a stream of bytes.  An attribute stream is
 // composed of individual attribute sequences.  Each attribute sequence begins with
 // a header byte containing the attribute 'kind' (upper 5 bits of header) and the
@@ -188,7 +215,7 @@
 //    stream.
 //  - ATTRIBUTE_OFFSET represents the number of bytes from the beginning of the region
 //    storing the resources.  Thus, in an image this represents the number of bytes
-//    after the directory.
+//    after the index.
 //  - Currently, compressed resources are represented by having a non-zero
 //    ATTRIBUTE_COMPRESSED value.  This represents the number of bytes stored in the
 //    image, and the value of ATTRIBUTE_UNCOMPRESSED represents number of bytes of the
@@ -198,17 +225,19 @@
 //    represented differently.
 //  - Package strings include trailing slash and extensions include prefix period.
 //
-class ImageLocation {
+class ImageLocation VALUE_OBJ_CLASS_SPEC {
 public:
-  // Attribute kind enumeration.
-  static const u1 ATTRIBUTE_END = 0; // End of attribute stream marker
-  static const u1 ATTRIBUTE_BASE = 1; // String table offset of resource path base
-  static const u1 ATTRIBUTE_PARENT = 2; // String table offset of resource path parent
-  static const u1 ATTRIBUTE_EXTENSION = 3; // String table offset of resource path extension
-  static const u1 ATTRIBUTE_OFFSET = 4; // Container byte offset of resource
-  static const u1 ATTRIBUTE_COMPRESSED = 5; // In image byte size of the compressed resource
-  static const u1 ATTRIBUTE_UNCOMPRESSED = 6; // In memory byte size of the uncompressed resource
-  static const u1 ATTRIBUTE_COUNT = 7; // Number of attribute kinds
+  enum {
+    ATTRIBUTE_END,          // End of attribute stream marker
+    ATTRIBUTE_MODULE,       // String table offset of module name
+    ATTRIBUTE_PARENT,       // String table offset of resource path parent
+    ATTRIBUTE_BASE,         // String table offset of resource path base
+    ATTRIBUTE_EXTENSION,    // String table offset of resource path extension
+    ATTRIBUTE_OFFSET,       // Container byte offset of resource
+    ATTRIBUTE_COMPRESSED,   // In image byte size of the compressed resource
+    ATTRIBUTE_UNCOMPRESSED, // In memory byte size of the uncompressed resource
+    ATTRIBUTE_COUNT         // Number of attribute kinds
+  };
 
 private:
   // Values of inflated attributes.
@@ -222,30 +251,43 @@
   // Return the attribute kind.
   inline static u1 attribute_kind(u1 data) {
     u1 kind = data >> 3;
-    assert(kind < ATTRIBUTE_COUNT, "invalid attribute kind");
+    guarantee(kind < ATTRIBUTE_COUNT, "invalid attribute kind");
     return kind;
   }
 
   // Return the attribute length.
   inline static u8 attribute_value(u1* data, u1 n) {
-    assert(0 < n && n <= 8, "invalid attribute value length");
+    guarantee(0 < n && n <= 8, "invalid attribute value length");
     u8 value = 0;
-
     // Most significant bytes first.
     for (u1 i = 0; i < n; i++) {
       value <<= 8;
       value |= data[i];
     }
-
     return value;
   }
 
 public:
-  ImageLocation(u1* data);
+  ImageLocation() {
+    clear_data();
+  }
+
+  ImageLocation(u1* data) {
+    clear_data();
+    set_data(data);
+  }
+
+  // Inflates the attribute stream into individual values stored in the long
+  // array _attributes. This allows an attribute value to be quickly accessed by
+  // direct indexing. Unspecified values default to zero.
+  void set_data(u1* data);
+
+  // Zero all attribute values.
+  void clear_data();
 
   // Retrieve an attribute value from the inflated array.
   inline u8 get_attribute(u1 kind) const {
-    assert(ATTRIBUTE_END < kind && kind < ATTRIBUTE_COUNT, "invalid attribute kind");
+    guarantee(ATTRIBUTE_END < kind && kind < ATTRIBUTE_COUNT, "invalid attribute kind");
     return _attributes[kind];
   }
 
@@ -255,89 +297,306 @@
   }
 };
 
-// Manage the image file.
-class ImageFile: public CHeapObj<mtClass> {
-private:
-  // Image file marker.
-  static const u4 IMAGE_MAGIC = 0xCAFEDADA;
-  // Image file major version number.
-  static const u2 MAJOR_VERSION = 0;
-  // Image file minor version number.
-  static const u2 MINOR_VERSION = 1;
+//
+// NOTE: needs revision.
+// Each loader requires set of module meta data to identify which modules and
+// packages are managed by that loader.  Currently, there is one image file per
+// builtin loader, so only one  module meta data resource per file.
+//
+// Each element in the module meta data is a native endian 4 byte integer.  Note
+// that entries with zero offsets for string table entries should be ignored (
+// padding for hash table lookup.)
+//
+// Format:
+//    Count of package to module entries
+//    Count of module to package entries
+//    Perfect Hash redirect table[Count of package to module entries]
+//    Package to module entries[Count of package to module entries]
+//        Offset to package name in string table
+//        Offset to module name in string table
+//    Perfect Hash redirect table[Count of module to package entries]
+//    Module to package entries[Count of module to package entries]
+//        Offset to module name in string table
+//        Count of packages in module
+//        Offset to first package in packages table
+//    Packages[]
+//        Offset to package name in string table
+//
+// Manage the image module meta data.
+class ImageModuleData : public CHeapObj<mtClass> {
+  class Header VALUE_OBJ_CLASS_SPEC {
+  private:
+    u4 _ptm_count;      // Count of package to module entries
+    u4 _mtp_count;      // Count of module to package entries
+  public:
+    inline u4 ptm_count(Endian* endian) const { return endian->get(_ptm_count); }
+    inline u4 mtp_count(Endian* endian) const { return endian->get(_mtp_count); }
+  };
 
-  struct ImageHeader {
-    u4 _magic;          // Image file marker
-    u2 _major_version;  // Image file major version number
-    u2 _minor_version;  // Image file minor version number
-    u4 _location_count; // Number of locations managed in index.
-    u4 _locations_size; // Number of bytes in attribute table.
-    u4 _strings_size;   // Number of bytes in string table.
+  // Hashtable entry
+  class HashData VALUE_OBJ_CLASS_SPEC {
+  private:
+    u4 _name_offset;    // Name offset in string table
+  public:
+    inline s4 name_offset(Endian* endian) const { return endian->get(_name_offset); }
+  };
+
+  // Package to module hashtable entry
+  class PTMData : public HashData {
+  private:
+    u4 _module_name_offset; // Module name offset in string table
+  public:
+    inline s4 module_name_offset(Endian* endian) const { return endian->get(_module_name_offset); }
+  };
+
+  // Module to package hashtable entry
+  class MTPData : public HashData {
+  private:
+    u4 _package_count;     // Number of packages in module
+    u4 _package_offset;    // Offset in package list
+  public:
+    inline u4 package_count(Endian* endian)  const { return endian->get(_package_count); }
+    inline u4 package_offset(Endian* endian) const { return endian->get(_package_offset); }
   };
 
-  char* _name;          // Name of image
-  int _fd;              // File descriptor
-  bool _memory_mapped;  // Is file memory mapped
-  ImageHeader _header;  // Image header
-  u8 _index_size;       // Total size of index
-  u1* _index_data;      // Raw index data
-  s4* _redirect_table;  // Perfect hash redirect table
-  u4* _offsets_table;   // Location offset table
-  u1* _location_bytes;  // Location attributes
-  u1* _string_bytes;    // String table
+  const ImageFileReader* _image_file; // Source image file
+  Endian* _endian;                    // Endian handler
+  ImageStrings _strings;              // Image file strings
+  u1* _data;                          // Module data resource data
+  u8 _data_size;                      // Size of resource data
+  Header* _header;                    // Module data header
+  s4* _ptm_redirect;                  // Package to module hashtable redirect
+  PTMData* _ptm_data;                 // Package to module data
+  s4* _mtp_redirect;                  // Module to packages hashtable redirect
+  MTPData* _mtp_data;                 // Module to packages data
+  s4* _mtp_packages;                  // Package data (name offsets)
+
+  // Return a string from the string table.
+  inline const char* get_string(u4 offset) {
+    return _strings.get(offset);
+  }
+
+  inline u4 mtp_package(u4 index) {
+    return _endian->get(_mtp_packages[index]);
+  }
+
+public:
+  ImageModuleData(const ImageFileReader* image_file, const char* module_data_name);
+  ~ImageModuleData();
+
+  // Return the name of the module data resource.
+  static void module_data_name(char* buffer, const char* image_file_name);
+
+  // Return the module in which a package resides.  Returns NULL if not found.
+  const char* package_to_module(const char* package_name);
+
+  // Returns all the package names in a module.  Returns NULL if module not found.
+  GrowableArray<const char*>* module_to_packages(const char* module_name);
+};
+
+// Image file header, starting at offset 0.
+class ImageHeader VALUE_OBJ_CLASS_SPEC {
+private:
+  u4 _magic;           // Image file marker
+  u4 _version;         // Image file major version number
+  u4 _flags;           // Image file flags
+  u4 _resource_count;  // Number of resources in file
+  u4 _table_length;    // Number of slots in index tables
+  u4 _locations_size;  // Number of bytes in attribute table
+  u4 _strings_size;    // Number of bytes in string table
+
+public:
+  u4 magic() const { return _magic; }
+  u4 magic(Endian* endian) const { return endian->get(_magic); }
+  void set_magic(Endian* endian, u4 magic) { return endian->set(_magic, magic); }
+
+  u4 major_version(Endian* endian) const { return endian->get(_version) >> 16; }
+  u4 minor_version(Endian* endian) const { return endian->get(_version) & 0xFFFF; }
+  void set_version(Endian* endian, u4 major_version, u4 minor_version) {
+    return endian->set(_version, major_version << 16 | minor_version);
+  }
+
+  u4 flags(Endian* endian) const { return endian->get(_flags); }
+  void set_flags(Endian* endian, u4 value) { return endian->set(_flags, value); }
+
+  u4 resource_count(Endian* endian) const { return endian->get(_resource_count); }
+  void set_resource_count(Endian* endian, u4 count) { return endian->set(_resource_count, count); }
+
+  u4 table_length(Endian* endian) const { return endian->get(_table_length); }
+  void set_table_length(Endian* endian, u4 count) { return endian->set(_table_length, count); }
+
+  u4 locations_size(Endian* endian) const { return endian->get(_locations_size); }
+  void set_locations_size(Endian* endian, u4 size) { return endian->set(_locations_size, size); }
+
+  u4 strings_size(Endian* endian) const { return endian->get(_strings_size); }
+  void set_strings_size(Endian* endian, u4 size) { return endian->set(_strings_size, size); }
+};
+
+// Max path length limit independent of platform.  Windows max path is 1024,
+// other platforms use 4096.  The JCK fails several tests when 1024 is used.
+#define IMAGE_MAX_PATH 4096
+
+// Manage the image file.
+// ImageFileReader manages the content of an image file.
+// Initially, the header of the image file is read for validation.  If valid,
+// values in the header are used calculate the size of the image index.  The
+// index is then memory mapped to allow load on demand and sharing.  The
+// -XX:+MemoryMapImage flag determines if the entire file is loaded (server use.)
+// An image can be used by Hotspot and multiple reference points in the JDK, thus
+// it is desirable to share a reader.  To accomodate sharing, a share table is
+// defined (see ImageFileReaderTable in imageFile.cpp)  To track the number of
+// uses, ImageFileReader keeps a use count (_use).  Use is incremented when
+// 'opened' by reference point and decremented when 'closed'.  Use of zero
+// leads the ImageFileReader to be actually closed and discarded.
+class ImageFileReader : public CHeapObj<mtClass> {
+private:
+  // Manage a number of image files such that an image can be shared across
+  // multiple uses (ex. loader.)
+  static GrowableArray<ImageFileReader*>* _reader_table;
+
+  char* _name;         // Name of image
+  s4 _use;             // Use count
+  int _fd;             // File descriptor
+  Endian* _endian;     // Endian handler
+  u8 _file_size;       // File size in bytes
+  ImageHeader _header; // Image header
+  size_t _index_size;  // Total size of index
+  u1* _index_data;     // Raw index data
+  s4* _redirect_table; // Perfect hash redirect table
+  u4* _offsets_table;  // Location offset table
+  u1* _location_bytes; // Location attributes
+  u1* _string_bytes;   // String table
+
+  ImageFileReader(const char* name, bool big_endian);
+  ~ImageFileReader();
 
   // Compute number of bytes in image file index.
   inline u8 index_size() {
     return sizeof(ImageHeader) +
-    _header._location_count * sizeof(u4) * 2 +
-    _header._locations_size +
-    _header._strings_size;
+      table_length() * sizeof(u4) * 2 + locations_size() + strings_size();
   }
 
 public:
-  ImageFile(const char* name);
-  ~ImageFile();
+  enum {
+    // Image file marker.
+    IMAGE_MAGIC = 0xCAFEDADA,
+    // Endian inverted Image file marker.
+    IMAGE_MAGIC_INVERT = 0xDADAFECA,
+    // Image file major version number.
+    MAJOR_VERSION = 1,
+    // Image file minor version number.
+    MINOR_VERSION = 0
+  };
+
+  // Open an image file, reuse structure if file already open.
+  static ImageFileReader* open(const char* name, bool big_endian = Endian::is_big_endian());
 
-  // Open image file for access.
+  // Close an image file if the file is not in use elsewhere.
+  static void close(ImageFileReader *reader);
+
+  // Return an id for the specifed ImageFileReader.
+  static u8 readerToID(ImageFileReader *reader);
+
+  // Validate the image id.
+  static bool idCheck(u8 id);
+
+  // Return an id for the specifed ImageFileReader.
+  static ImageFileReader* idToReader(u8 id);
+
+  // Open image file for read access.
   bool open();
+
   // Close image file.
   void close();
 
+  // Read directly from the file.
+  bool read_at(u1* data, u8 size, u8 offset) const;
+
+  inline Endian* endian() const { return _endian; }
+
   // Retrieve name of image file.
   inline const char* name() const {
     return _name;
   }
 
+  // Retrieve size of image file.
+  inline u8 file_size() const {
+    return _file_size;
+  }
+
+  // Return first address of index data.
+  inline u1* get_index_address() const {
+    return _index_data;
+  }
+
+  // Return first address of resource data.
+  inline u1* get_data_address() const {
+    return _index_data + _index_size;
+  }
+
+  // Get the size of the index data.
+  size_t get_index_size() const {
+    return _index_size;
+  }
+
+  inline u4 table_length() const {
+    return _header.table_length(_endian);
+  }
+
+  inline u4 locations_size() const {
+    return _header.locations_size(_endian);
+  }
+
+  inline u4 strings_size()const  {
+    return _header.strings_size(_endian);
+  }
+
+  inline u4* offsets_table() const {
+    return _offsets_table;
+  }
+
+  // Increment use count.
+  inline void inc_use() {
+    _use++;
+  }
+
+  // Decrement use count.
+  inline bool dec_use() {
+    return --_use == 0;
+  }
+
   // Return a string table accessor.
   inline const ImageStrings get_strings() const {
-    return ImageStrings(_string_bytes, _header._strings_size);
+    return ImageStrings(_string_bytes, _header.strings_size(_endian));
   }
 
-  // Return number of locations in image file index.
-  inline u4 get_location_count() const {
-    return _header._location_count;
+  // Return location attribute stream at offset.
+  inline u1* get_location_offset_data(u4 offset) const {
+    guarantee((u4)offset < _header.locations_size(_endian),
+              "offset exceeds location attributes size");
+    return offset != 0 ? _location_bytes + offset : NULL;
   }
 
   // Return location attribute stream for location i.
-  inline u1* get_location_data(u4 i) const {
-    u4 offset = _offsets_table[i];
+  inline u1* get_location_data(u4 index) const {
+    guarantee((u4)index < _header.table_length(_endian),
+              "index exceeds location count");
+    u4 offset = _endian->get(_offsets_table[index]);
 
-    return offset != 0 ? _location_bytes + offset : NULL;
+    return get_location_offset_data(offset);
   }
 
-  // Return the attribute stream for a named resourced.
-  u1* find_location_data(const char* path) const;
+  // Find the location attributes associated with the path.  Returns true if
+  // the location is found, false otherwise.
+  bool find_location(const char* path, ImageLocation& location) const;
+
+  // Assemble the location path.
+  void location_path(ImageLocation& location, char* path, size_t max) const;
 
   // Verify that a found location matches the supplied path.
   bool verify_location(ImageLocation& location, const char* path) const;
 
-  // Return the resource for the supplied location info.
-  u1* get_resource(ImageLocation& location) const;
-
-  // Return the resource associated with the path else NULL if not found.
-  void get_resource(const char* path, u1*& buffer, u8& size) const;
-
-  // Return an array of packages for a given module
-  GrowableArray<const char*>* packages(const char* name);
+  // Return the resource for the supplied path.
+  void get_resource(ImageLocation& location, u1* uncompressed_data) const;
 };
-
 #endif // SHARE_VM_CLASSFILE_IMAGEFILE_HPP
--- a/hotspot/src/share/vm/classfile/javaClasses.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/classfile/javaClasses.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1707,8 +1707,7 @@
     // - rest of the stack
 
     if (!skip_fillInStackTrace_check) {
-      if ((method->name() == vmSymbols::fillInStackTrace_name() ||
-           method->name() == vmSymbols::fillInStackTrace0_name()) &&
+      if (method->name() == vmSymbols::fillInStackTrace_name() &&
           throwable->is_a(method->method_holder())) {
         continue;
       }
--- a/hotspot/src/share/vm/classfile/systemDictionary.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/classfile/systemDictionary.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -2346,9 +2346,6 @@
   assert(!THREAD->is_Compiler_thread(), "");
   Handle method_type =
     SystemDictionary::find_method_handle_type(signature, accessing_klass, CHECK_(empty));
-  if (false) {  // FIXME: Decide if the Java upcall should resolve signatures.
-    method_type = java_lang_String::create_from_symbol(signature, CHECK_(empty));
-  }
 
   KlassHandle  mh_klass = SystemDictionary::MethodHandle_klass();
   int ref_kind = JVM_REF_invokeVirtual;
@@ -2380,6 +2377,24 @@
   return unpack_method_and_appendix(mname, accessing_klass, appendix_box, appendix_result, THREAD);
 }
 
+// Decide if we can globally cache a lookup of this class, to be returned to any client that asks.
+// We must ensure that all class loaders everywhere will reach this class, for any client.
+// This is a safe bet for public classes in java.lang, such as Object and String.
+// We also include public classes in java.lang.invoke, because they appear frequently in system-level method types.
+// Out of an abundance of caution, we do not include any other classes, not even for packages like java.util.
+static bool is_always_visible_class(oop mirror) {
+  Klass* klass = java_lang_Class::as_Klass(mirror);
+  if (klass->oop_is_objArray()) {
+    klass = ObjArrayKlass::cast(klass)->bottom_klass(); // check element type
+  }
+  if (klass->oop_is_typeArray()) {
+    return true; // primitive array
+  }
+  assert(klass->oop_is_instance(), klass->external_name());
+  return klass->is_public() &&
+         (InstanceKlass::cast(klass)->is_same_class_package(SystemDictionary::Object_klass()) ||       // java.lang
+          InstanceKlass::cast(klass)->is_same_class_package(SystemDictionary::MethodHandle_klass()));  // java.lang.invoke
+}
 
 // Ask Java code to find or construct a java.lang.invoke.MethodType for the given
 // signature, as interpreted relative to the given class loader.
@@ -2402,32 +2417,33 @@
   }
 
   Handle class_loader, protection_domain;
-  bool is_on_bcp = true;  // keep this true as long as we can materialize from the boot classloader
+  if (accessing_klass.not_null()) {
+    class_loader      = Handle(THREAD, InstanceKlass::cast(accessing_klass())->class_loader());
+    protection_domain = Handle(THREAD, InstanceKlass::cast(accessing_klass())->protection_domain());
+  }
+  bool can_be_cached = true;
   int npts = ArgumentCount(signature).size();
   objArrayHandle pts = oopFactory::new_objArray(SystemDictionary::Class_klass(), npts, CHECK_(empty));
   int arg = 0;
-  Handle rt;                            // the return type from the signature
+  Handle rt; // the return type from the signature
   ResourceMark rm(THREAD);
   for (SignatureStream ss(signature); !ss.is_done(); ss.next()) {
     oop mirror = NULL;
-    if (is_on_bcp) {
-      // Note:  class_loader & protection_domain are both null at this point.
-      mirror = ss.as_java_mirror(class_loader, protection_domain,
+    if (can_be_cached) {
+      // Use neutral class loader to lookup candidate classes to be placed in the cache.
+      mirror = ss.as_java_mirror(Handle(), Handle(),
                                  SignatureStream::ReturnNull, CHECK_(empty));
-      if (mirror == NULL) {
-        // fall back from BCP to accessing_klass
-        if (accessing_klass.not_null()) {
-          class_loader      = Handle(THREAD, InstanceKlass::cast(accessing_klass())->class_loader());
-          protection_domain = Handle(THREAD, InstanceKlass::cast(accessing_klass())->protection_domain());
-        }
-        is_on_bcp = false;
+      if (mirror == NULL || (ss.is_object() && !is_always_visible_class(mirror))) {
+        // Fall back to accessing_klass context.
+        can_be_cached = false;
       }
     }
-    if (!is_on_bcp) {
+    if (!can_be_cached) {
       // Resolve, throwing a real error if it doesn't work.
       mirror = ss.as_java_mirror(class_loader, protection_domain,
                                  SignatureStream::NCDFError, CHECK_(empty));
     }
+    assert(!oopDesc::is_null(mirror), ss.as_symbol(THREAD)->as_C_string());
     if (ss.at_return_type())
       rt = Handle(THREAD, mirror);
     else
@@ -2459,7 +2475,7 @@
                          &args, CHECK_(empty));
   Handle method_type(THREAD, (oop) result.get_jobject());
 
-  if (is_on_bcp) {
+  if (can_be_cached) {
     // We can cache this MethodType inside the JVM.
     MutexLocker ml(SystemDictionary_lock, THREAD);
     spe = invoke_method_table()->find_entry(index, hash, signature, null_iid);
--- a/hotspot/src/share/vm/classfile/vmSymbols.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/classfile/vmSymbols.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -258,6 +258,8 @@
   /* Type Annotations (JDK 8 and above) */                                                        \
   template(type_annotations_name,                     "typeAnnotations")                          \
                                                                                                   \
+  /* Intrinsic Annotation (JDK 9 and above) */                                                    \
+  template(jdk_internal_HotSpotIntrinsicCandidate_signature, "Ljdk/internal/HotSpotIntrinsicCandidate;") \
                                                                                                   \
   /* Support for JSR 292 & invokedynamic (JDK 1.7 and above) */                                   \
   template(java_lang_invoke_CallSite,                 "java/lang/invoke/CallSite")                \
@@ -345,7 +347,6 @@
   template(dispatch_name,                             "dispatch")                                 \
   template(getSystemClassLoader_name,                 "getSystemClassLoader")                     \
   template(fillInStackTrace_name,                     "fillInStackTrace")                         \
-  template(fillInStackTrace0_name,                    "fillInStackTrace0")                        \
   template(getCause_name,                             "getCause")                                 \
   template(initCause_name,                            "initCause")                                \
   template(setProperty_name,                          "setProperty")                              \
@@ -635,7 +636,43 @@
 // The F_xx is one of the Flags enum; see below.
 //
 // for Emacs: (let ((c-backslash-column 120) (c-backslash-max-column 120)) (c-backslash-region (point) (point-max) nil t))
+//
+//
+// There are two types of intrinsic methods: (1) Library intrinsics and (2) bytecode intrinsics.
+//
+// (1) A library intrinsic method may be replaced with hand-crafted assembly code,
+// with hand-crafted compiler IR, or with a combination of the two. The semantics
+// of the replacement code may differ from the semantics of the replaced code.
+//
+// (2) Bytecode intrinsic methods are not replaced by special code, but they are
+// treated in some other special way by the compiler. For example, the compiler
+// may delay inlining for some String-related intrinsic methods (e.g., some methods
+// defined in the StringBuilder and StringBuffer classes, see
+// Compile::should_delay_string_inlining() for more details).
+//
+// Due to the difference between the semantics of an intrinsic method as defined
+// in the (Java) source code and the semantics of the method as defined
+// by the code in the VM, intrinsic methods must be explicitly marked.
+//
+// Intrinsic methods are marked by the jdk.internal.HotSpotIntrinsicCandidate
+// annotation. If CheckIntrinsics is enabled, the VM performs the following
+// checks when a class C is loaded: (1) all intrinsics defined by the VM for
+// class C are present in the loaded class file and are marked;
+// (2) an intrinsic is defined by the VM for all marked methods of class C.
+//
+// If a mismatch is detected for a method, the VM behaves differently depending
+// on the type of build. A fastdebug build exits and reports an error on a mismatch.
+// A product build will not replace an unmarked library intrinsic method with
+// hand-crafted code, that is, unmarked library intrinsics are treated as ordinary
+// methods in a product build. The special treatment of a bytecode intrinsic method
+// persists even if the method not marked.
+//
+// When adding an intrinsic for a method, please make sure to appropriately
+// annotate the method in the source code. The list below contains all
+// library intrinsics followed by bytecode intrinsics. Please also make sure to
+// add the declaration of the intrinsic to the approriate section of the list.
 #define VM_INTRINSICS_DO(do_intrinsic, do_class, do_name, do_signature, do_alias)                                       \
+  /* (1) Library intrinsics                                                                        */                   \
   do_intrinsic(_hashCode,                 java_lang_Object,       hashCode_name, void_int_signature,             F_R)   \
    do_name(     hashCode_name,                                   "hashCode")                                            \
   do_intrinsic(_getClass,                 java_lang_Object,       getClass_name, void_class_signature,           F_R)   \
@@ -792,12 +829,12 @@
                                                                                                                         \
   do_class(sun_nio_cs_iso8859_1_Encoder,  "sun/nio/cs/ISO_8859_1$Encoder")                                              \
   do_intrinsic(_encodeISOArray,     sun_nio_cs_iso8859_1_Encoder, encodeISOArray_name, encodeISOArray_signature, F_S)   \
-   do_name(     encodeISOArray_name,                             "encodeISOArray")                                      \
+   do_name(     encodeISOArray_name,                             "implEncodeISOArray")                                  \
    do_signature(encodeISOArray_signature,                        "([CI[BII)I")                                          \
                                                                                                                         \
   do_class(java_math_BigInteger,                      "java/math/BigInteger")                                           \
-  do_intrinsic(_multiplyToLen,      java_math_BigInteger, multiplyToLen_name, multiplyToLen_signature, F_R)             \
-   do_name(     multiplyToLen_name,                             "multiplyToLen")                                        \
+  do_intrinsic(_multiplyToLen,      java_math_BigInteger, multiplyToLen_name, multiplyToLen_signature, F_S)             \
+   do_name(     multiplyToLen_name,                             "implMultiplyToLen")                                    \
    do_signature(multiplyToLen_signature,                        "([II[II[I)[I")                                         \
                                                                                                                         \
   do_intrinsic(_squareToLen, java_math_BigInteger, squareToLen_name, squareToLen_signature, F_S)                        \
@@ -808,6 +845,14 @@
    do_name(     mulAdd_name,                                  "implMulAdd")                                             \
    do_signature(mulAdd_signature,                             "([I[IIII)I")                                             \
                                                                                                                         \
+  do_intrinsic(_montgomeryMultiply,      java_math_BigInteger, montgomeryMultiply_name, montgomeryMultiply_signature, F_S) \
+   do_name(     montgomeryMultiply_name,                             "implMontgomeryMultiply")                          \
+   do_signature(montgomeryMultiply_signature,                        "([I[I[IIJ[I)[I")                                  \
+                                                                                                                        \
+  do_intrinsic(_montgomerySquare,      java_math_BigInteger, montgomerySquare_name, montgomerySquare_signature, F_S)    \
+   do_name(     montgomerySquare_name,                             "implMontgomerySquare")                              \
+   do_signature(montgomerySquare_signature,                        "([I[IIJ[I)[I")                                      \
+                                                                                                                        \
   /* java/lang/ref/Reference */                                                                                         \
   do_intrinsic(_Reference_get,            java_lang_ref_Reference, get_name,    void_object_signature, F_R)             \
                                                                                                                         \
@@ -815,21 +860,21 @@
   do_class(com_sun_crypto_provider_aescrypt,      "com/sun/crypto/provider/AESCrypt")                                   \
   do_intrinsic(_aescrypt_encryptBlock, com_sun_crypto_provider_aescrypt, encryptBlock_name, byteArray_int_byteArray_int_signature, F_R)   \
   do_intrinsic(_aescrypt_decryptBlock, com_sun_crypto_provider_aescrypt, decryptBlock_name, byteArray_int_byteArray_int_signature, F_R)   \
-   do_name(     encryptBlock_name,                                 "encryptBlock")                                      \
-   do_name(     decryptBlock_name,                                 "decryptBlock")                                      \
+   do_name(     encryptBlock_name,                                 "implEncryptBlock")                                  \
+   do_name(     decryptBlock_name,                                 "implDecryptBlock")                                  \
    do_signature(byteArray_int_byteArray_int_signature,             "([BI[BI)V")                                         \
                                                                                                                         \
   do_class(com_sun_crypto_provider_cipherBlockChaining,            "com/sun/crypto/provider/CipherBlockChaining")       \
    do_intrinsic(_cipherBlockChaining_encryptAESCrypt, com_sun_crypto_provider_cipherBlockChaining, encrypt_name, byteArray_int_int_byteArray_int_signature, F_R)   \
    do_intrinsic(_cipherBlockChaining_decryptAESCrypt, com_sun_crypto_provider_cipherBlockChaining, decrypt_name, byteArray_int_int_byteArray_int_signature, F_R)   \
-   do_name(     encrypt_name,                                      "encrypt")                                           \
-   do_name(     decrypt_name,                                      "decrypt")                                           \
+   do_name(     encrypt_name,                                      "implEncrypt")                                       \
+   do_name(     decrypt_name,                                      "implDecrypt")                                       \
    do_signature(byteArray_int_int_byteArray_int_signature,         "([BII[BI)I")                                        \
                                                                                                                         \
   /* support for sun.security.provider.SHA */                                                                           \
   do_class(sun_security_provider_sha,                              "sun/security/provider/SHA")                         \
   do_intrinsic(_sha_implCompress, sun_security_provider_sha, implCompress_name, implCompress_signature, F_R)            \
-   do_name(     implCompress_name,                                 "implCompress")                                      \
+   do_name(     implCompress_name,                                 "implCompress0")                                     \
    do_signature(implCompress_signature,                            "([BI)V")                                            \
                                                                                                                         \
   /* support for sun.security.provider.SHA2 */                                                                          \
@@ -843,7 +888,7 @@
   /* support for sun.security.provider.DigestBase */                                                                    \
   do_class(sun_security_provider_digestbase,                       "sun/security/provider/DigestBase")                  \
   do_intrinsic(_digestBase_implCompressMB, sun_security_provider_digestbase, implCompressMB_name, implCompressMB_signature, F_R)   \
-   do_name(     implCompressMB_name,                               "implCompressMultiBlock")                            \
+   do_name(     implCompressMB_name,                               "implCompressMultiBlock0")                           \
    do_signature(implCompressMB_signature,                          "([BII)I")                                           \
                                                                                                                         \
   /* support for com.sun.crypto.provider.GHASH */                                                                       \
@@ -857,17 +902,18 @@
   do_intrinsic(_updateCRC32,               java_util_zip_CRC32,   update_name, int2_int_signature,               F_SN)  \
    do_name(     update_name,                                      "update")                                             \
   do_intrinsic(_updateBytesCRC32,          java_util_zip_CRC32,   updateBytes_name, updateBytes_signature,       F_SN)  \
-   do_name(     updateBytes_name,                                "updateBytes")                                         \
+   do_name(     updateBytes_name,                                "updateBytes0")                                        \
    do_signature(updateBytes_signature,                           "(I[BII)I")                                            \
   do_intrinsic(_updateByteBufferCRC32,     java_util_zip_CRC32,   updateByteBuffer_name, updateByteBuffer_signature, F_SN) \
-   do_name(     updateByteBuffer_name,                           "updateByteBuffer")                                    \
+   do_name(     updateByteBuffer_name,                           "updateByteBuffer0")                                   \
    do_signature(updateByteBuffer_signature,                      "(IJII)I")                                             \
                                                                                                                         \
   /* support for java.util.zip.CRC32C */                                                                                \
   do_class(java_util_zip_CRC32C,          "java/util/zip/CRC32C")                                                       \
-  do_intrinsic(_updateBytesCRC32C,         java_util_zip_CRC32C,  updateBytes_name, updateBytes_signature,       F_S)   \
-  do_intrinsic(_updateDirectByteBufferCRC32C, java_util_zip_CRC32C, updateDirectByteBuffer_name, updateByteBuffer_signature, F_S) \
-   do_name(     updateDirectByteBuffer_name,                     "updateDirectByteBuffer")                              \
+  do_intrinsic(_updateBytesCRC32C,         java_util_zip_CRC32C,  updateBytes_C_name, updateBytes_signature,       F_S) \
+   do_name(     updateBytes_C_name,                               "updateBytes")                                        \
+  do_intrinsic(_updateDirectByteBufferCRC32C, java_util_zip_CRC32C, updateDirectByteBuffer_C_name, updateByteBuffer_signature, F_S) \
+   do_name(    updateDirectByteBuffer_C_name,                     "updateDirectByteBuffer")                             \
                                                                                                                         \
   /* support for sun.misc.Unsafe */                                                                                     \
   do_class(sun_misc_Unsafe,               "sun/misc/Unsafe")                                                            \
@@ -878,12 +924,6 @@
   do_intrinsic(_copyMemory,               sun_misc_Unsafe,        copyMemory_name, copyMemory_signature,         F_RN)  \
    do_name(     copyMemory_name,                                 "copyMemory")                                          \
    do_signature(copyMemory_signature,         "(Ljava/lang/Object;JLjava/lang/Object;JJ)V")                             \
-  do_intrinsic(_park,                     sun_misc_Unsafe,        park_name, park_signature,                     F_RN)  \
-   do_name(     park_name,                                       "park")                                                \
-   do_signature(park_signature,                                  "(ZJ)V")                                               \
-  do_intrinsic(_unpark,                   sun_misc_Unsafe,        unpark_name, unpark_signature,                 F_RN)  \
-   do_name(     unpark_name,                                     "unpark")                                              \
-   do_alias(    unpark_signature,                               /*(LObject;)V*/ object_void_signature)                  \
   do_intrinsic(_loadFence,                sun_misc_Unsafe,        loadFence_name, loadFence_signature,           F_RN)  \
    do_name(     loadFence_name,                                  "loadFence")                                           \
    do_alias(    loadFence_signature,                              void_method_signature)                                \
@@ -1066,11 +1106,15 @@
   do_intrinsic(_getAndSetObject,          sun_misc_Unsafe,        getAndSetObject_name, getAndSetObject_signature,  F_R)\
    do_name(     getAndSetObject_name,                             "getAndSetObject")                                    \
    do_signature(getAndSetObject_signature,                        "(Ljava/lang/Object;JLjava/lang/Object;)Ljava/lang/Object;" ) \
-    /*== LAST_COMPILER_INLINE*/                                                                                         \
-    /*the compiler does have special inlining code for these; bytecode inline is just fine */                           \
+                                                                                                                        \
+   /* (2) Bytecode intrinsics                                                                        */                 \
                                                                                                                         \
-  do_intrinsic(_fillInStackTrace,         java_lang_Throwable, fillInStackTrace_name, void_throwable_signature,  F_RNY) \
-                                                                                                                          \
+  do_intrinsic(_park,                     sun_misc_Unsafe,        park_name, park_signature,                     F_RN)  \
+   do_name(     park_name,                                       "park")                                                \
+   do_signature(park_signature,                                  "(ZJ)V")                                               \
+  do_intrinsic(_unpark,                   sun_misc_Unsafe,        unpark_name, unpark_signature,                 F_RN)  \
+   do_name(     unpark_name,                                     "unpark")                                              \
+   do_alias(    unpark_signature,                               /*(LObject;)V*/ object_void_signature)                  \
   do_intrinsic(_StringBuilder_void,   java_lang_StringBuilder, object_initializer_name, void_method_signature,     F_R)   \
   do_intrinsic(_StringBuilder_int,    java_lang_StringBuilder, object_initializer_name, int_void_signature,        F_R)   \
   do_intrinsic(_StringBuilder_String, java_lang_StringBuilder, object_initializer_name, string_void_signature,     F_R)   \
--- a/hotspot/src/share/vm/code/codeBlob.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/code/codeBlob.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1998, 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
@@ -25,6 +25,7 @@
 #include "precompiled.hpp"
 #include "code/codeBlob.hpp"
 #include "code/codeCache.hpp"
+#include "code/codeCacheExtensions.hpp"
 #include "code/relocInfo.hpp"
 #include "compiler/disassembler.hpp"
 #include "interpreter/bytecode.hpp"
@@ -88,6 +89,7 @@
   _data_offset           = size;
   _frame_size            =  0;
   set_oop_maps(NULL);
+  _strings               = CodeStrings();
 }
 
 
@@ -114,6 +116,7 @@
   _code_offset           = _content_offset + cb->total_offset_of(cb->insts());
   _data_offset           = _content_offset + round_to(cb->total_content_size(), oopSize);
   assert(_data_offset <= size, "codeBlob is too small");
+  _strings               = CodeStrings();
 
   cb->copy_code_and_locs_to(this);
   set_oop_maps(oop_maps);
@@ -192,6 +195,7 @@
 
   BufferBlob* blob = NULL;
   unsigned int size = sizeof(BufferBlob);
+  CodeCacheExtensions::size_blob(name, &buffer_size);
   // align the size to CodeEntryAlignment
   size = align_code_offset(size);
   size += round_to(buffer_size, oopSize);
@@ -275,6 +279,7 @@
 
   MethodHandlesAdapterBlob* blob = NULL;
   unsigned int size = sizeof(MethodHandlesAdapterBlob);
+  CodeCacheExtensions::size_blob("MethodHandles adapters", &buffer_size);
   // align the size to CodeEntryAlignment
   size = align_code_offset(size);
   size += round_to(buffer_size, oopSize);
@@ -315,11 +320,13 @@
 {
   RuntimeStub* stub = NULL;
   ThreadInVMfromUnknown __tiv;  // get to VM state in case we block on CodeCache_lock
-  {
+  if (!CodeCacheExtensions::skip_code_generation()) {
+    // bypass useless code generation
     MutexLockerEx mu(CodeCache_lock, Mutex::_no_safepoint_check_flag);
     unsigned int size = allocation_size(cb, sizeof(RuntimeStub));
     stub = new (size) RuntimeStub(stub_name, cb, size, frame_complete, frame_size, oop_maps, caller_must_gc_arguments);
   }
+  stub = (RuntimeStub*) CodeCacheExtensions::handle_generated_blob(stub, stub_name);
 
   trace_new_stub(stub, "RuntimeStub - ", stub_name);
 
--- a/hotspot/src/share/vm/code/codeBlob.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/code/codeBlob.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1998, 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
@@ -38,7 +38,8 @@
     MethodProfiled      = 1,    // Execution level 2 and 3 (profiled) nmethods
     NonNMethod          = 2,    // Non-nmethods like Buffers, Adapters and Runtime Stubs
     All                 = 3,    // All types (No code cache segmentation)
-    NumTypes            = 4     // Number of CodeBlobTypes
+    Pregenerated        = 4,    // Special blobs, managed by CodeCacheExtensions
+    NumTypes            = 5     // Number of CodeBlobTypes
   };
 };
 
@@ -63,6 +64,7 @@
 class CodeBlob VALUE_OBJ_CLASS_SPEC {
 
   friend class VMStructs;
+  friend class CodeCacheDumper;
 
  private:
   const char* _name;
@@ -206,6 +208,14 @@
   void set_strings(CodeStrings& strings) {
     _strings.assign(strings);
   }
+
+  static ByteSize name_field_offset() {
+    return byte_offset_of(CodeBlob, _name);
+  }
+
+  static ByteSize oop_maps_field_offset() {
+    return byte_offset_of(CodeBlob, _oop_maps);
+  }
 };
 
 class WhiteBox;
--- a/hotspot/src/share/vm/code/codeCache.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/code/codeCache.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -409,7 +409,7 @@
     }
     if (PrintCodeCacheExtension) {
       ResourceMark rm;
-      if (SegmentedCodeCache) {
+      if (_heaps->length() >= 1) {
         tty->print("%s", heap->name());
       } else {
         tty->print("CodeCache");
@@ -1211,7 +1211,7 @@
 
   int i = 0;
   FOR_ALL_HEAPS(heap) {
-    if (SegmentedCodeCache && Verbose) {
+    if ((_heaps->length() >= 1) && Verbose) {
       tty->print_cr("-- %s --", (*heap)->name());
     }
     FOR_ALL_BLOBS(cb, *heap) {
@@ -1360,7 +1360,7 @@
   FOR_ALL_HEAPS(heap_iterator) {
     CodeHeap* heap = (*heap_iterator);
     size_t total = (heap->high_boundary() - heap->low_boundary());
-    if (SegmentedCodeCache) {
+    if (_heaps->length() >= 1) {
       st->print("%s:", heap->name());
     } else {
       st->print("CodeCache:");
@@ -1397,7 +1397,7 @@
     nmethod* nm = iter.method();
     ResourceMark rm;
     char *method_name = nm->method()->name_and_sig_as_C_string();
-    st->print_cr("%d %d %s ["INTPTR_FORMAT", "INTPTR_FORMAT" - "INTPTR_FORMAT"]",
+    st->print_cr("%d %d %s [" INTPTR_FORMAT ", " INTPTR_FORMAT " - " INTPTR_FORMAT "]",
                  nm->compile_id(), nm->comp_level(), method_name, (intptr_t)nm->header_begin(),
                  (intptr_t)nm->code_begin(), (intptr_t)nm->code_end());
   }
--- a/hotspot/src/share/vm/code/codeCache.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/code/codeCache.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -78,6 +78,7 @@
   friend class VMStructs;
   friend class NMethodIterator;
   friend class WhiteBox;
+  friend class CodeCacheLoader;
  private:
   // CodeHeaps of the cache
   static GrowableArray<CodeHeap*>* _heaps;
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/vm/code/codeCacheExtensions.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,52 @@
+/*
+ * Copyright (c) 2012, 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.
+ *
+ */
+
+#ifndef SHARE_VM_CODE_CODE_CACHE_EXTENSIONS_HPP
+#define SHARE_VM_CODE_CODE_CACHE_EXTENSIONS_HPP
+
+#include "memory/allocation.hpp"
+
+class CodeCacheExtensionsSteps: AllStatic {
+public:
+  enum Step {
+    // Support for optional fine grain initialization hooks
+    // Note: these hooks must support refining the granularity
+    // (e.g. adding intermediate steps in the ordered enum
+    // if needed for future features)
+    Start,
+    VMVersion,
+    StubRoutines1,
+    Universe,
+    TemplateInterpreter,
+    Interpreter,
+    StubRoutines2,
+    InitGlobals,
+    CreateVM,
+    LastStep
+  };
+};
+
+#include "code/codeCacheExtensions_ext.hpp"
+
+#endif // SHARE_VM_CODE_CODE_CACHE_EXTENSIONS_HPP
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/vm/code/codeCacheExtensions_ext.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,130 @@
+/*
+ * Copyright (c) 2012, 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.
+ *
+ */
+
+#ifndef SHARE_VM_CODE_CODE_CACHE_EXTENSIONS_EXT_HPP
+#define SHARE_VM_CODE_CODE_CACHE_EXTENSIONS_EXT_HPP
+
+#include "utilities/macros.hpp"
+#include "memory/allocation.hpp"
+#include "utilities/globalDefinitions.hpp"
+#include "interpreter/bytecodes.hpp"
+
+class AdapterHandlerEntry;
+class CodeBlob;
+class CodeBuffer;
+class InterpreterMacroAssembler;
+class Template;
+
+// All the methods defined here are placeholders for possible extensions.
+
+class CodeCacheExtensions: AllStatic {
+  friend class CodeCacheDumper;
+
+public:
+  // init both code saving and loading
+  // Must be called very early, before any code is generated.
+  static void initialize() {}
+
+  // Check whether the generated interpreter will be saved.
+  static bool saving_generated_interpreter() { return false; }
+
+  // Check whether a pregenerated interpreter is used.
+  static bool use_pregenerated_interpreter() { return false; }
+
+  // Placeholder for additional VM initialization code
+  static void complete_step(CodeCacheExtensionsSteps::Step phase) {}
+
+  // Return false for newly generated code, on systems where it is not
+  // executable.
+  static bool is_executable(void *pc) { return true; }
+
+  // Return whether dynamically generated code can be executable
+  static bool support_dynamic_code() { return true; }
+
+  // Skip new code generation when known to be useless.
+  static bool skip_code_generation() { return false; }
+
+  // Skip stubs used only for compiled code support.
+  static bool skip_compiler_support() { return false; }
+
+  // Ignore UseFastSignatureHandlers when returning false
+  static bool support_fast_signature_handlers() { return true; }
+
+  /////////////////////////
+  // Handle generated code:
+  // - allow newly generated code to be shared
+  // - allow pregenerated code to be used in place of the newly generated one
+  //   (modifying pc).
+  // - support remapping when doing both save and load
+  // 'remap' can be set to false if the addresses handled are not referenced
+  // from code generated later.
+
+  // Associate a name to a generated codelet and possibly modify the pc
+  // Note: use instead the specialized versions when they exist:
+  // - handle_generated_blob for CodeBlob
+  // - handle_generated_handler for SignatureHandlers
+  // See also the optimized calls below that handle several PCs at once.
+  static void handle_generated_pc(address &pc, const char *name) {}
+
+  // Adds a safe definition of the codelet, for codelets used right after
+  // generation (else we would need to immediately stop the JVM and convert
+  // the generated code to executable format before being able to go further).
+  static void handle_generated_pc(address &pc, const char *name, address default_entry) {}
+
+  // Special cases
+
+  // Special case for CodeBlobs, which may require blob specific actions.
+  static CodeBlob* handle_generated_blob(CodeBlob* blob, const char *name = NULL) { return blob; }
+
+  // Special case for Signature Handlers.
+  static void handle_generated_handler(address &handler_start, const char *name, address handler_end) {}
+
+  // Support for generating different variants of the interpreter
+  // that can be dynamically selected after reload.
+  //
+  // - init_interpreter_assembler allows to configure the assembler for
+  //   the current variant
+  //
+  // - needs_other_interpreter_variant returns true as long as other
+  //   variants are needed.
+  //
+  // - skip_template_interpreter_entries returns true if new entries
+  //   need not be generated for this masm setup and this bytecode
+  //
+  // - completed_template_interpreter_entries is called after new
+  //   entries have been generated and installed, for any non skipped
+  //   bytecode.
+  static void init_interpreter_assembler(InterpreterMacroAssembler* masm, CodeBuffer* code) {}
+  static bool needs_other_interpreter_variant() { return false; }
+  static bool skip_template_interpreter_entries(Bytecodes::Code code) { return false; }
+  static void completed_template_interpreter_entries(InterpreterMacroAssembler* masm, Bytecodes::Code code) {}
+
+  // Code size optimization. May optimize the requested size.
+  static void size_blob(const char* name, int *updatable_size) {}
+
+  // ergonomics
+  static void set_ergonomics_flags() {}
+};
+
+#endif // SHARE_VM_CODE_CODE_CACHE_EXTENSIONS_EXT_HPP
--- a/hotspot/src/share/vm/code/exceptionHandlerTable.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/code/exceptionHandlerTable.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -186,7 +186,7 @@
 void ImplicitExceptionTable::print(address base) const {
   tty->print("{");
   for( uint i=0; i<len(); i++ )
-    tty->print("< "INTPTR_FORMAT", "INTPTR_FORMAT" > ",base + *adr(i), base + *(adr(i)+1));
+    tty->print("< " INTPTR_FORMAT ", " INTPTR_FORMAT " > ",base + *adr(i), base + *(adr(i)+1));
   tty->print_cr("}");
 }
 
--- a/hotspot/src/share/vm/code/nmethod.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/code/nmethod.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -2118,7 +2118,7 @@
   void maybe_print(oop* p) {
     if (_print_nm == NULL)  return;
     if (!_detected_scavenge_root)  _print_nm->print_on(tty, "new scavenge root");
-    tty->print_cr(""PTR_FORMAT"[offset=%d] detected scavengable oop "PTR_FORMAT" (found at "PTR_FORMAT")",
+    tty->print_cr("" PTR_FORMAT "[offset=%d] detected scavengable oop " PTR_FORMAT " (found at " PTR_FORMAT ")",
                   _print_nm, (int)((intptr_t)p - (intptr_t)_print_nm),
                   (void *)(*p), (intptr_t)p);
     (*p)->print();
@@ -2518,7 +2518,7 @@
       _nm->print_nmethod(true);
       _ok = false;
     }
-    tty->print_cr("*** non-oop "PTR_FORMAT" found at "PTR_FORMAT" (offset %d)",
+    tty->print_cr("*** non-oop " PTR_FORMAT " found at " PTR_FORMAT " (offset %d)",
                   (void *)(*p), (intptr_t)p, (int)((intptr_t)p - (intptr_t)_nm));
   }
   virtual void do_oop(narrowOop* p) { ShouldNotReachHere(); }
@@ -2642,7 +2642,7 @@
       _nm->print_nmethod(true);
       _ok = false;
     }
-    tty->print_cr("*** scavengable oop "PTR_FORMAT" found at "PTR_FORMAT" (offset %d)",
+    tty->print_cr("*** scavengable oop " PTR_FORMAT " found at " PTR_FORMAT " (offset %d)",
                   (void *)(*p), (intptr_t)p, (int)((intptr_t)p - (intptr_t)_nm));
     (*p)->print();
   }
@@ -2687,7 +2687,7 @@
   print_on(tty, NULL);
 
   if (WizardMode) {
-    tty->print("((nmethod*) "INTPTR_FORMAT ") ", this);
+    tty->print("((nmethod*) " INTPTR_FORMAT ") ", this);
     tty->print(" for method " INTPTR_FORMAT , (address)method());
     tty->print(" { ");
     if (is_in_use())      tty->print("in_use ");
--- a/hotspot/src/share/vm/code/stubs.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/code/stubs.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 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
@@ -261,3 +261,17 @@
     stub_print(s);
   }
 }
+
+// Fixup for pregenerated code
+void StubQueue::fix_buffer(address buffer, address queue_end, address buffer_end, int number_of_stubs) {
+  const int extra_bytes = CodeEntryAlignment;
+  _stub_buffer = buffer;
+  _queue_begin = 0;
+  _queue_end = queue_end - buffer;
+  _number_of_stubs = number_of_stubs;
+  int size = buffer_end - buffer;
+  // Note: _buffer_limit must differ from _queue_end in the iteration loops
+  // => add extra space at the end (preserving alignment for asserts) if needed
+  if (buffer_end == queue_end) size += extra_bytes;
+  _buffer_limit = _buffer_size = size;
+}
--- a/hotspot/src/share/vm/code/stubs.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/code/stubs.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 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
@@ -216,6 +216,9 @@
   // Debugging/printing
   void  verify();                                // verifies the stub queue
   void  print();                                 // prints information about the stub queue
+
+  // Fixup for pregenerated code
+  void fix_buffer(address buffer, address queue_end, address buffer_end, int number_of_stubs);
 };
 
 #endif // SHARE_VM_CODE_STUBS_HPP
--- a/hotspot/src/share/vm/compiler/compileBroker.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/compiler/compileBroker.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -172,7 +172,7 @@
   }
 
   void log_nmethod(JavaThread* thread, nmethod* nm) {
-    log(thread, "nmethod %d%s " INTPTR_FORMAT " code ["INTPTR_FORMAT ", " INTPTR_FORMAT "]",
+    log(thread, "nmethod %d%s " INTPTR_FORMAT " code [" INTPTR_FORMAT ", " INTPTR_FORMAT "]",
         nm->compile_id(), nm->is_osr_method() ? "%" : "",
         p2i(nm), p2i(nm->code_begin()), p2i(nm->code_end()));
   }
--- a/hotspot/src/share/vm/compiler/compilerOracle.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/compiler/compilerOracle.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1998, 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
@@ -578,7 +578,7 @@
                       int* bytes_read, const char*& error_msg) {
   *bytes_read = 0;
   error_msg = NULL;
-  if (2 == sscanf(line, "%*[ \t]%255" RANGESLASH "%*[ ]" "%255"  RANGE0 "%n", class_name, method_name, bytes_read)) {
+  if (2 == sscanf(line, "%*[ \t]%255" RANGESLASH "%*[ ]" "%255" RANGE0 "%n", class_name, method_name, bytes_read)) {
     *c_mode = check_mode(class_name, error_msg);
     *m_mode = check_mode(method_name, error_msg);
     return *c_mode != MethodMatcher::Unknown && *m_mode != MethodMatcher::Unknown;
@@ -586,8 +586,6 @@
   return false;
 }
 
-
-
 // Scan next flag and value in line, return MethodMatcher object on success, NULL on failure.
 // On failure, error_msg contains description for the first error.
 // For future extensions: set error_msg on first error.
@@ -665,7 +663,7 @@
           jio_snprintf(errorbuf, buf_size, "  Value cannot be read for flag %s of type %s", flag, type);
         }
       } else {
-        jio_snprintf(errorbuf, sizeof(errorbuf), "  Value cannot be read for flag %s of type %s", flag, type);
+        jio_snprintf(errorbuf, buf_size, "  Value cannot be read for flag %s of type %s", flag, type);
       }
     } else if (strcmp(type, "double") == 0) {
       char buffer[2][256];
@@ -680,10 +678,10 @@
         jio_snprintf(errorbuf, buf_size, "  Value cannot be read for flag %s of type %s", flag, type);
       }
     } else {
-      jio_snprintf(errorbuf, sizeof(errorbuf), "  Type %s not supported ", type);
+      jio_snprintf(errorbuf, buf_size, "  Type %s not supported ", type);
     }
   } else {
-    jio_snprintf(errorbuf, sizeof(errorbuf), "  Flag name for type %s should be alphanumeric ", type);
+    jio_snprintf(errorbuf, buf_size, "  Flag name for type %s should be alphanumeric ", type);
   }
   return NULL;
 }
--- a/hotspot/src/share/vm/compiler/disassembler.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/compiler/disassembler.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -65,7 +65,7 @@
 Disassembler::decode_func_virtual Disassembler::_decode_instructions_virtual = NULL;
 Disassembler::decode_func Disassembler::_decode_instructions = NULL;
 
-static const char hsdis_library_name[] = "hsdis-"HOTSPOT_LIB_ARCH;
+static const char hsdis_library_name[] = "hsdis-" HOTSPOT_LIB_ARCH;
 static const char decode_instructions_virtual_name[] = "decode_instructions_virtual";
 static const char decode_instructions_name[] = "decode_instructions";
 static bool use_new_version = true;
--- a/hotspot/src/share/vm/gc/cms/concurrentMarkSweepGeneration.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/cms/concurrentMarkSweepGeneration.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -688,18 +688,18 @@
            "The CMS generation should be the old generation");
     uint level = 1;
     if (Verbose) {
-      gclog_or_tty->print("[%u %s-%s: "SIZE_FORMAT"("SIZE_FORMAT")]",
+      gclog_or_tty->print("[%u %s-%s: " SIZE_FORMAT "(" SIZE_FORMAT ")]",
         level, short_name(), s, used(), capacity());
     } else {
-      gclog_or_tty->print("[%u %s-%s: "SIZE_FORMAT"K("SIZE_FORMAT"K)]",
+      gclog_or_tty->print("[%u %s-%s: " SIZE_FORMAT "K(" SIZE_FORMAT "K)]",
         level, short_name(), s, used() / K, capacity() / K);
     }
   }
   if (Verbose) {
-    gclog_or_tty->print(" "SIZE_FORMAT"("SIZE_FORMAT")",
+    gclog_or_tty->print(" " SIZE_FORMAT "(" SIZE_FORMAT ")",
               gch->used(), gch->capacity());
   } else {
-    gclog_or_tty->print(" "SIZE_FORMAT"K("SIZE_FORMAT"K)",
+    gclog_or_tty->print(" " SIZE_FORMAT "K(" SIZE_FORMAT "K)",
               gch->used() / K, gch->capacity() / K);
   }
 }
@@ -729,8 +729,8 @@
   bool   res = (available >= av_promo) || (available >= max_promotion_in_bytes);
   if (Verbose && PrintGCDetails) {
     gclog_or_tty->print_cr(
-      "CMS: promo attempt is%s safe: available("SIZE_FORMAT") %s av_promo("SIZE_FORMAT"),"
-      "max_promo("SIZE_FORMAT")",
+      "CMS: promo attempt is%s safe: available(" SIZE_FORMAT ") %s av_promo(" SIZE_FORMAT "),"
+      "max_promo(" SIZE_FORMAT ")",
       res? "":" not", available, res? ">=":"<",
       av_promo, max_promotion_in_bytes);
   }
@@ -805,18 +805,18 @@
               desired_free_percentage);
       gclog_or_tty->print_cr("  Maximum free fraction %f",
               maximum_free_percentage);
-      gclog_or_tty->print_cr("  Capacity "SIZE_FORMAT, capacity()/1000);
-      gclog_or_tty->print_cr("  Desired capacity "SIZE_FORMAT,
+      gclog_or_tty->print_cr("  Capacity " SIZE_FORMAT, capacity()/1000);
+      gclog_or_tty->print_cr("  Desired capacity " SIZE_FORMAT,
               desired_capacity/1000);
       GenCollectedHeap* gch = GenCollectedHeap::heap();
       assert(gch->is_old_gen(this), "The CMS generation should always be the old generation");
       size_t young_size = gch->young_gen()->capacity();
       gclog_or_tty->print_cr("  Young gen size " SIZE_FORMAT, young_size / 1000);
-      gclog_or_tty->print_cr("  unsafe_max_alloc_nogc "SIZE_FORMAT,
+      gclog_or_tty->print_cr("  unsafe_max_alloc_nogc " SIZE_FORMAT,
               unsafe_max_alloc_nogc()/1000);
-      gclog_or_tty->print_cr("  contiguous available "SIZE_FORMAT,
+      gclog_or_tty->print_cr("  contiguous available " SIZE_FORMAT,
               contiguous_available()/1000);
-      gclog_or_tty->print_cr("  Expand by "SIZE_FORMAT" (bytes)",
+      gclog_or_tty->print_cr("  Expand by " SIZE_FORMAT " (bytes)",
               expand_bytes);
     }
     // safe if expansion fails
@@ -1182,8 +1182,8 @@
     stats().print_on(gclog_or_tty);
     gclog_or_tty->print_cr("time_until_cms_gen_full %3.7f",
       stats().time_until_cms_gen_full());
-    gclog_or_tty->print_cr("free="SIZE_FORMAT, _cmsGen->free());
-    gclog_or_tty->print_cr("contiguous_available="SIZE_FORMAT,
+    gclog_or_tty->print_cr("free=" SIZE_FORMAT, _cmsGen->free());
+    gclog_or_tty->print_cr("contiguous_available=" SIZE_FORMAT,
                            _cmsGen->contiguous_available());
     gclog_or_tty->print_cr("promotion_rate=%g", stats().promotion_rate());
     gclog_or_tty->print_cr("cms_allocation_rate=%g", stats().cms_allocation_rate());
@@ -2160,8 +2160,8 @@
     assert(_numObjectsPromoted == 0, "check");
     assert(_numWordsPromoted   == 0, "check");
     if (Verbose && PrintGC) {
-      gclog_or_tty->print("Allocated "SIZE_FORMAT" objects, "
-                          SIZE_FORMAT" bytes concurrently",
+      gclog_or_tty->print("Allocated " SIZE_FORMAT " objects, "
+                          SIZE_FORMAT " bytes concurrently",
       _numObjectsAllocated, _numWordsAllocated*sizeof(HeapWord));
     }
     _numObjectsAllocated = 0;
@@ -2241,8 +2241,8 @@
     assert(_numObjectsAllocated == 0, "check");
     assert(_numWordsAllocated == 0, "check");
     if (Verbose && PrintGC) {
-      gclog_or_tty->print("Promoted "SIZE_FORMAT" objects, "
-                          SIZE_FORMAT" bytes",
+      gclog_or_tty->print("Promoted " SIZE_FORMAT " objects, "
+                          SIZE_FORMAT " bytes",
                  _numObjectsPromoted, _numWordsPromoted*sizeof(HeapWord));
     }
     _numObjectsPromoted = 0;
@@ -2252,7 +2252,7 @@
   if (PrintGC && Verbose) {
     // Call down the chain in contiguous_available needs the freelistLock
     // so print this out before releasing the freeListLock.
-    gclog_or_tty->print(" Contiguous available "SIZE_FORMAT" bytes ",
+    gclog_or_tty->print(" Contiguous available " SIZE_FORMAT " bytes ",
                         contiguous_available());
   }
 }
@@ -2340,7 +2340,7 @@
     HeapWord* addr = _marks->offsetToHeapWord(offset);
     if (!_marks->isMarked(addr)) {
       oop(addr)->print_on(gclog_or_tty);
-      gclog_or_tty->print_cr(" ("INTPTR_FORMAT" should have been marked)", p2i(addr));
+      gclog_or_tty->print_cr(" (" INTPTR_FORMAT " should have been marked)", p2i(addr));
       _failed = true;
     }
     return true;
@@ -2702,9 +2702,11 @@
   // Not unloading classes this cycle
   assert(!should_unload_classes(), "Inconsistency!");
 
+  // If we are not unloading classes then add SO_AllCodeCache to root
+  // scanning options.
+  add_root_scanning_option(rso);
+
   if ((!verifying() || unloaded_classes_last_cycle()) && should_verify) {
-    // Include symbols, strings and code cache elements to prevent their resurrection.
-    add_root_scanning_option(rso);
     set_verifying(true);
   } else if (verifying() && !should_verify) {
     // We were verifying, but some verification flags got disabled.
@@ -4269,7 +4271,7 @@
   verify_overflow_empty();
 
   if (PrintGCDetails) {
-    gclog_or_tty->print("[YG occupancy: "SIZE_FORMAT" K ("SIZE_FORMAT" K)]",
+    gclog_or_tty->print("[YG occupancy: " SIZE_FORMAT " K (" SIZE_FORMAT " K)]",
                         _young_gen->used() / K,
                         _young_gen->capacity() / K);
   }
@@ -4381,8 +4383,8 @@
   if (ser_ovflw > 0) {
     if (PrintCMSStatistics != 0) {
       gclog_or_tty->print_cr("Marking stack overflow (benign) "
-        "(pmc_pc="SIZE_FORMAT", pmc_rm="SIZE_FORMAT", kac="SIZE_FORMAT
-        ", kac_preclean="SIZE_FORMAT")",
+        "(pmc_pc=" SIZE_FORMAT ", pmc_rm=" SIZE_FORMAT ", kac=" SIZE_FORMAT
+        ", kac_preclean=" SIZE_FORMAT ")",
         _ser_pmc_preclean_ovflw, _ser_pmc_remark_ovflw,
         _ser_kac_ovflw, _ser_kac_preclean_ovflw);
     }
@@ -4395,7 +4397,7 @@
   if (_par_pmc_remark_ovflw > 0 || _par_kac_ovflw > 0) {
     if (PrintCMSStatistics != 0) {
       gclog_or_tty->print_cr("Work queue overflow (benign) "
-        "(pmc_rm="SIZE_FORMAT", kac="SIZE_FORMAT")",
+        "(pmc_rm=" SIZE_FORMAT ", kac=" SIZE_FORMAT ")",
         _par_pmc_remark_ovflw, _par_kac_ovflw);
     }
     _par_pmc_remark_ovflw = 0;
@@ -4403,12 +4405,12 @@
   }
   if (PrintCMSStatistics != 0) {
      if (_markStack._hit_limit > 0) {
-       gclog_or_tty->print_cr(" (benign) Hit max stack size limit ("SIZE_FORMAT")",
+       gclog_or_tty->print_cr(" (benign) Hit max stack size limit (" SIZE_FORMAT ")",
                               _markStack._hit_limit);
      }
      if (_markStack._failed_double > 0) {
-       gclog_or_tty->print_cr(" (benign) Failed stack doubling ("SIZE_FORMAT"),"
-                              " current capacity "SIZE_FORMAT,
+       gclog_or_tty->print_cr(" (benign) Failed stack doubling (" SIZE_FORMAT "),"
+                              " current capacity " SIZE_FORMAT,
                               _markStack._failed_double,
                               _markStack.capacity());
      }
@@ -5161,7 +5163,7 @@
                                                &markFromDirtyCardsClosure);
       verify_work_stacks_empty();
       if (PrintCMSStatistics != 0) {
-        gclog_or_tty->print(" (re-scanned "SIZE_FORMAT" dirty cards in cms gen) ",
+        gclog_or_tty->print(" (re-scanned " SIZE_FORMAT " dirty cards in cms gen) ",
           markFromDirtyCardsClosure.num_dirty_cards());
       }
     }
@@ -6035,8 +6037,8 @@
   } else if (_failed_double++ == 0 && !CMSConcurrentMTEnabled && PrintGCDetails) {
     // Failed to double capacity, continue;
     // we print a detail message only once per CMS cycle.
-    gclog_or_tty->print(" (benign) Failed to expand marking stack from "SIZE_FORMAT"K to "
-            SIZE_FORMAT"K",
+    gclog_or_tty->print(" (benign) Failed to expand marking stack from " SIZE_FORMAT "K to "
+            SIZE_FORMAT "K",
             _capacity / K, new_capacity / K);
   }
 }
@@ -7335,25 +7337,25 @@
     ShouldNotReachHere();
   }
   if (Verbose && PrintGC) {
-    gclog_or_tty->print("Collected "SIZE_FORMAT" objects, " SIZE_FORMAT " bytes",
+    gclog_or_tty->print("Collected " SIZE_FORMAT " objects, " SIZE_FORMAT " bytes",
                         _numObjectsFreed, _numWordsFreed*sizeof(HeapWord));
-    gclog_or_tty->print_cr("\nLive "SIZE_FORMAT" objects,  "
-                           SIZE_FORMAT" bytes  "
-      "Already free "SIZE_FORMAT" objects, "SIZE_FORMAT" bytes",
+    gclog_or_tty->print_cr("\nLive " SIZE_FORMAT " objects,  "
+                           SIZE_FORMAT " bytes  "
+      "Already free " SIZE_FORMAT " objects, " SIZE_FORMAT " bytes",
       _numObjectsLive, _numWordsLive*sizeof(HeapWord),
       _numObjectsAlreadyFree, _numWordsAlreadyFree*sizeof(HeapWord));
     size_t totalBytes = (_numWordsFreed + _numWordsLive + _numWordsAlreadyFree)
                         * sizeof(HeapWord);
-    gclog_or_tty->print_cr("Total sweep: "SIZE_FORMAT" bytes", totalBytes);
+    gclog_or_tty->print_cr("Total sweep: " SIZE_FORMAT " bytes", totalBytes);
 
     if (PrintCMSStatistics && CMSVerifyReturnedBytes) {
       size_t indexListReturnedBytes = _sp->sumIndexedFreeListArrayReturnedBytes();
       size_t dict_returned_bytes = _sp->dictionary()->sum_dict_returned_bytes();
       size_t returned_bytes = indexListReturnedBytes + dict_returned_bytes;
-      gclog_or_tty->print("Returned "SIZE_FORMAT" bytes", returned_bytes);
-      gclog_or_tty->print("   Indexed List Returned "SIZE_FORMAT" bytes",
+      gclog_or_tty->print("Returned " SIZE_FORMAT " bytes", returned_bytes);
+      gclog_or_tty->print("   Indexed List Returned " SIZE_FORMAT " bytes",
         indexListReturnedBytes);
-      gclog_or_tty->print_cr("        Dictionary Returned "SIZE_FORMAT" bytes",
+      gclog_or_tty->print_cr("        Dictionary Returned " SIZE_FORMAT " bytes",
         dict_returned_bytes);
     }
   }
@@ -7432,12 +7434,12 @@
     // coalesced chunk to the appropriate free list.
     if (inFreeRange()) {
       assert(freeFinger() >= _sp->bottom() && freeFinger() < _limit,
-             err_msg("freeFinger() " PTR_FORMAT" is out-of-bounds", p2i(freeFinger())));
+             err_msg("freeFinger() " PTR_FORMAT " is out-of-bounds", p2i(freeFinger())));
       flush_cur_free_chunk(freeFinger(),
                            pointer_delta(addr, freeFinger()));
       if (CMSTraceSweeper) {
         gclog_or_tty->print("Sweep: last chunk: ");
-        gclog_or_tty->print("put_free_blk " PTR_FORMAT " ("SIZE_FORMAT") "
+        gclog_or_tty->print("put_free_blk " PTR_FORMAT " (" SIZE_FORMAT ") "
                    "[coalesced:%d]\n",
                    p2i(freeFinger()), pointer_delta(addr, freeFinger()),
                    lastFreeRangeCoalesced() ? 1 : 0);
--- a/hotspot/src/share/vm/gc/cms/parNewGeneration.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/cms/parNewGeneration.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1021,7 +1021,7 @@
   to()->set_concurrent_iteration_safe_limit(to()->top());
 
   if (ResizePLAB) {
-    plab_stats()->adjust_desired_plab_sz(active_workers);
+    plab_stats()->adjust_desired_plab_sz();
   }
 
   if (PrintGC && !PrintGCDetails) {
@@ -1059,6 +1059,10 @@
   _gc_tracer.report_gc_end(_gc_timer->gc_end(), _gc_timer->time_partitions());
 }
 
+size_t ParNewGeneration::desired_plab_sz() {
+  return _plab_stats.desired_plab_sz(GenCollectedHeap::heap()->workers()->active_workers());
+}
+
 static int sum;
 void ParNewGeneration::waste_some_time() {
   for (int i = 0; i < 100; i++) {
--- a/hotspot/src/share/vm/gc/cms/parNewGeneration.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/cms/parNewGeneration.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -411,9 +411,7 @@
     return &_plab_stats;
   }
 
-  size_t desired_plab_sz() {
-    return _plab_stats.desired_plab_sz();
-  }
+  size_t desired_plab_sz();
 
   const ParNewTracer* gc_tracer() const {
     return &_gc_tracer;
--- a/hotspot/src/share/vm/gc/g1/collectionSetChooser.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/collectionSetChooser.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -119,7 +119,7 @@
   }
   guarantee(sum_of_reclaimable_bytes == _remaining_reclaimable_bytes,
             err_msg("reclaimable bytes inconsistent, "
-                    "remaining: "SIZE_FORMAT" sum: "SIZE_FORMAT,
+                    "remaining: " SIZE_FORMAT " sum: " SIZE_FORMAT,
                     _remaining_reclaimable_bytes, sum_of_reclaimable_bytes));
 }
 #endif // !PRODUCT
--- a/hotspot/src/share/vm/gc/g1/collectionSetChooser.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/collectionSetChooser.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -92,7 +92,7 @@
     regions_at_put(_curr_index, NULL);
     assert(hr->reclaimable_bytes() <= _remaining_reclaimable_bytes,
            err_msg("remaining reclaimable bytes inconsistent "
-                   "from region: "SIZE_FORMAT" remaining: "SIZE_FORMAT,
+                   "from region: " SIZE_FORMAT " remaining: " SIZE_FORMAT,
                    hr->reclaimable_bytes(), _remaining_reclaimable_bytes));
     _remaining_reclaimable_bytes -= hr->reclaimable_bytes();
     _curr_index += 1;
--- a/hotspot/src/share/vm/gc/g1/concurrentMark.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/concurrentMark.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -307,7 +307,7 @@
     if (PrintGCDetails && Verbose) {
       // Failed to double capacity, continue;
       gclog_or_tty->print(" (benign) Failed to expand marking stack capacity from "
-                          SIZE_FORMAT"K to " SIZE_FORMAT"K",
+                          SIZE_FORMAT "K to " SIZE_FORMAT "K",
                           _capacity / K, new_capacity / K);
     }
   }
@@ -555,7 +555,7 @@
   _verbose_level = verbose_level;
 
   if (verbose_low()) {
-    gclog_or_tty->print_cr("[global] init, heap start = "PTR_FORMAT", "
+    gclog_or_tty->print_cr("[global] init, heap start = " PTR_FORMAT ", "
                            "heap end = " PTR_FORMAT, p2i(_heap_start), p2i(_heap_end));
   }
 
@@ -802,7 +802,7 @@
     // in a STW phase.
     assert(!concurrent_marking_in_progress(), "invariant");
     assert(out_of_regions(),
-           err_msg("only way to get here: _finger: "PTR_FORMAT", _heap_end: "PTR_FORMAT,
+           err_msg("only way to get here: _finger: " PTR_FORMAT ", _heap_end: " PTR_FORMAT,
                    p2i(_finger), p2i(_heap_end)));
   }
 }
@@ -1424,7 +1424,7 @@
 
     assert(start <= hr->end() && start <= ntams && ntams <= hr->end(),
            err_msg("Preconditions not met - "
-                   "start: "PTR_FORMAT", ntams: "PTR_FORMAT", end: "PTR_FORMAT,
+                   "start: " PTR_FORMAT ", ntams: " PTR_FORMAT ", end: " PTR_FORMAT,
                    p2i(start), p2i(ntams), p2i(hr->end())));
 
     // Find the first marked object at or after "start".
@@ -1725,10 +1725,10 @@
       }
 
       assert(end_idx <= _card_bm->size(),
-             err_msg("oob: end_idx=  "SIZE_FORMAT", bitmap size= "SIZE_FORMAT,
+             err_msg("oob: end_idx=  " SIZE_FORMAT ", bitmap size= " SIZE_FORMAT,
                      end_idx, _card_bm->size()));
       assert(start_idx < _card_bm->size(),
-             err_msg("oob: start_idx=  "SIZE_FORMAT", bitmap size= "SIZE_FORMAT,
+             err_msg("oob: start_idx=  " SIZE_FORMAT ", bitmap size= " SIZE_FORMAT,
                      start_idx, _card_bm->size()));
 
       _cm->set_card_bitmap_range(_card_bm, start_idx, end_idx, true /* is_par */);
@@ -2133,7 +2133,7 @@
       oop obj = oopDesc::load_decode_heap_oop(p);
       if (_cm->verbose_high()) {
         gclog_or_tty->print_cr("\t[%u] we're looking at location "
-                               "*"PTR_FORMAT" = "PTR_FORMAT,
+                               "*" PTR_FORMAT " = " PTR_FORMAT,
                                _task->worker_id(), p2i(p), p2i((void*) obj));
       }
 
@@ -2660,9 +2660,9 @@
       HeapWord*   limit         = curr_region->next_top_at_mark_start();
 
       if (verbose_low()) {
-        gclog_or_tty->print_cr("[%u] curr_region = "PTR_FORMAT" "
-                               "["PTR_FORMAT", "PTR_FORMAT"), "
-                               "limit = "PTR_FORMAT,
+        gclog_or_tty->print_cr("[%u] curr_region = " PTR_FORMAT " "
+                               "[" PTR_FORMAT ", " PTR_FORMAT "), "
+                               "limit = " PTR_FORMAT,
                                worker_id, p2i(curr_region), p2i(bottom), p2i(end), p2i(limit));
       }
 
@@ -2677,7 +2677,7 @@
 
       if (limit > bottom) {
         if (verbose_low()) {
-          gclog_or_tty->print_cr("[%u] region "PTR_FORMAT" is not empty, "
+          gclog_or_tty->print_cr("[%u] region " PTR_FORMAT " is not empty, "
                                  "returning it ", worker_id, p2i(curr_region));
         }
         return curr_region;
@@ -2685,7 +2685,7 @@
         assert(limit == bottom,
                "the region limit should be at bottom");
         if (verbose_low()) {
-          gclog_or_tty->print_cr("[%u] region "PTR_FORMAT" is empty, "
+          gclog_or_tty->print_cr("[%u] region " PTR_FORMAT " is empty, "
                                  "returning NULL", worker_id, p2i(curr_region));
         }
         // we return NULL and the caller should try calling
@@ -2697,13 +2697,13 @@
       if (verbose_low()) {
         if (curr_region == NULL) {
           gclog_or_tty->print_cr("[%u] found uncommitted region, moving finger, "
-                                 "global finger = "PTR_FORMAT", "
-                                 "our finger = "PTR_FORMAT,
+                                 "global finger = " PTR_FORMAT ", "
+                                 "our finger = " PTR_FORMAT,
                                  worker_id, p2i(_finger), p2i(finger));
         } else {
           gclog_or_tty->print_cr("[%u] somebody else moved the finger, "
-                                 "global finger = "PTR_FORMAT", "
-                                 "our finger = "PTR_FORMAT,
+                                 "global finger = " PTR_FORMAT ", "
+                                 "our finger = " PTR_FORMAT,
                                  worker_id, p2i(_finger), p2i(finger));
         }
       }
@@ -2739,7 +2739,7 @@
 
   void do_object_work(oop obj) {
     guarantee(!_g1h->obj_in_cs(obj),
-              err_msg("obj: "PTR_FORMAT" in CSet, phase: %s, info: %d",
+              err_msg("obj: " PTR_FORMAT " in CSet, phase: %s, info: %d",
                       p2i((void*) obj), phase_str(), _info));
   }
 
@@ -2800,7 +2800,7 @@
     // here.
     HeapRegion* global_hr = _g1h->heap_region_containing_raw(global_finger);
     guarantee(global_hr == NULL || global_finger == global_hr->bottom(),
-              err_msg("global finger: "PTR_FORMAT" region: "HR_FORMAT,
+              err_msg("global finger: " PTR_FORMAT " region: " HR_FORMAT,
                       p2i(global_finger), HR_FORMAT_PARAMS(global_hr)));
   }
 
@@ -2814,7 +2814,7 @@
       HeapRegion* task_hr = _g1h->heap_region_containing_raw(task_finger);
       guarantee(task_hr == NULL || task_finger == task_hr->bottom() ||
                 !task_hr->in_collection_set(),
-                err_msg("task finger: "PTR_FORMAT" region: "HR_FORMAT,
+                err_msg("task finger: " PTR_FORMAT " region: " HR_FORMAT,
                         p2i(task_finger), HR_FORMAT_PARAMS(task_hr)));
     }
   }
@@ -2856,8 +2856,8 @@
 
     assert(start <= limit && limit <= hr->top() && hr->top() <= hr->end(),
            err_msg("Preconditions not met - "
-                   "start: "PTR_FORMAT", limit: "PTR_FORMAT", "
-                   "top: "PTR_FORMAT", end: "PTR_FORMAT,
+                   "start: " PTR_FORMAT ", limit: " PTR_FORMAT ", "
+                   "top: " PTR_FORMAT ", end: " PTR_FORMAT,
                    p2i(start), p2i(limit), p2i(hr->top()), p2i(hr->end())));
 
     assert(hr->next_marked_bytes() == 0, "Precondition");
@@ -3118,7 +3118,7 @@
 #ifndef PRODUCT
 // for debugging purposes
 void ConcurrentMark::print_finger() {
-  gclog_or_tty->print_cr("heap ["PTR_FORMAT", "PTR_FORMAT"), global finger = "PTR_FORMAT,
+  gclog_or_tty->print_cr("heap [" PTR_FORMAT ", " PTR_FORMAT "), global finger = " PTR_FORMAT,
                          p2i(_heap_start), p2i(_heap_end), p2i(_finger));
   for (uint i = 0; i < _max_worker_id; ++i) {
     gclog_or_tty->print("   %u: " PTR_FORMAT, i, p2i(_tasks[i]->finger()));
@@ -3203,7 +3203,7 @@
         "claim_region() should have filtered out continues humongous regions");
 
   if (_cm->verbose_low()) {
-    gclog_or_tty->print_cr("[%u] setting up for region "PTR_FORMAT,
+    gclog_or_tty->print_cr("[%u] setting up for region " PTR_FORMAT,
                            _worker_id, p2i(hr));
   }
 
@@ -3220,7 +3220,7 @@
   if (limit == bottom) {
     if (_cm->verbose_low()) {
       gclog_or_tty->print_cr("[%u] found an empty region "
-                             "["PTR_FORMAT", "PTR_FORMAT")",
+                             "[" PTR_FORMAT ", " PTR_FORMAT ")",
                              _worker_id, p2i(bottom), p2i(limit));
     }
     // The region was collected underneath our feet.
@@ -3252,7 +3252,7 @@
 void CMTask::giveup_current_region() {
   assert(_curr_region != NULL, "invariant");
   if (_cm->verbose_low()) {
-    gclog_or_tty->print_cr("[%u] giving up region "PTR_FORMAT,
+    gclog_or_tty->print_cr("[%u] giving up region " PTR_FORMAT,
                            _worker_id, p2i(_curr_region));
   }
   clear_region_fields();
@@ -3374,7 +3374,7 @@
 
   if (_cm->verbose_medium()) {
       gclog_or_tty->print_cr("[%u] regular clock, interval = %1.2lfms, "
-                        "scanned = "SIZE_FORMAT"%s, refs reached = "SIZE_FORMAT"%s",
+                        "scanned = " SIZE_FORMAT "%s, refs reached = " SIZE_FORMAT "%s",
                         _worker_id, last_interval_ms,
                         _words_scanned,
                         (_words_scanned >= _words_scanned_limit) ? " (*)" : "",
@@ -3543,7 +3543,7 @@
       statsOnly( ++_local_pops );
 
       if (_cm->verbose_high()) {
-        gclog_or_tty->print_cr("[%u] popped "PTR_FORMAT, _worker_id,
+        gclog_or_tty->print_cr("[%u] popped " PTR_FORMAT, _worker_id,
                                p2i((void*) obj));
       }
 
@@ -3900,8 +3900,8 @@
 
       if (_cm->verbose_low()) {
         gclog_or_tty->print_cr("[%u] we're scanning part "
-                               "["PTR_FORMAT", "PTR_FORMAT") "
-                               "of region "HR_FORMAT,
+                               "[" PTR_FORMAT ", " PTR_FORMAT ") "
+                               "of region " HR_FORMAT,
                                _worker_id, p2i(_finger), p2i(_region_limit),
                                HR_FORMAT_PARAMS(_curr_region));
       }
@@ -3988,7 +3988,7 @@
 
         if (_cm->verbose_low()) {
           gclog_or_tty->print_cr("[%u] we successfully claimed "
-                                 "region "PTR_FORMAT,
+                                 "region " PTR_FORMAT,
                                  _worker_id, p2i(claimed_region));
         }
 
@@ -4049,7 +4049,7 @@
 
       if (_cm->try_stealing(_worker_id, &_hash_seed, obj)) {
         if (_cm->verbose_medium()) {
-          gclog_or_tty->print_cr("[%u] stolen "PTR_FORMAT" successfully",
+          gclog_or_tty->print_cr("[%u] stolen " PTR_FORMAT " successfully",
                                  _worker_id, p2i((void*) obj));
         }
 
@@ -4257,7 +4257,7 @@
 // identify them easily in a large log file.
 #define G1PPRL_LINE_PREFIX            "###"
 
-#define G1PPRL_ADDR_BASE_FORMAT    " "PTR_FORMAT"-"PTR_FORMAT
+#define G1PPRL_ADDR_BASE_FORMAT    " " PTR_FORMAT "-" PTR_FORMAT
 #ifdef _LP64
 #define G1PPRL_ADDR_BASE_H_FORMAT  " %37s"
 #else // _LP64
@@ -4267,16 +4267,16 @@
 // For per-region info
 #define G1PPRL_TYPE_FORMAT            "   %-4s"
 #define G1PPRL_TYPE_H_FORMAT          "   %4s"
-#define G1PPRL_BYTE_FORMAT            "  "SIZE_FORMAT_W(9)
+#define G1PPRL_BYTE_FORMAT            "  " SIZE_FORMAT_W(9)
 #define G1PPRL_BYTE_H_FORMAT          "  %9s"
 #define G1PPRL_DOUBLE_FORMAT          "  %14.1f"
 #define G1PPRL_DOUBLE_H_FORMAT        "  %14s"
 
 // For summary info
-#define G1PPRL_SUM_ADDR_FORMAT(tag)    "  "tag":"G1PPRL_ADDR_BASE_FORMAT
-#define G1PPRL_SUM_BYTE_FORMAT(tag)    "  "tag": "SIZE_FORMAT
-#define G1PPRL_SUM_MB_FORMAT(tag)      "  "tag": %1.2f MB"
-#define G1PPRL_SUM_MB_PERC_FORMAT(tag) G1PPRL_SUM_MB_FORMAT(tag)" / %1.2f %%"
+#define G1PPRL_SUM_ADDR_FORMAT(tag)    "  " tag ":" G1PPRL_ADDR_BASE_FORMAT
+#define G1PPRL_SUM_BYTE_FORMAT(tag)    "  " tag ": " SIZE_FORMAT
+#define G1PPRL_SUM_MB_FORMAT(tag)      "  " tag ": %1.2f MB"
+#define G1PPRL_SUM_MB_PERC_FORMAT(tag) G1PPRL_SUM_MB_FORMAT(tag) " / %1.2f %%"
 
 G1PrintRegionLivenessInfoClosure::
 G1PrintRegionLivenessInfoClosure(outputStream* out, const char* phase_name)
--- a/hotspot/src/share/vm/gc/g1/concurrentMark.inline.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/concurrentMark.inline.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -197,8 +197,8 @@
   assert(_bmStartWord <= (addr) && (addr) < (_bmStartWord + _bmWordSize),      \
          "outside underlying space?");                                         \
   assert(G1CollectedHeap::heap()->is_in_exact(addr),                           \
-         err_msg("Trying to access not available bitmap "PTR_FORMAT            \
-                 " corresponding to "PTR_FORMAT" (%u)",                        \
+         err_msg("Trying to access not available bitmap " PTR_FORMAT           \
+                 " corresponding to " PTR_FORMAT " (%u)",                      \
                  p2i(this), p2i(addr), G1CollectedHeap::heap()->addr_to_region(addr)));
 
 inline void CMBitMap::mark(HeapWord* addr) {
@@ -344,7 +344,7 @@
 
 inline void CMTask::deal_with_reference(oop obj) {
   if (_cm->verbose_high()) {
-    gclog_or_tty->print_cr("[%u] we're dealing with reference = "PTR_FORMAT,
+    gclog_or_tty->print_cr("[%u] we're dealing with reference = " PTR_FORMAT,
                            _worker_id, p2i((void*) obj));
   }
 
@@ -393,7 +393,7 @@
   // assert that word_size is under an upper bound which is its
   // containing region's capacity.
   assert(word_size * HeapWordSize <= hr->capacity(),
-         err_msg("size: "SIZE_FORMAT" capacity: "SIZE_FORMAT" "HR_FORMAT,
+         err_msg("size: " SIZE_FORMAT " capacity: " SIZE_FORMAT " " HR_FORMAT,
                  word_size * HeapWordSize, hr->capacity(),
                  HR_FORMAT_PARAMS(hr)));
 
--- a/hotspot/src/share/vm/gc/g1/concurrentMarkThread.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/concurrentMarkThread.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -44,8 +44,7 @@
 ConcurrentMarkThread::ConcurrentMarkThread(ConcurrentMark* cm) :
   ConcurrentGCThread(),
   _cm(cm),
-  _started(false),
-  _in_progress(false),
+  _state(Idle),
   _vtime_accum(0.0),
   _vtime_mark_accum(0.0) {
 
@@ -307,7 +306,6 @@
 
   if (started()) {
     set_in_progress();
-    clear_started();
   }
 }
 
--- a/hotspot/src/share/vm/gc/g1/concurrentMarkThread.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/concurrentMarkThread.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -47,8 +47,14 @@
 
  private:
   ConcurrentMark*                  _cm;
-  volatile bool                    _started;
-  volatile bool                    _in_progress;
+
+  enum State {
+    Idle,
+    Started,
+    InProgress
+  };
+
+  volatile State _state;
 
   void sleepBeforeNextCycle();
 
@@ -68,23 +74,22 @@
 
   ConcurrentMark* cm()     { return _cm; }
 
-  void set_started()       { assert(!_in_progress, "cycle in progress"); _started = true;  }
-  void clear_started()     { assert(_in_progress, "must be starting a cycle"); _started = false; }
-  bool started()           { return _started;  }
+  void set_idle()          { assert(_state != Started, "must not be starting a new cycle"); _state = Idle; }
+  bool idle()              { return _state == Idle; }
+  void set_started()       { assert(_state == Idle, "cycle in progress"); _state = Started; }
+  bool started()           { return _state == Started; }
+  void set_in_progress()   { assert(_state == Started, "must be starting a cycle"); _state = InProgress; }
+  bool in_progress()       { return _state == InProgress; }
 
-  void set_in_progress()   { assert(_started, "must be starting a cycle"); _in_progress = true;  }
-  void clear_in_progress() { assert(!_started, "must not be starting a new cycle"); _in_progress = false; }
-  bool in_progress()       { return _in_progress;  }
-
-  // This flag returns true from the moment a marking cycle is
+  // Returns true from the moment a marking cycle is
   // initiated (during the initial-mark pause when started() is set)
   // to the moment when the cycle completes (just after the next
   // marking bitmap has been cleared and in_progress() is
-  // cleared). While this flag is true we will not start another cycle
+  // cleared). While during_cycle() is true we will not start another cycle
   // so that cycles do not overlap. We cannot use just in_progress()
   // as the CM thread might take some time to wake up before noticing
   // that started() is set and set in_progress().
-  bool during_cycle()      { return started() || in_progress(); }
+  bool during_cycle()      { return !idle(); }
 
   // shutdown
   void stop();
--- a/hotspot/src/share/vm/gc/g1/g1AllocRegion.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1AllocRegion.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -140,7 +140,7 @@
 }
 
 void G1AllocRegion::fill_in_ext_msg(ar_ext_msg* msg, const char* message) {
-  msg->append("[%s] %s c: %u b: %s r: "PTR_FORMAT" u: "SIZE_FORMAT,
+  msg->append("[%s] %s c: %u b: %s r: " PTR_FORMAT " u: " SIZE_FORMAT,
               _name, message, _count, BOOL_TO_STR(_bot_updates),
               p2i(_alloc_region), _used_bytes_before);
 }
@@ -217,7 +217,7 @@
 
     if (G1_ALLOC_REGION_TRACING > 1) {
       if (result != NULL) {
-        jio_snprintf(rest_buffer, buffer_length, SIZE_FORMAT" "PTR_FORMAT,
+        jio_snprintf(rest_buffer, buffer_length, SIZE_FORMAT " " PTR_FORMAT,
                      word_size, result);
       } else if (word_size != 0) {
         jio_snprintf(rest_buffer, buffer_length, SIZE_FORMAT, word_size);
--- a/hotspot/src/share/vm/gc/g1/g1Allocator.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1Allocator.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -86,7 +86,7 @@
                             &_retained_old_gc_alloc_region);
 }
 
-void G1DefaultAllocator::release_gc_alloc_regions(uint no_of_gc_workers, EvacuationInfo& evacuation_info) {
+void G1DefaultAllocator::release_gc_alloc_regions(EvacuationInfo& evacuation_info) {
   AllocationContext_t context = AllocationContext::current();
   evacuation_info.set_allocation_regions(survivor_gc_alloc_region(context)->count() +
                                          old_gc_alloc_region(context)->count());
@@ -102,8 +102,8 @@
   }
 
   if (ResizePLAB) {
-    _g1h->alloc_buffer_stats(InCSetState::Young)->adjust_desired_plab_sz(no_of_gc_workers);
-    _g1h->alloc_buffer_stats(InCSetState::Old)->adjust_desired_plab_sz(no_of_gc_workers);
+    _g1h->alloc_buffer_stats(InCSetState::Young)->adjust_desired_plab_sz();
+    _g1h->alloc_buffer_stats(InCSetState::Old)->adjust_desired_plab_sz();
   }
 }
 
--- a/hotspot/src/share/vm/gc/g1/g1Allocator.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1Allocator.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -53,7 +53,7 @@
    virtual void release_mutator_alloc_region() = 0;
 
    virtual void init_gc_alloc_regions(EvacuationInfo& evacuation_info) = 0;
-   virtual void release_gc_alloc_regions(uint no_of_gc_workers, EvacuationInfo& evacuation_info) = 0;
+   virtual void release_gc_alloc_regions(EvacuationInfo& evacuation_info) = 0;
    virtual void abandon_gc_alloc_regions() = 0;
 
    virtual MutatorAllocRegion*    mutator_alloc_region(AllocationContext_t context) = 0;
@@ -76,7 +76,7 @@
 
    void decrease_used(size_t bytes) {
      assert(_summary_bytes_used >= bytes,
-            err_msg("invariant: _summary_bytes_used: "SIZE_FORMAT" should be >= bytes: "SIZE_FORMAT,
+            err_msg("invariant: _summary_bytes_used: " SIZE_FORMAT " should be >= bytes: " SIZE_FORMAT,
                 _summary_bytes_used, bytes));
      _summary_bytes_used -= bytes;
    }
@@ -114,7 +114,7 @@
   virtual void release_mutator_alloc_region();
 
   virtual void init_gc_alloc_regions(EvacuationInfo& evacuation_info);
-  virtual void release_gc_alloc_regions(uint no_of_gc_workers, EvacuationInfo& evacuation_info);
+  virtual void release_gc_alloc_regions(EvacuationInfo& evacuation_info);
   virtual void abandon_gc_alloc_regions();
 
   virtual bool is_retained_old_region(HeapRegion* hr) {
--- a/hotspot/src/share/vm/gc/g1/g1BiasedArray.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1BiasedArray.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -36,19 +36,19 @@
 #ifndef PRODUCT
 void G1BiasedMappedArrayBase::verify_index(idx_t index) const {
   guarantee(_base != NULL, "Array not initialized");
-  guarantee(index < length(), err_msg("Index out of bounds index: "SIZE_FORMAT" length: "SIZE_FORMAT, index, length()));
+  guarantee(index < length(), err_msg("Index out of bounds index: " SIZE_FORMAT " length: " SIZE_FORMAT, index, length()));
 }
 
 void G1BiasedMappedArrayBase::verify_biased_index(idx_t biased_index) const {
   guarantee(_biased_base != NULL, "Array not initialized");
   guarantee(biased_index >= bias() && biased_index < (bias() + length()),
-    err_msg("Biased index out of bounds, index: "SIZE_FORMAT" bias: "SIZE_FORMAT" length: "SIZE_FORMAT, biased_index, bias(), length()));
+    err_msg("Biased index out of bounds, index: " SIZE_FORMAT " bias: " SIZE_FORMAT " length: " SIZE_FORMAT, biased_index, bias(), length()));
 }
 
 void G1BiasedMappedArrayBase::verify_biased_index_inclusive_end(idx_t biased_index) const {
   guarantee(_biased_base != NULL, "Array not initialized");
   guarantee(biased_index >= bias() && biased_index <= (bias() + length()),
-    err_msg("Biased index out of inclusive bounds, index: "SIZE_FORMAT" bias: "SIZE_FORMAT" length: "SIZE_FORMAT, biased_index, bias(), length()));
+    err_msg("Biased index out of inclusive bounds, index: " SIZE_FORMAT " bias: " SIZE_FORMAT " length: " SIZE_FORMAT, biased_index, bias(), length()));
 }
 
 class TestMappedArray : public G1BiasedMappedArray<int> {
--- a/hotspot/src/share/vm/gc/g1/g1BiasedArray.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1BiasedArray.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -71,10 +71,10 @@
     assert(is_power_of_2(mapping_granularity_in_bytes),
       err_msg("mapping granularity must be power of 2, is %zd", mapping_granularity_in_bytes));
     assert((uintptr_t)bottom % mapping_granularity_in_bytes == 0,
-      err_msg("bottom mapping area address must be a multiple of mapping granularity %zd, is "PTR_FORMAT,
+      err_msg("bottom mapping area address must be a multiple of mapping granularity %zd, is  " PTR_FORMAT,
         mapping_granularity_in_bytes, p2i(bottom)));
     assert((uintptr_t)end % mapping_granularity_in_bytes == 0,
-      err_msg("end mapping area address must be a multiple of mapping granularity %zd, is "PTR_FORMAT,
+      err_msg("end mapping area address must be a multiple of mapping granularity %zd, is " PTR_FORMAT,
         mapping_granularity_in_bytes, p2i(end)));
     size_t num_target_elems = pointer_delta(end, bottom, mapping_granularity_in_bytes);
     idx_t bias = (uintptr_t)bottom / mapping_granularity_in_bytes;
--- a/hotspot/src/share/vm/gc/g1/g1BlockOffsetTable.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1BlockOffsetTable.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -69,10 +69,10 @@
 #ifdef ASSERT
 void G1BlockOffsetSharedArray::check_index(size_t index, const char* msg) const {
   assert((index) < (_reserved.word_size() >> LogN_words),
-         err_msg("%s - index: "SIZE_FORMAT", _vs.committed_size: "SIZE_FORMAT,
+         err_msg("%s - index: " SIZE_FORMAT ", _vs.committed_size: " SIZE_FORMAT,
                  msg, (index), (_reserved.word_size() >> LogN_words)));
   assert(G1CollectedHeap::heap()->is_in_exact(address_for_index_raw(index)),
-         err_msg("Index "SIZE_FORMAT" corresponding to "PTR_FORMAT
+         err_msg("Index " SIZE_FORMAT " corresponding to " PTR_FORMAT
                  " (%u) is not in committed area.",
                  (index),
                  p2i(address_for_index_raw(index)),
@@ -430,11 +430,11 @@
 G1BlockOffsetArray::print_on(outputStream* out) {
   size_t from_index = _array->index_for(_bottom);
   size_t to_index = _array->index_for(_end);
-  out->print_cr(">> BOT for area ["PTR_FORMAT","PTR_FORMAT") "
-                "cards ["SIZE_FORMAT","SIZE_FORMAT")",
+  out->print_cr(">> BOT for area [" PTR_FORMAT "," PTR_FORMAT ") "
+                "cards [" SIZE_FORMAT "," SIZE_FORMAT ")",
                 p2i(_bottom), p2i(_end), from_index, to_index);
   for (size_t i = from_index; i < to_index; ++i) {
-    out->print_cr("  entry "SIZE_FORMAT_W(8)" | "PTR_FORMAT" : %3u",
+    out->print_cr("  entry " SIZE_FORMAT_W(8) " | " PTR_FORMAT " : %3u",
                   i, p2i(_array->address_for_index(i)),
                   (uint) _array->offset_array(i));
   }
@@ -514,7 +514,7 @@
 void
 G1BlockOffsetArrayContigSpace::print_on(outputStream* out) {
   G1BlockOffsetArray::print_on(out);
-  out->print_cr("  next offset threshold: "PTR_FORMAT, p2i(_next_offset_threshold));
-  out->print_cr("  next offset index:     "SIZE_FORMAT, _next_offset_index);
+  out->print_cr("  next offset threshold: " PTR_FORMAT, p2i(_next_offset_threshold));
+  out->print_cr("  next offset index:     " SIZE_FORMAT, _next_offset_index);
 }
 #endif // !PRODUCT
--- a/hotspot/src/share/vm/gc/g1/g1BlockOffsetTable.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1BlockOffsetTable.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -150,7 +150,7 @@
   void check_offset(size_t offset, const char* msg) const {
     assert(offset <= N_words,
            err_msg("%s - "
-                   "offset: " SIZE_FORMAT", N_words: %u",
+                   "offset: " SIZE_FORMAT ", N_words: %u",
                    msg, offset, (uint)N_words));
   }
 
--- a/hotspot/src/share/vm/gc/g1/g1CardCounts.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1CardCounts.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -53,7 +53,7 @@
 void G1CardCounts::clear_range(size_t from_card_num, size_t to_card_num) {
   if (has_count_table()) {
     assert(from_card_num < to_card_num,
-           err_msg("Wrong order? from: " SIZE_FORMAT ", to: "SIZE_FORMAT,
+           err_msg("Wrong order? from: " SIZE_FORMAT ", to: " SIZE_FORMAT,
                    from_card_num, to_card_num));
     Copy::fill_to_bytes(&_card_counts[from_card_num], (to_card_num - from_card_num));
   }
@@ -96,7 +96,7 @@
   if (has_count_table()) {
     size_t card_num = ptr_2_card_num(card_ptr);
     assert(card_num < _reserved_max_card_num,
-           err_msg("Card "SIZE_FORMAT" outside of card counts table (max size "SIZE_FORMAT")",
+           err_msg("Card " SIZE_FORMAT " outside of card counts table (max size " SIZE_FORMAT ")",
                    card_num, _reserved_max_card_num));
     count = (uint) _card_counts[card_num];
     if (count < G1ConcRSHotCardLimit) {
--- a/hotspot/src/share/vm/gc/g1/g1CardCounts.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1CardCounts.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -91,7 +91,7 @@
 
   jbyte* card_num_2_ptr(size_t card_num) {
     assert(card_num < _reserved_max_card_num,
-           err_msg("card num out of range: "SIZE_FORMAT, card_num));
+           err_msg("card num out of range: " SIZE_FORMAT, card_num));
     return (jbyte*) (_ct_bot + card_num);
   }
 
--- a/hotspot/src/share/vm/gc/g1/g1CodeCacheRemSet.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1CodeCacheRemSet.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -350,11 +350,11 @@
       assert(set1.is_empty(), "Code root set must be initially empty but is not.");
 
       assert(G1CodeRootSet::static_mem_size() == sizeof(void*),
-          err_msg("The code root set's static memory usage is incorrect, "SIZE_FORMAT" bytes", G1CodeRootSet::static_mem_size()));
+          err_msg("The code root set's static memory usage is incorrect, " SIZE_FORMAT " bytes", G1CodeRootSet::static_mem_size()));
 
       set1.add((nmethod*)1);
       assert(set1.length() == 1, err_msg("Added exactly one element, but set contains "
-          SIZE_FORMAT" elements", set1.length()));
+          SIZE_FORMAT " elements", set1.length()));
 
       const size_t num_to_add = (size_t)G1CodeRootSet::Threshold + 1;
 
@@ -363,14 +363,14 @@
       }
       assert(set1.length() == 1,
           err_msg("Duplicate detection should not have increased the set size but "
-              "is "SIZE_FORMAT, set1.length()));
+              "is " SIZE_FORMAT, set1.length()));
 
       for (size_t i = 2; i <= num_to_add; i++) {
         set1.add((nmethod*)(uintptr_t)(i));
       }
       assert(set1.length() == num_to_add,
-          err_msg("After adding in total "SIZE_FORMAT" distinct code roots, they "
-              "need to be in the set, but there are only "SIZE_FORMAT,
+          err_msg("After adding in total " SIZE_FORMAT " distinct code roots, they "
+              "need to be in the set, but there are only " SIZE_FORMAT,
               num_to_add, set1.length()));
 
       assert(CodeRootSetTable::_purge_list != NULL, "should have grown to large hashtable");
@@ -385,7 +385,7 @@
         }
       }
       assert(num_popped == num_to_add,
-          err_msg("Managed to pop "SIZE_FORMAT" code roots, but only "SIZE_FORMAT" "
+          err_msg("Managed to pop " SIZE_FORMAT " code roots, but only " SIZE_FORMAT " "
               "were added", num_popped, num_to_add));
       assert(CodeRootSetTable::_purge_list != NULL, "should have grown to large hashtable");
 
--- a/hotspot/src/share/vm/gc/g1/g1CollectedHeap.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1CollectedHeap.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -197,7 +197,7 @@
   HeapRegion* last = NULL;
   while (curr != NULL) {
     if (!curr->is_young()) {
-      gclog_or_tty->print_cr("### YOUNG REGION "PTR_FORMAT"-"PTR_FORMAT" "
+      gclog_or_tty->print_cr("### YOUNG REGION " PTR_FORMAT "-" PTR_FORMAT " "
                              "incorrectly tagged (y: %d, surv: %d)",
                              p2i(curr->bottom()), p2i(curr->end()),
                              curr->is_young(), curr->is_survivor());
@@ -326,7 +326,7 @@
     if (curr == NULL)
       gclog_or_tty->print_cr("  empty");
     while (curr != NULL) {
-      gclog_or_tty->print_cr("  "HR_FORMAT", P: "PTR_FORMAT ", N: "PTR_FORMAT", age: %4d",
+      gclog_or_tty->print_cr("  " HR_FORMAT ", P: " PTR_FORMAT ", N: " PTR_FORMAT ", age: %4d",
                              HR_FORMAT_PARAMS(curr),
                              p2i(curr->prev_top_at_mark_start()),
                              p2i(curr->next_top_at_mark_start()),
@@ -430,7 +430,7 @@
       HeapRegion* res = _hrm.allocate_free_region(is_old);
       if (G1ConcRegionFreeingVerbose) {
         gclog_or_tty->print_cr("G1ConcRegionFreeing [region alloc] : "
-                               "allocated "HR_FORMAT" from secondary_free_list",
+                               "allocated " HR_FORMAT " from secondary_free_list",
                                HR_FORMAT_PARAMS(res));
       }
       return res;
@@ -1670,8 +1670,8 @@
   // This assert only makes sense here, before we adjust them
   // with respect to the min and max heap size.
   assert(minimum_desired_capacity <= maximum_desired_capacity,
-         err_msg("minimum_desired_capacity = "SIZE_FORMAT", "
-                 "maximum_desired_capacity = "SIZE_FORMAT,
+         err_msg("minimum_desired_capacity = " SIZE_FORMAT ", "
+                 "maximum_desired_capacity = " SIZE_FORMAT,
                  minimum_desired_capacity, maximum_desired_capacity));
 
   // Should not be greater than the heap max size. No need to adjust
@@ -2332,7 +2332,7 @@
   virtual bool doHeapRegion(HeapRegion* hr) {
     unsigned region_gc_time_stamp = hr->get_gc_time_stamp();
     if (_gc_time_stamp != region_gc_time_stamp) {
-      gclog_or_tty->print_cr("Region "HR_FORMAT" has GC time stamp = %d, "
+      gclog_or_tty->print_cr("Region " HR_FORMAT " has GC time stamp = %d, "
                              "expected %d", HR_FORMAT_PARAMS(hr),
                              region_gc_time_stamp, _gc_time_stamp);
       _failures = true;
@@ -2487,7 +2487,7 @@
   // is set) so that if a waiter requests another System.gc() it doesn't
   // incorrectly see that a marking cycle is still in progress.
   if (concurrent) {
-    _cmThread->clear_in_progress();
+    _cmThread->set_idle();
   }
 
   // This notify_all() will ensure that a thread that called
@@ -2926,10 +2926,10 @@
     if (!oopDesc::is_null(heap_oop)) {
       oop obj = oopDesc::decode_heap_oop_not_null(heap_oop);
       if (_g1h->is_obj_dead_cond(obj, _vo)) {
-        gclog_or_tty->print_cr("Root location "PTR_FORMAT" "
-                               "points to dead obj "PTR_FORMAT, p2i(p), p2i(obj));
+        gclog_or_tty->print_cr("Root location " PTR_FORMAT " "
+                               "points to dead obj " PTR_FORMAT, p2i(p), p2i(obj));
         if (_vo == VerifyOption_G1UseMarkWord) {
-          gclog_or_tty->print_cr("  Mark word: "INTPTR_FORMAT, (intptr_t)obj->mark());
+          gclog_or_tty->print_cr("  Mark word: " INTPTR_FORMAT, (intptr_t)obj->mark());
         }
         obj->print_on(gclog_or_tty);
         _failures = true;
@@ -2976,9 +2976,9 @@
       // Verify that the strong code root list for this region
       // contains the nmethod
       if (!hrrs->strong_code_roots_list_contains(_nm)) {
-        gclog_or_tty->print_cr("Code root location "PTR_FORMAT" "
-                               "from nmethod "PTR_FORMAT" not in strong "
-                               "code roots for region ["PTR_FORMAT","PTR_FORMAT")",
+        gclog_or_tty->print_cr("Code root location " PTR_FORMAT " "
+                               "from nmethod " PTR_FORMAT " not in strong "
+                               "code roots for region [" PTR_FORMAT "," PTR_FORMAT ")",
                                p2i(p), p2i(_nm), p2i(hr->bottom()), p2i(hr->end()));
         _failures = true;
       }
@@ -3157,9 +3157,9 @@
         r->object_iterate(&not_dead_yet_cl);
         if (_vo != VerifyOption_G1UseNextMarking) {
           if (r->max_live_bytes() < not_dead_yet_cl.live_bytes()) {
-            gclog_or_tty->print_cr("["PTR_FORMAT","PTR_FORMAT"] "
-                                   "max_live_bytes "SIZE_FORMAT" "
-                                   "< calculated "SIZE_FORMAT,
+            gclog_or_tty->print_cr("[" PTR_FORMAT "," PTR_FORMAT "] "
+                                   "max_live_bytes " SIZE_FORMAT " "
+                                   "< calculated " SIZE_FORMAT,
                                    p2i(r->bottom()), p2i(r->end()),
                                    r->max_live_bytes(),
                                  not_dead_yet_cl.live_bytes());
@@ -3444,7 +3444,7 @@
     size_t occupied = hrrs->occupied();
     _occupied_sum += occupied;
 
-    gclog_or_tty->print_cr("Printing RSet for region "HR_FORMAT,
+    gclog_or_tty->print_cr("Printing RSet for region " HR_FORMAT,
                            HR_FORMAT_PARAMS(r));
     if (occupied == 0) {
       gclog_or_tty->print_cr("  RSet is empty");
@@ -3463,7 +3463,7 @@
   }
 
   ~PrintRSetsClosure() {
-    gclog_or_tty->print_cr("Occupied Sum: "SIZE_FORMAT, _occupied_sum);
+    gclog_or_tty->print_cr("Occupied Sum: " SIZE_FORMAT, _occupied_sum);
     gclog_or_tty->print_cr("========================================");
     gclog_or_tty->cr();
   }
@@ -4273,7 +4273,7 @@
 void G1CollectedHeap::remove_self_forwarding_pointers() {
   double remove_self_forwards_start = os::elapsedTime();
 
-  G1ParRemoveSelfForwardPtrsTask rsfp_task(this);
+  G1ParRemoveSelfForwardPtrsTask rsfp_task;
   workers()->run_task(&rsfp_task);
 
   // Now restore saved marks, if any.
@@ -4308,7 +4308,7 @@
 G1CollectedHeap::handle_evacuation_failure_par(G1ParScanThreadState* _par_scan_state,
                                                oop old) {
   assert(obj_in_cs(old),
-         err_msg("obj: "PTR_FORMAT" should still be in the CSet",
+         err_msg("obj: " PTR_FORMAT " should still be in the CSet",
                  p2i(old)));
   markOop m = old->mark();
   oop forward_ptr = old->forward_to_atomic(old);
@@ -4342,7 +4342,7 @@
     // space for this object (old != forward_ptr) or they beat us in
     // self-forwarding it (old == forward_ptr).
     assert(old == forward_ptr || !obj_in_cs(forward_ptr),
-           err_msg("obj: "PTR_FORMAT" forwarded to: "PTR_FORMAT" "
+           err_msg("obj: " PTR_FORMAT " forwarded to: " PTR_FORMAT " "
                    "should not be in the CSet",
                    p2i(old), p2i(forward_ptr)));
     return forward_ptr;
@@ -4730,8 +4730,8 @@
 
     if (G1TraceStringSymbolTableScrubbing) {
       gclog_or_tty->print_cr("Cleaned string and symbol table, "
-                             "strings: "SIZE_FORMAT" processed, "SIZE_FORMAT" removed, "
-                             "symbols: "SIZE_FORMAT" processed, "SIZE_FORMAT" removed",
+                             "strings: " SIZE_FORMAT " processed, " SIZE_FORMAT " removed, "
+                             "symbols: " SIZE_FORMAT " processed, " SIZE_FORMAT " removed",
                              strings_processed(), strings_removed(),
                              symbols_processed(), symbols_removed());
     }
@@ -5644,7 +5644,7 @@
     phase_times->record_string_dedup_fixup_time(fixup_time_ms);
   }
 
-  _allocator->release_gc_alloc_regions(n_workers, evacuation_info);
+  _allocator->release_gc_alloc_regions(evacuation_info);
   g1_rem_set()->cleanup_after_oops_into_collection_set_do();
 
   // Reset and re-enable the hot card cache.
@@ -5828,13 +5828,13 @@
 bool G1CollectedHeap::verify_no_bits_over_tams(const char* bitmap_name, CMBitMapRO* bitmap,
                                                HeapWord* tams, HeapWord* end) {
   guarantee(tams <= end,
-            err_msg("tams: "PTR_FORMAT" end: "PTR_FORMAT, p2i(tams), p2i(end)));
+            err_msg("tams: " PTR_FORMAT " end: " PTR_FORMAT, p2i(tams), p2i(end)));
   HeapWord* result = bitmap->getNextMarkedWordAddress(tams, end);
   if (result < end) {
     gclog_or_tty->cr();
-    gclog_or_tty->print_cr("## wrong marked address on %s bitmap: "PTR_FORMAT,
+    gclog_or_tty->print_cr("## wrong marked address on %s bitmap: " PTR_FORMAT,
                            bitmap_name, p2i(result));
-    gclog_or_tty->print_cr("## %s tams: "PTR_FORMAT" end: "PTR_FORMAT,
+    gclog_or_tty->print_cr("## %s tams: " PTR_FORMAT " end: " PTR_FORMAT,
                            bitmap_name, p2i(tams), p2i(end));
     return false;
   }
@@ -5860,7 +5860,7 @@
     res_n = verify_no_bits_over_tams("next", next_bitmap, ntams, end);
   }
   if (!res_p || !res_n) {
-    gclog_or_tty->print_cr("#### Bitmap verification failed for "HR_FORMAT,
+    gclog_or_tty->print_cr("#### Bitmap verification failed for " HR_FORMAT,
                            HR_FORMAT_PARAMS(hr));
     gclog_or_tty->print_cr("#### Caller: %s", caller);
     return false;
@@ -6157,7 +6157,7 @@
         !r->rem_set()->is_empty()) {
 
       if (G1TraceEagerReclaimHumongousObjects) {
-        gclog_or_tty->print_cr("Live humongous region %u size "SIZE_FORMAT" start "PTR_FORMAT" length %u with remset "SIZE_FORMAT" code roots "SIZE_FORMAT" is marked %d reclaim candidate %d type array %d",
+        gclog_or_tty->print_cr("Live humongous region %u size " SIZE_FORMAT " start " PTR_FORMAT " length %u with remset " SIZE_FORMAT " code roots " SIZE_FORMAT " is marked %d reclaim candidate %d type array %d",
                                region_idx,
                                (size_t)obj->size() * HeapWordSize,
                                p2i(r->bottom()),
@@ -6179,7 +6179,7 @@
                       p2i(r->bottom())));
 
     if (G1TraceEagerReclaimHumongousObjects) {
-      gclog_or_tty->print_cr("Dead humongous region %u size "SIZE_FORMAT" start "PTR_FORMAT" length %u with remset "SIZE_FORMAT" code roots "SIZE_FORMAT" is marked %d reclaim candidate %d type array %d",
+      gclog_or_tty->print_cr("Dead humongous region %u size " SIZE_FORMAT " start " PTR_FORMAT " length %u with remset " SIZE_FORMAT " code roots " SIZE_FORMAT " is marked %d reclaim candidate %d type array %d",
                              region_idx,
                              (size_t)obj->size() * HeapWordSize,
                              p2i(r->bottom()),
@@ -6333,7 +6333,7 @@
   NoYoungRegionsClosure() : _success(true) { }
   bool doHeapRegion(HeapRegion* r) {
     if (r->is_young()) {
-      gclog_or_tty->print_cr("Region ["PTR_FORMAT", "PTR_FORMAT") tagged as young",
+      gclog_or_tty->print_cr("Region [" PTR_FORMAT ", " PTR_FORMAT ") tagged as young",
                              p2i(r->bottom()), p2i(r->end()));
       _success = false;
     }
@@ -6470,7 +6470,7 @@
   }
   assert(_allocator->used_unlocked() == recalculate_used(),
          err_msg("inconsistent _allocator->used_unlocked(), "
-                 "value: "SIZE_FORMAT" recalculated: "SIZE_FORMAT,
+                 "value: " SIZE_FORMAT " recalculated: " SIZE_FORMAT,
                  _allocator->used_unlocked(), recalculate_used()));
 }
 
@@ -6697,8 +6697,8 @@
       oop obj = oopDesc::decode_heap_oop_not_null(heap_oop);
       HeapRegion* hr = _g1h->heap_region_containing(obj);
       assert(!hr->is_continues_humongous(),
-             err_msg("trying to add code root "PTR_FORMAT" in continuation of humongous region "HR_FORMAT
-                     " starting at "HR_FORMAT,
+             err_msg("trying to add code root " PTR_FORMAT " in continuation of humongous region " HR_FORMAT
+                     " starting at " HR_FORMAT,
                      p2i(_nm), HR_FORMAT_PARAMS(hr), HR_FORMAT_PARAMS(hr->humongous_start_region())));
 
       // HeapRegion::add_strong_code_root_locked() avoids adding duplicate entries.
@@ -6724,8 +6724,8 @@
       oop obj = oopDesc::decode_heap_oop_not_null(heap_oop);
       HeapRegion* hr = _g1h->heap_region_containing(obj);
       assert(!hr->is_continues_humongous(),
-             err_msg("trying to remove code root "PTR_FORMAT" in continuation of humongous region "HR_FORMAT
-                     " starting at "HR_FORMAT,
+             err_msg("trying to remove code root " PTR_FORMAT " in continuation of humongous region " HR_FORMAT
+                     " starting at " HR_FORMAT,
                      p2i(_nm), HR_FORMAT_PARAMS(hr), HR_FORMAT_PARAMS(hr->humongous_start_region())));
 
       hr->remove_strong_code_root(_nm);
--- a/hotspot/src/share/vm/gc/g1/g1CollectedHeap.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1CollectedHeap.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -281,7 +281,7 @@
   void init_gc_alloc_regions(EvacuationInfo& evacuation_info);
 
   // It releases the GC alloc regions at the end of a GC.
-  void release_gc_alloc_regions(uint no_of_gc_workers, EvacuationInfo& evacuation_info);
+  void release_gc_alloc_regions(EvacuationInfo& evacuation_info);
 
   // It does any cleanup that needs to be done on the GC alloc regions
   // before a Full GC.
@@ -1109,6 +1109,8 @@
   // The STW reference processor....
   ReferenceProcessor* ref_processor_stw() const { return _ref_processor_stw; }
 
+  G1NewTracer* gc_tracer_stw() const { return _gc_tracer_stw; }
+
   // The Concurrent Marking reference processor...
   ReferenceProcessor* ref_processor_cm() const { return _ref_processor_cm; }
 
--- a/hotspot/src/share/vm/gc/g1/g1CollectedHeap.inline.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1CollectedHeap.inline.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -49,7 +49,7 @@
 }
 
 size_t G1CollectedHeap::desired_plab_sz(InCSetState dest) {
-  size_t gclab_word_size = alloc_buffer_stats(dest)->desired_plab_sz();
+  size_t gclab_word_size = alloc_buffer_stats(dest)->desired_plab_sz(G1CollectedHeap::heap()->workers()->active_workers());
   // Prevent humongous PLAB sizes for two reasons:
   // * PLABs are allocated using a similar paths as oops, but should
   //   never be in a humongous region
@@ -82,7 +82,7 @@
 
 inline uint G1CollectedHeap::addr_to_region(HeapWord* addr) const {
   assert(is_in_reserved(addr),
-         err_msg("Cannot calculate region index for address "PTR_FORMAT" that is outside of the heap ["PTR_FORMAT", "PTR_FORMAT")",
+         err_msg("Cannot calculate region index for address " PTR_FORMAT " that is outside of the heap [" PTR_FORMAT ", " PTR_FORMAT ")",
                  p2i(addr), p2i(reserved_region().start()), p2i(reserved_region().end())));
   return (uint)(pointer_delta(addr, reserved_region().start(), sizeof(uint8_t)) >> HeapRegion::LogOfHRGrainBytes);
 }
@@ -95,7 +95,7 @@
 inline HeapRegion* G1CollectedHeap::heap_region_containing_raw(const T addr) const {
   assert(addr != NULL, "invariant");
   assert(is_in_g1_reserved((const void*) addr),
-      err_msg("Address "PTR_FORMAT" is outside of the heap ranging from ["PTR_FORMAT" to "PTR_FORMAT")",
+      err_msg("Address " PTR_FORMAT " is outside of the heap ranging from [" PTR_FORMAT " to " PTR_FORMAT ")",
           p2i((void*)addr), p2i(g1_reserved().start()), p2i(g1_reserved().end())));
   return _hrm.addr_to_region((HeapWord*) addr);
 }
--- a/hotspot/src/share/vm/gc/g1/g1CollectorPolicy.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1CollectorPolicy.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -184,7 +184,7 @@
   const size_t region_size = HeapRegion::GrainWords;
   if (YoungPLABSize > region_size || OldPLABSize > region_size) {
     char buffer[128];
-    jio_snprintf(buffer, sizeof(buffer), "%sPLABSize should be at most "SIZE_FORMAT,
+    jio_snprintf(buffer, sizeof(buffer), "%sPLABSize should be at most " SIZE_FORMAT,
                  OldPLABSize > region_size ? "Old" : "Young", region_size);
     vm_exit_during_initialization(buffer);
   }
@@ -821,7 +821,7 @@
   update_survivors_policy();
 
   assert(_g1->used() == _g1->recalculate_used(),
-         err_msg("sanity, used: "SIZE_FORMAT" recalculate_used: "SIZE_FORMAT,
+         err_msg("sanity, used: " SIZE_FORMAT " recalculate_used: " SIZE_FORMAT,
                  _g1->used(), _g1->recalculate_used()));
 
   double s_w_t_ms = (start_time_sec - _stop_world_start) * 1000.0;
@@ -865,7 +865,7 @@
   _cur_mark_stop_world_time_ms += elapsed_time_ms;
   _prev_collection_pause_end_ms += elapsed_time_ms;
 
-  _mmu_tracker->add_pause(_mark_remark_start_sec, end_time_sec, true);
+  _mmu_tracker->add_pause(_mark_remark_start_sec, end_time_sec, _g1->gc_tracer_cm()->gc_id());
 }
 
 void G1CollectorPolicy::record_concurrent_mark_cleanup_start() {
@@ -961,7 +961,7 @@
   }
 
   _mmu_tracker->add_pause(end_time_sec - pause_time_ms/1000.0,
-                          end_time_sec, false);
+                          end_time_sec, _g1->gc_tracer_stw()->gc_id());
 
   evacuation_info.set_collectionset_used_before(_collection_set_bytes_used_before);
   evacuation_info.set_bytes_copied(_bytes_copied_during_gc);
@@ -1216,10 +1216,10 @@
     (_young_list_target_length * HeapRegion::GrainBytes) - survivor_used_bytes_after_gc;
 
   gclog_or_tty->print(
-    "   [Eden: "EXT_SIZE_FORMAT"("EXT_SIZE_FORMAT")->"EXT_SIZE_FORMAT"("EXT_SIZE_FORMAT") "
-    "Survivors: "EXT_SIZE_FORMAT"->"EXT_SIZE_FORMAT" "
-    "Heap: "EXT_SIZE_FORMAT"("EXT_SIZE_FORMAT")->"
-    EXT_SIZE_FORMAT"("EXT_SIZE_FORMAT")]",
+    "   [Eden: " EXT_SIZE_FORMAT "(" EXT_SIZE_FORMAT ")->" EXT_SIZE_FORMAT "(" EXT_SIZE_FORMAT ") "
+    "Survivors: " EXT_SIZE_FORMAT "->" EXT_SIZE_FORMAT " "
+    "Heap: " EXT_SIZE_FORMAT "(" EXT_SIZE_FORMAT ")->"
+    EXT_SIZE_FORMAT "(" EXT_SIZE_FORMAT ")]",
     EXT_SIZE_PARAMS(_eden_used_bytes_before_gc),
     EXT_SIZE_PARAMS(_eden_capacity_bytes_before_gc),
     EXT_SIZE_PARAMS(eden_used_bytes_after_gc),
@@ -1597,7 +1597,7 @@
   _concurrent_mark_cleanup_times_ms->add(elapsed_time_ms);
   _cur_mark_stop_world_time_ms += elapsed_time_ms;
   _prev_collection_pause_end_ms += elapsed_time_ms;
-  _mmu_tracker->add_pause(_mark_cleanup_start_sec, end_sec, true);
+  _mmu_tracker->add_pause(_mark_cleanup_start_sec, end_sec, _g1->gc_tracer_cm()->gc_id());
 }
 
 // Add the heap region at the head of the non-incremental collection set
@@ -1787,7 +1787,7 @@
   while (csr != NULL) {
     HeapRegion* next = csr->next_in_collection_set();
     assert(csr->in_collection_set(), "bad CS");
-    st->print_cr("  "HR_FORMAT", P: "PTR_FORMAT "N: "PTR_FORMAT", age: %4d",
+    st->print_cr("  " HR_FORMAT ", P: " PTR_FORMAT "N: " PTR_FORMAT ", age: %4d",
                  HR_FORMAT_PARAMS(csr),
                  p2i(csr->prev_top_at_mark_start()), p2i(csr->next_top_at_mark_start()),
                  csr->age_in_surv_rate_group_cond());
--- a/hotspot/src/share/vm/gc/g1/g1ErgoVerbose.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1ErgoVerbose.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -121,15 +121,15 @@
 // Single parameter format strings
 #define ergo_format_str(_name_)      ", " _name_ ": %s"
 #define ergo_format_region(_name_)   ", " _name_ ": %u regions"
-#define ergo_format_byte(_name_)     ", " _name_ ": "SIZE_FORMAT" bytes"
+#define ergo_format_byte(_name_)     ", " _name_ ": " SIZE_FORMAT " bytes"
 #define ergo_format_double(_name_)   ", " _name_ ": %1.2f"
 #define ergo_format_perc(_name_)     ", " _name_ ": %1.2f %%"
 #define ergo_format_ms(_name_)       ", " _name_ ": %1.2f ms"
-#define ergo_format_size(_name_)     ", " _name_ ": "SIZE_FORMAT
+#define ergo_format_size(_name_)     ", " _name_ ": " SIZE_FORMAT
 
 // Double parameter format strings
 #define ergo_format_byte_perc(_name_)                                   \
-                             ", " _name_ ": "SIZE_FORMAT" bytes (%1.2f %%)"
+                             ", " _name_ ": " SIZE_FORMAT " bytes (%1.2f %%)"
 
 // Generates the format string
 #define ergo_format(_extra_format_)                           \
--- a/hotspot/src/share/vm/gc/g1/g1EvacFailure.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1EvacFailure.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -40,8 +40,8 @@
   G1SATBCardTableModRefBS* _ct_bs;
 
 public:
-  UpdateRSetDeferred(G1CollectedHeap* g1, DirtyCardQueue* dcq) :
-    _g1(g1), _ct_bs(_g1->g1_barrier_set()), _dcq(dcq) {}
+  UpdateRSetDeferred(DirtyCardQueue* dcq) :
+    _g1(G1CollectedHeap::heap()), _ct_bs(_g1->g1_barrier_set()), _dcq(dcq) {}
 
   virtual void do_oop(narrowOop* p) { do_oop_work(p); }
   virtual void do_oop(      oop* p) { do_oop_work(p); }
@@ -65,60 +65,41 @@
   size_t _marked_bytes;
   OopsInHeapRegionClosure *_update_rset_cl;
   bool _during_initial_mark;
-  bool _during_conc_mark;
   uint _worker_id;
-  HeapWord* _end_of_last_gap;
-  HeapWord* _last_gap_threshold;
-  HeapWord* _last_obj_threshold;
+  HeapWord* _last_forwarded_object_end;
 
 public:
-  RemoveSelfForwardPtrObjClosure(G1CollectedHeap* g1, ConcurrentMark* cm,
-                                 HeapRegion* hr,
+  RemoveSelfForwardPtrObjClosure(HeapRegion* hr,
                                  OopsInHeapRegionClosure* update_rset_cl,
                                  bool during_initial_mark,
-                                 bool during_conc_mark,
                                  uint worker_id) :
-    _g1(g1), _cm(cm), _hr(hr), _marked_bytes(0),
+    _g1(G1CollectedHeap::heap()),
+    _cm(_g1->concurrent_mark()),
+    _hr(hr),
+    _marked_bytes(0),
     _update_rset_cl(update_rset_cl),
     _during_initial_mark(during_initial_mark),
-    _during_conc_mark(during_conc_mark),
     _worker_id(worker_id),
-    _end_of_last_gap(hr->bottom()),
-    _last_gap_threshold(hr->bottom()),
-    _last_obj_threshold(hr->bottom()) { }
+    _last_forwarded_object_end(hr->bottom()) { }
 
   size_t marked_bytes() { return _marked_bytes; }
 
-  // <original comment>
-  // The original idea here was to coalesce evacuated and dead objects.
-  // However that caused complications with the block offset table (BOT).
-  // In particular if there were two TLABs, one of them partially refined.
-  // |----- TLAB_1--------|----TLAB_2-~~~(partially refined part)~~~|
-  // The BOT entries of the unrefined part of TLAB_2 point to the start
-  // of TLAB_2. If the last object of the TLAB_1 and the first object
-  // of TLAB_2 are coalesced, then the cards of the unrefined part
-  // would point into middle of the filler object.
-  // The current approach is to not coalesce and leave the BOT contents intact.
-  // </original comment>
-  //
-  // We now reset the BOT when we start the object iteration over the
-  // region and refine its entries for every object we come across. So
-  // the above comment is not really relevant and we should be able
-  // to coalesce dead objects if we want to.
+  // Iterate over the live objects in the region to find self-forwarded objects
+  // that need to be kept live. We need to update the remembered sets of these
+  // objects. Further update the BOT and marks.
+  // We can coalesce and overwrite the remaining heap contents with dummy objects
+  // as they have either been dead or evacuated (which are unreferenced now, i.e.
+  // dead too) already.
   void do_object(oop obj) {
     HeapWord* obj_addr = (HeapWord*) obj;
     assert(_hr->is_in(obj_addr), "sanity");
     size_t obj_size = obj->size();
     HeapWord* obj_end = obj_addr + obj_size;
 
-    if (_end_of_last_gap != obj_addr) {
-      // there was a gap before obj_addr
-      _last_gap_threshold = _hr->cross_threshold(_end_of_last_gap, obj_addr);
-    }
-
     if (obj->is_forwarded() && obj->forwardee() == obj) {
       // The object failed to move.
 
+      zap_dead_objects(_last_forwarded_object_end, obj_addr);
       // We consider all objects that we find self-forwarded to be
       // live. What we'll do is that we'll update the prev marking
       // info so that they are all under PTAMS and explicitly marked.
@@ -154,24 +135,52 @@
       // remembered set entries missing given that we skipped cards on
       // the collection set. So, we'll recreate such entries now.
       obj->oop_iterate(_update_rset_cl);
-    } else {
+
+      _last_forwarded_object_end = obj_end;
+      _hr->cross_threshold(obj_addr, obj_end);
+    }
+  }
+
+  // Fill the memory area from start to end with filler objects, and update the BOT
+  // and the mark bitmap accordingly.
+  void zap_dead_objects(HeapWord* start, HeapWord* end) {
+    if (start == end) {
+      return;
+    }
+
+    size_t gap_size = pointer_delta(end, start);
+    MemRegion mr(start, gap_size);
+    if (gap_size >= CollectedHeap::min_fill_size()) {
+      CollectedHeap::fill_with_objects(start, gap_size);
 
-      // The object has been either evacuated or is dead. Fill it with a
-      // dummy object.
-      MemRegion mr(obj_addr, obj_size);
-      CollectedHeap::fill_with_object(mr);
+      HeapWord* end_first_obj = start + ((oop)start)->size();
+      _hr->cross_threshold(start, end_first_obj);
+      // Fill_with_objects() may have created multiple (i.e. two)
+      // objects, as the max_fill_size() is half a region.
+      // After updating the BOT for the first object, also update the
+      // BOT for the second object to make the BOT complete.
+      if (end_first_obj != end) {
+        _hr->cross_threshold(end_first_obj, end);
+#ifdef ASSERT
+        size_t size_second_obj = ((oop)end_first_obj)->size();
+        HeapWord* end_of_second_obj = end_first_obj + size_second_obj;
+        assert(end == end_of_second_obj,
+               err_msg("More than two objects were used to fill the area from " PTR_FORMAT " to " PTR_FORMAT ", "
+                       "second objects size " SIZE_FORMAT " ends at " PTR_FORMAT,
+                       p2i(start), p2i(end), size_second_obj, p2i(end_of_second_obj)));
+#endif
+      }
+    }
+    _cm->clearRangePrevBitmap(mr);
+  }
 
-      // must nuke all dead objects which we skipped when iterating over the region
-      _cm->clearRangePrevBitmap(MemRegion(_end_of_last_gap, obj_end));
-    }
-    _end_of_last_gap = obj_end;
-    _last_obj_threshold = _hr->cross_threshold(obj_addr, obj_end);
+  void zap_remainder() {
+    zap_dead_objects(_last_forwarded_object_end, _hr->top());
   }
 };
 
 class RemoveSelfForwardPtrHRClosure: public HeapRegionClosure {
   G1CollectedHeap* _g1h;
-  ConcurrentMark* _cm;
   uint _worker_id;
   HeapRegionClaimer* _hrclaimer;
 
@@ -179,11 +188,27 @@
   UpdateRSetDeferred _update_rset_cl;
 
 public:
-  RemoveSelfForwardPtrHRClosure(G1CollectedHeap* g1h,
-                                uint worker_id,
+  RemoveSelfForwardPtrHRClosure(uint worker_id,
                                 HeapRegionClaimer* hrclaimer) :
-      _g1h(g1h), _dcq(&g1h->dirty_card_queue_set()), _update_rset_cl(g1h, &_dcq),
-      _worker_id(worker_id), _cm(_g1h->concurrent_mark()), _hrclaimer(hrclaimer) {
+    _g1h(G1CollectedHeap::heap()),
+    _dcq(&_g1h->dirty_card_queue_set()),
+    _update_rset_cl(&_dcq),
+    _worker_id(worker_id),
+    _hrclaimer(hrclaimer) {
+  }
+
+  size_t remove_self_forward_ptr_by_walking_hr(HeapRegion* hr,
+                                               bool during_initial_mark) {
+    RemoveSelfForwardPtrObjClosure rspc(hr,
+                                        &_update_rset_cl,
+                                        during_initial_mark,
+                                        _worker_id);
+    _update_rset_cl.set_region(hr);
+    hr->object_iterate(&rspc);
+    // Need to zap the remainder area of the processed region.
+    rspc.zap_remainder();
+
+    return rspc.marked_bytes();
   }
 
   bool doHeapRegion(HeapRegion *hr) {
@@ -195,11 +220,6 @@
 
     if (_hrclaimer->claim_region(hr->hrm_index())) {
       if (hr->evacuation_failed()) {
-        RemoveSelfForwardPtrObjClosure rspc(_g1h, _cm, hr, &_update_rset_cl,
-                                            during_initial_mark,
-                                            during_conc_mark,
-                                            _worker_id);
-
         hr->note_self_forwarding_removal_start(during_initial_mark,
                                                during_conc_mark);
         _g1h->check_bitmaps("Self-Forwarding Ptr Removal", hr);
@@ -214,26 +234,27 @@
         // whenever this might be required in the future.
         hr->rem_set()->reset_for_par_iteration();
         hr->reset_bot();
-        _update_rset_cl.set_region(hr);
-        hr->object_iterate(&rspc);
+
+        size_t live_bytes = remove_self_forward_ptr_by_walking_hr(hr, during_initial_mark);
 
         hr->rem_set()->clean_strong_code_roots(hr);
 
         hr->note_self_forwarding_removal_end(during_initial_mark,
                                              during_conc_mark,
-                                             rspc.marked_bytes());
+                                             live_bytes);
       }
     }
     return false;
   }
 };
 
-G1ParRemoveSelfForwardPtrsTask::G1ParRemoveSelfForwardPtrsTask(G1CollectedHeap* g1h) :
-    AbstractGangTask("G1 Remove Self-forwarding Pointers"), _g1h(g1h),
-    _hrclaimer(g1h->workers()->active_workers()) {}
+G1ParRemoveSelfForwardPtrsTask::G1ParRemoveSelfForwardPtrsTask() :
+  AbstractGangTask("G1 Remove Self-forwarding Pointers"),
+  _g1h(G1CollectedHeap::heap()),
+  _hrclaimer(_g1h->workers()->active_workers()) { }
 
 void G1ParRemoveSelfForwardPtrsTask::work(uint worker_id) {
-  RemoveSelfForwardPtrHRClosure rsfp_cl(_g1h, worker_id, &_hrclaimer);
+  RemoveSelfForwardPtrHRClosure rsfp_cl(worker_id, &_hrclaimer);
 
   HeapRegion* hr = _g1h->start_cset_region_for_worker(worker_id);
   _g1h->collection_set_iterate_from(hr, &rsfp_cl);
--- a/hotspot/src/share/vm/gc/g1/g1EvacFailure.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1EvacFailure.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -40,7 +40,7 @@
   HeapRegionClaimer _hrclaimer;
 
 public:
-  G1ParRemoveSelfForwardPtrsTask(G1CollectedHeap* g1h);
+  G1ParRemoveSelfForwardPtrsTask();
 
   void work(uint worker_id);
 };
--- a/hotspot/src/share/vm/gc/g1/g1GCPhaseTimes.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1GCPhaseTimes.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -331,7 +331,7 @@
 }
 
 void G1GCPhaseTimes::print_stats(int level, const char* str, size_t value) {
-  LineBuffer(level).append_and_print_cr("[%s: "SIZE_FORMAT"]", str, value);
+  LineBuffer(level).append_and_print_cr("[%s: " SIZE_FORMAT "]", str, value);
 }
 
 void G1GCPhaseTimes::print_stats(int level, const char* str, double value, uint workers) {
@@ -451,7 +451,7 @@
 
     if (phase->_thread_work_items != NULL) {
       LineBuffer buf2(phase->_thread_work_items->_indent_level);
-      buf2.append_and_print_cr("[%s:  "SIZE_FORMAT"]", phase->_thread_work_items->_title, _phase_times->sum_thread_work_items(phase_id));
+      buf2.append_and_print_cr("[%s:  " SIZE_FORMAT "]", phase->_thread_work_items->_title, _phase_times->sum_thread_work_items(phase_id));
     }
   }
 
--- a/hotspot/src/share/vm/gc/g1/g1HRPrinter.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1HRPrinter.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -83,18 +83,18 @@
 
   if (type_str != NULL) {
     if (top != NULL) {
-      gclog_or_tty->print_cr(G1HR_PREFIX" %s(%s) "PTR_FORMAT" "PTR_FORMAT,
+      gclog_or_tty->print_cr(G1HR_PREFIX " %s(%s) " PTR_FORMAT " " PTR_FORMAT,
                              action_str, type_str, p2i(bottom), p2i(top));
     } else {
-      gclog_or_tty->print_cr(G1HR_PREFIX" %s(%s) "PTR_FORMAT,
+      gclog_or_tty->print_cr(G1HR_PREFIX " %s(%s) " PTR_FORMAT,
                              action_str, type_str, p2i(bottom));
     }
   } else {
     if (top != NULL) {
-      gclog_or_tty->print_cr(G1HR_PREFIX" %s "PTR_FORMAT" "PTR_FORMAT,
+      gclog_or_tty->print_cr(G1HR_PREFIX " %s " PTR_FORMAT " " PTR_FORMAT,
                              action_str, p2i(bottom), p2i(top));
     } else {
-      gclog_or_tty->print_cr(G1HR_PREFIX" %s "PTR_FORMAT,
+      gclog_or_tty->print_cr(G1HR_PREFIX " %s " PTR_FORMAT,
                              action_str, p2i(bottom));
     }
   }
@@ -103,11 +103,11 @@
 void G1HRPrinter::print(ActionType action, HeapWord* bottom, HeapWord* end) {
   const char* action_str = action_name(action);
 
-  gclog_or_tty->print_cr(G1HR_PREFIX" %s ["PTR_FORMAT","PTR_FORMAT"]",
+  gclog_or_tty->print_cr(G1HR_PREFIX " %s [" PTR_FORMAT "," PTR_FORMAT "]",
                          action_str, p2i(bottom), p2i(end));
 }
 
 void G1HRPrinter::print(PhaseType phase, size_t phase_num) {
   const char* phase_str = phase_name(phase);
-  gclog_or_tty->print_cr(G1HR_PREFIX" #%s "SIZE_FORMAT, phase_str, phase_num);
+  gclog_or_tty->print_cr(G1HR_PREFIX " #%s " SIZE_FORMAT, phase_str, phase_num);
 }
--- a/hotspot/src/share/vm/gc/g1/g1InCSetState.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1InCSetState.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -104,7 +104,7 @@
  public:
   void set_humongous(uintptr_t index) {
     assert(get_by_index(index).is_default(),
-           err_msg("State at index " INTPTR_FORMAT" should be default but is " CSETSTATE_FORMAT, index, get_by_index(index).value()));
+           err_msg("State at index " INTPTR_FORMAT " should be default but is " CSETSTATE_FORMAT, index, get_by_index(index).value()));
     set_by_index(index, InCSetState::Humongous);
   }
 
@@ -114,13 +114,13 @@
 
   void set_in_young(uintptr_t index) {
     assert(get_by_index(index).is_default(),
-           err_msg("State at index " INTPTR_FORMAT" should be default but is " CSETSTATE_FORMAT, index, get_by_index(index).value()));
+           err_msg("State at index " INTPTR_FORMAT " should be default but is " CSETSTATE_FORMAT, index, get_by_index(index).value()));
     set_by_index(index, InCSetState::Young);
   }
 
   void set_in_old(uintptr_t index) {
     assert(get_by_index(index).is_default(),
-           err_msg("State at index " INTPTR_FORMAT" should be default but is " CSETSTATE_FORMAT, index, get_by_index(index).value()));
+           err_msg("State at index " INTPTR_FORMAT " should be default but is " CSETSTATE_FORMAT, index, get_by_index(index).value()));
     set_by_index(index, InCSetState::Old);
   }
 
--- a/hotspot/src/share/vm/gc/g1/g1MMUTracker.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1MMUTracker.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -24,6 +24,7 @@
 
 #include "precompiled.hpp"
 #include "gc/g1/g1MMUTracker.hpp"
+#include "gc/shared/gcTrace.hpp"
 #include "runtime/mutexLocker.hpp"
 #include "utilities/ostream.hpp"
 
@@ -75,7 +76,7 @@
   return gc_time;
 }
 
-void G1MMUTrackerQueue::add_pause(double start, double end, bool gc_thread) {
+void G1MMUTrackerQueue::add_pause(double start, double end, const GCId& gcId) {
   double duration = end - start;
 
   remove_expired_entries(end);
@@ -102,6 +103,10 @@
     ++_no_entries;
   }
   _array[_head_index] = G1MMUTrackerQueueElem(start, end);
+
+  // Current entry needs to be added before calculating the value
+  double slice_time = calculate_gc_time(end);
+  G1MMUTracer::report_mmu(gcId, _time_slice, slice_time, _max_gc_time);
 }
 
 // basically the _internal call does not remove expired entries
--- a/hotspot/src/share/vm/gc/g1/g1MMUTracker.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1MMUTracker.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -25,6 +25,7 @@
 #ifndef SHARE_VM_GC_G1_G1MMUTRACKER_HPP
 #define SHARE_VM_GC_G1_G1MMUTRACKER_HPP
 
+#include "gc/shared/gcId.hpp"
 #include "memory/allocation.hpp"
 #include "utilities/debug.hpp"
 
@@ -42,7 +43,7 @@
 public:
   G1MMUTracker(double time_slice, double max_gc_time);
 
-  virtual void add_pause(double start, double end, bool gc_thread) = 0;
+  virtual void add_pause(double start, double end, const GCId& gcId) = 0;
   virtual double when_sec(double current_time, double pause_time) = 0;
 
   double max_gc_time() {
@@ -126,7 +127,7 @@
 public:
   G1MMUTrackerQueue(double time_slice, double max_gc_time);
 
-  virtual void add_pause(double start, double end, bool gc_thread);
+  virtual void add_pause(double start, double end, const GCId& gcId);
 
   virtual double when_sec(double current_time, double pause_time);
 };
--- a/hotspot/src/share/vm/gc/g1/g1OopClosures.inline.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1OopClosures.inline.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -118,7 +118,7 @@
   oop obj = oopDesc::load_decode_heap_oop(p);
   if (_cm->verbose_high()) {
     gclog_or_tty->print_cr("[%u] we're looking at location "
-                           "*"PTR_FORMAT" = "PTR_FORMAT,
+                           "*" PTR_FORMAT " = " PTR_FORMAT,
                            _task->worker_id(), p2i(p), p2i((void*) obj));
   }
   _task->deal_with_reference(obj);
--- a/hotspot/src/share/vm/gc/g1/g1RemSet.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1RemSet.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -424,7 +424,7 @@
 bool G1RemSet::refine_card(jbyte* card_ptr, uint worker_i,
                            bool check_for_refs_into_cset) {
   assert(_g1->is_in_exact(_ct_bs->addr_for(card_ptr)),
-         err_msg("Card at "PTR_FORMAT" index "SIZE_FORMAT" representing heap at "PTR_FORMAT" (%u) must be in committed heap",
+         err_msg("Card at " PTR_FORMAT " index " SIZE_FORMAT " representing heap at " PTR_FORMAT " (%u) must be in committed heap",
                  p2i(card_ptr),
                  _ct_bs->index_for(_ct_bs->addr_for(card_ptr)),
                  p2i(_ct_bs->addr_for(card_ptr)),
--- a/hotspot/src/share/vm/gc/g1/g1RemSetSummary.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1RemSetSummary.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -187,22 +187,22 @@
   size_t code_root_elems() const { return _code_root_elems; }
 
   void print_rs_mem_info_on(outputStream * out, size_t total) {
-    out->print_cr("    "SIZE_FORMAT_W(8)"K (%5.1f%%) by "SIZE_FORMAT" %s regions",
+    out->print_cr("    " SIZE_FORMAT_W(8) "K (%5.1f%%) by " SIZE_FORMAT " %s regions",
         round_to_K(rs_mem_size()), rs_mem_size_percent_of(total), amount(), _name);
   }
 
   void print_cards_occupied_info_on(outputStream * out, size_t total) {
-    out->print_cr("     "SIZE_FORMAT_W(8)" (%5.1f%%) entries by "SIZE_FORMAT" %s regions",
+    out->print_cr("     " SIZE_FORMAT_W(8) " (%5.1f%%) entries by " SIZE_FORMAT " %s regions",
         cards_occupied(), cards_occupied_percent_of(total), amount(), _name);
   }
 
   void print_code_root_mem_info_on(outputStream * out, size_t total) {
-    out->print_cr("    "SIZE_FORMAT_W(8)"K (%5.1f%%) by "SIZE_FORMAT" %s regions",
+    out->print_cr("    " SIZE_FORMAT_W(8) "K (%5.1f%%) by " SIZE_FORMAT " %s regions",
         round_to_K(code_root_mem_size()), code_root_mem_size_percent_of(total), amount(), _name);
   }
 
   void print_code_root_elems_info_on(outputStream * out, size_t total) {
-    out->print_cr("     "SIZE_FORMAT_W(8)" (%5.1f%%) elements by "SIZE_FORMAT" %s regions",
+    out->print_cr("     " SIZE_FORMAT_W(8) " (%5.1f%%) elements by " SIZE_FORMAT " %s regions",
         code_root_elems(), code_root_elems_percent_of(total), amount(), _name);
   }
 };
@@ -280,19 +280,19 @@
     RegionTypeCounter* counters[] = { &_young, &_humonguous, &_free, &_old, NULL };
 
     out->print_cr("\n Current rem set statistics");
-    out->print_cr("  Total per region rem sets sizes = "SIZE_FORMAT"K."
-                  " Max = "SIZE_FORMAT"K.",
+    out->print_cr("  Total per region rem sets sizes = " SIZE_FORMAT "K."
+                  " Max = " SIZE_FORMAT "K.",
                   round_to_K(total_rs_mem_sz()), round_to_K(max_rs_mem_sz()));
     for (RegionTypeCounter** current = &counters[0]; *current != NULL; current++) {
       (*current)->print_rs_mem_info_on(out, total_rs_mem_sz());
     }
 
-    out->print_cr("   Static structures = "SIZE_FORMAT"K,"
-                  " free_lists = "SIZE_FORMAT"K.",
+    out->print_cr("   Static structures = " SIZE_FORMAT "K,"
+                  " free_lists = " SIZE_FORMAT "K.",
                   round_to_K(HeapRegionRemSet::static_mem_size()),
                   round_to_K(HeapRegionRemSet::fl_mem_size()));
 
-    out->print_cr("    "SIZE_FORMAT" occupied cards represented.",
+    out->print_cr("    " SIZE_FORMAT " occupied cards represented.",
                   total_cards_occupied());
     for (RegionTypeCounter** current = &counters[0]; *current != NULL; current++) {
       (*current)->print_cards_occupied_info_on(out, total_cards_occupied());
@@ -300,30 +300,30 @@
 
     // Largest sized rem set region statistics
     HeapRegionRemSet* rem_set = max_rs_mem_sz_region()->rem_set();
-    out->print_cr("    Region with largest rem set = "HR_FORMAT", "
-                  "size = "SIZE_FORMAT "K, occupied = "SIZE_FORMAT"K.",
+    out->print_cr("    Region with largest rem set = " HR_FORMAT ", "
+                  "size = " SIZE_FORMAT "K, occupied = " SIZE_FORMAT "K.",
                   HR_FORMAT_PARAMS(max_rs_mem_sz_region()),
                   round_to_K(rem_set->mem_size()),
                   round_to_K(rem_set->occupied()));
 
     // Strong code root statistics
     HeapRegionRemSet* max_code_root_rem_set = max_code_root_mem_sz_region()->rem_set();
-    out->print_cr("  Total heap region code root sets sizes = "SIZE_FORMAT"K."
-                  "  Max = "SIZE_FORMAT"K.",
+    out->print_cr("  Total heap region code root sets sizes = " SIZE_FORMAT "K."
+                  "  Max = " SIZE_FORMAT "K.",
                   round_to_K(total_code_root_mem_sz()),
                   round_to_K(max_code_root_rem_set->strong_code_roots_mem_size()));
     for (RegionTypeCounter** current = &counters[0]; *current != NULL; current++) {
       (*current)->print_code_root_mem_info_on(out, total_code_root_mem_sz());
     }
 
-    out->print_cr("    "SIZE_FORMAT" code roots represented.",
+    out->print_cr("    " SIZE_FORMAT " code roots represented.",
                   total_code_root_elems());
     for (RegionTypeCounter** current = &counters[0]; *current != NULL; current++) {
       (*current)->print_code_root_elems_info_on(out, total_code_root_elems());
     }
 
-    out->print_cr("    Region with largest amount of code roots = "HR_FORMAT", "
-                  "size = "SIZE_FORMAT "K, num_elems = "SIZE_FORMAT".",
+    out->print_cr("    Region with largest amount of code roots = " HR_FORMAT ", "
+                  "size = " SIZE_FORMAT "K, num_elems = " SIZE_FORMAT ".",
                   HR_FORMAT_PARAMS(max_code_root_mem_sz_region()),
                   round_to_K(max_code_root_rem_set->strong_code_roots_mem_size()),
                   round_to_K(max_code_root_rem_set->strong_code_roots_list_length()));
@@ -332,16 +332,16 @@
 
 void G1RemSetSummary::print_on(outputStream* out) {
   out->print_cr("\n Recent concurrent refinement statistics");
-  out->print_cr("  Processed "SIZE_FORMAT" cards",
+  out->print_cr("  Processed " SIZE_FORMAT " cards",
                 num_concurrent_refined_cards());
-  out->print_cr("  Of "SIZE_FORMAT" completed buffers:", num_processed_buf_total());
-  out->print_cr("     "SIZE_FORMAT_W(8)" (%5.1f%%) by concurrent RS threads.",
+  out->print_cr("  Of " SIZE_FORMAT " completed buffers:", num_processed_buf_total());
+  out->print_cr("     " SIZE_FORMAT_W(8) " (%5.1f%%) by concurrent RS threads.",
                 num_processed_buf_total(),
                 percent_of(num_processed_buf_rs_threads(), num_processed_buf_total()));
-  out->print_cr("     "SIZE_FORMAT_W(8)" (%5.1f%%) by mutator threads.",
+  out->print_cr("     " SIZE_FORMAT_W(8) " (%5.1f%%) by mutator threads.",
                 num_processed_buf_mutator(),
                 percent_of(num_processed_buf_mutator(), num_processed_buf_total()));
-  out->print_cr("  Did "SIZE_FORMAT" coarsenings.", num_coarsenings());
+  out->print_cr("  Did " SIZE_FORMAT " coarsenings.", num_coarsenings());
   out->print_cr("  Concurrent RS threads times (s)");
   out->print("     ");
   for (uint i = 0; i < _num_vtimes; i++) {
--- a/hotspot/src/share/vm/gc/g1/g1StringDedupQueue.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1StringDedupQueue.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -155,7 +155,7 @@
 void G1StringDedupQueue::print_statistics(outputStream* st) {
   st->print_cr(
     "   [Queue]\n"
-    "      [Dropped: "UINTX_FORMAT"]", _queue->_dropped);
+    "      [Dropped: " UINTX_FORMAT "]", _queue->_dropped);
 }
 
 void G1StringDedupQueue::verify() {
--- a/hotspot/src/share/vm/gc/g1/g1StringDedupStat.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1StringDedupStat.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -80,8 +80,8 @@
   st->stamp(PrintGCTimeStamps);
   st->print_cr(
     "[GC concurrent-string-deduplication, "
-    G1_STRDEDUP_BYTES_FORMAT_NS"->"G1_STRDEDUP_BYTES_FORMAT_NS"("G1_STRDEDUP_BYTES_FORMAT_NS"), avg "
-    G1_STRDEDUP_PERCENT_FORMAT_NS", "G1_STRDEDUP_TIME_FORMAT"]",
+    G1_STRDEDUP_BYTES_FORMAT_NS "->" G1_STRDEDUP_BYTES_FORMAT_NS "(" G1_STRDEDUP_BYTES_FORMAT_NS "), avg "
+    G1_STRDEDUP_PERCENT_FORMAT_NS ", " G1_STRDEDUP_TIME_FORMAT "]",
     G1_STRDEDUP_BYTES_PARAM(last_stat._new_bytes),
     G1_STRDEDUP_BYTES_PARAM(last_stat._new_bytes - last_stat._deduped_bytes),
     G1_STRDEDUP_BYTES_PARAM(last_stat._deduped_bytes),
@@ -135,22 +135,22 @@
 
   if (total) {
     st->print_cr(
-      "   [Total Exec: "UINTX_FORMAT"/"G1_STRDEDUP_TIME_FORMAT", Idle: "UINTX_FORMAT"/"G1_STRDEDUP_TIME_FORMAT", Blocked: "UINTX_FORMAT"/"G1_STRDEDUP_TIME_FORMAT"]",
+      "   [Total Exec: " UINTX_FORMAT "/" G1_STRDEDUP_TIME_FORMAT ", Idle: " UINTX_FORMAT "/" G1_STRDEDUP_TIME_FORMAT ", Blocked: " UINTX_FORMAT "/" G1_STRDEDUP_TIME_FORMAT "]",
       stat._exec, stat._exec_elapsed, stat._idle, stat._idle_elapsed, stat._block, stat._block_elapsed);
   } else {
     st->print_cr(
-      "   [Last Exec: "G1_STRDEDUP_TIME_FORMAT", Idle: "G1_STRDEDUP_TIME_FORMAT", Blocked: "UINTX_FORMAT"/"G1_STRDEDUP_TIME_FORMAT"]",
+      "   [Last Exec: " G1_STRDEDUP_TIME_FORMAT ", Idle: " G1_STRDEDUP_TIME_FORMAT ", Blocked: " UINTX_FORMAT "/" G1_STRDEDUP_TIME_FORMAT "]",
       stat._exec_elapsed, stat._idle_elapsed, stat._block, stat._block_elapsed);
   }
   st->print_cr(
-    "      [Inspected:    "G1_STRDEDUP_OBJECTS_FORMAT"]\n"
-    "         [Skipped:   "G1_STRDEDUP_OBJECTS_FORMAT"("G1_STRDEDUP_PERCENT_FORMAT")]\n"
-    "         [Hashed:    "G1_STRDEDUP_OBJECTS_FORMAT"("G1_STRDEDUP_PERCENT_FORMAT")]\n"
-    "         [Known:     "G1_STRDEDUP_OBJECTS_FORMAT"("G1_STRDEDUP_PERCENT_FORMAT")]\n"
-    "         [New:       "G1_STRDEDUP_OBJECTS_FORMAT"("G1_STRDEDUP_PERCENT_FORMAT") "G1_STRDEDUP_BYTES_FORMAT"]\n"
-    "      [Deduplicated: "G1_STRDEDUP_OBJECTS_FORMAT"("G1_STRDEDUP_PERCENT_FORMAT") "G1_STRDEDUP_BYTES_FORMAT"("G1_STRDEDUP_PERCENT_FORMAT")]\n"
-    "         [Young:     "G1_STRDEDUP_OBJECTS_FORMAT"("G1_STRDEDUP_PERCENT_FORMAT") "G1_STRDEDUP_BYTES_FORMAT"("G1_STRDEDUP_PERCENT_FORMAT")]\n"
-    "         [Old:       "G1_STRDEDUP_OBJECTS_FORMAT"("G1_STRDEDUP_PERCENT_FORMAT") "G1_STRDEDUP_BYTES_FORMAT"("G1_STRDEDUP_PERCENT_FORMAT")]",
+    "      [Inspected:    " G1_STRDEDUP_OBJECTS_FORMAT "]\n"
+    "         [Skipped:   " G1_STRDEDUP_OBJECTS_FORMAT "(" G1_STRDEDUP_PERCENT_FORMAT ")]\n"
+    "         [Hashed:    " G1_STRDEDUP_OBJECTS_FORMAT "(" G1_STRDEDUP_PERCENT_FORMAT ")]\n"
+    "         [Known:     " G1_STRDEDUP_OBJECTS_FORMAT "(" G1_STRDEDUP_PERCENT_FORMAT ")]\n"
+    "         [New:       " G1_STRDEDUP_OBJECTS_FORMAT "(" G1_STRDEDUP_PERCENT_FORMAT ") " G1_STRDEDUP_BYTES_FORMAT "]\n"
+    "      [Deduplicated: " G1_STRDEDUP_OBJECTS_FORMAT "(" G1_STRDEDUP_PERCENT_FORMAT ") " G1_STRDEDUP_BYTES_FORMAT "(" G1_STRDEDUP_PERCENT_FORMAT ")]\n"
+    "         [Young:     " G1_STRDEDUP_OBJECTS_FORMAT "(" G1_STRDEDUP_PERCENT_FORMAT ") " G1_STRDEDUP_BYTES_FORMAT "(" G1_STRDEDUP_PERCENT_FORMAT ")]\n"
+    "         [Old:       " G1_STRDEDUP_OBJECTS_FORMAT "(" G1_STRDEDUP_PERCENT_FORMAT ") " G1_STRDEDUP_BYTES_FORMAT "(" G1_STRDEDUP_PERCENT_FORMAT ")]",
     stat._inspected,
     stat._skipped, skipped_percent,
     stat._hashed, hashed_percent,
--- a/hotspot/src/share/vm/gc/g1/g1StringDedupTable.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/g1StringDedupTable.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -556,12 +556,12 @@
 void G1StringDedupTable::print_statistics(outputStream* st) {
   st->print_cr(
     "   [Table]\n"
-    "      [Memory Usage: "G1_STRDEDUP_BYTES_FORMAT_NS"]\n"
-    "      [Size: "SIZE_FORMAT", Min: "SIZE_FORMAT", Max: "SIZE_FORMAT"]\n"
-    "      [Entries: "UINTX_FORMAT", Load: "G1_STRDEDUP_PERCENT_FORMAT_NS", Cached: " UINTX_FORMAT ", Added: "UINTX_FORMAT", Removed: "UINTX_FORMAT"]\n"
-    "      [Resize Count: "UINTX_FORMAT", Shrink Threshold: "UINTX_FORMAT"("G1_STRDEDUP_PERCENT_FORMAT_NS"), Grow Threshold: "UINTX_FORMAT"("G1_STRDEDUP_PERCENT_FORMAT_NS")]\n"
-    "      [Rehash Count: "UINTX_FORMAT", Rehash Threshold: "UINTX_FORMAT", Hash Seed: 0x%x]\n"
-    "      [Age Threshold: "UINTX_FORMAT"]",
+    "      [Memory Usage: " G1_STRDEDUP_BYTES_FORMAT_NS "]\n"
+    "      [Size: " SIZE_FORMAT ", Min: " SIZE_FORMAT ", Max: " SIZE_FORMAT "]\n"
+    "      [Entries: " UINTX_FORMAT ", Load: " G1_STRDEDUP_PERCENT_FORMAT_NS ", Cached: " UINTX_FORMAT ", Added: " UINTX_FORMAT ", Removed: " UINTX_FORMAT "]\n"
+    "      [Resize Count: " UINTX_FORMAT ", Shrink Threshold: " UINTX_FORMAT "(" G1_STRDEDUP_PERCENT_FORMAT_NS "), Grow Threshold: " UINTX_FORMAT "(" G1_STRDEDUP_PERCENT_FORMAT_NS ")]\n"
+    "      [Rehash Count: " UINTX_FORMAT ", Rehash Threshold: " UINTX_FORMAT ", Hash Seed: 0x%x]\n"
+    "      [Age Threshold: " UINTX_FORMAT "]",
     G1_STRDEDUP_BYTES_PARAM(_table->_size * sizeof(G1StringDedupEntry*) + (_table->_entries + _entry_cache->size()) * sizeof(G1StringDedupEntry)),
     _table->_size, _min_size, _max_size,
     _table->_entries, (double)_table->_entries / (double)_table->_size * 100.0, _entry_cache->size(), _entries_added, _entries_removed,
--- a/hotspot/src/share/vm/gc/g1/heapRegion.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/heapRegion.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -327,7 +327,7 @@
                                                   bool during_conc_mark,
                                                   size_t marked_bytes) {
   assert(marked_bytes <= used(),
-         err_msg("marked: "SIZE_FORMAT" used: "SIZE_FORMAT, marked_bytes, used()));
+         err_msg("marked: " SIZE_FORMAT " used: " SIZE_FORMAT, marked_bytes, used()));
   _prev_top_at_mark_start = top();
   _prev_marked_bytes = marked_bytes;
 }
@@ -504,9 +504,9 @@
         // Object is in the region. Check that its less than top
         if (_hr->top() <= (HeapWord*)obj) {
           // Object is above top
-          gclog_or_tty->print_cr("Object "PTR_FORMAT" in region "
-                                 "["PTR_FORMAT", "PTR_FORMAT") is above "
-                                 "top "PTR_FORMAT,
+          gclog_or_tty->print_cr("Object " PTR_FORMAT " in region "
+                                 "[" PTR_FORMAT ", " PTR_FORMAT ") is above "
+                                 "top " PTR_FORMAT,
                                  p2i(obj), p2i(_hr->bottom()), p2i(_hr->end()), p2i(_hr->top()));
           _failures = true;
           return;
@@ -540,22 +540,22 @@
     if (nm != NULL) {
       // Verify that the nemthod is live
       if (!nm->is_alive()) {
-        gclog_or_tty->print_cr("region ["PTR_FORMAT","PTR_FORMAT"] has dead nmethod "
-                               PTR_FORMAT" in its strong code roots",
+        gclog_or_tty->print_cr("region [" PTR_FORMAT "," PTR_FORMAT "] has dead nmethod "
+                               PTR_FORMAT " in its strong code roots",
                                p2i(_hr->bottom()), p2i(_hr->end()), p2i(nm));
         _failures = true;
       } else {
         VerifyStrongCodeRootOopClosure oop_cl(_hr, nm);
         nm->oops_do(&oop_cl);
         if (!oop_cl.has_oops_in_region()) {
-          gclog_or_tty->print_cr("region ["PTR_FORMAT","PTR_FORMAT"] has nmethod "
-                                 PTR_FORMAT" in its strong code roots "
+          gclog_or_tty->print_cr("region [" PTR_FORMAT "," PTR_FORMAT "] has nmethod "
+                                 PTR_FORMAT " in its strong code roots "
                                  "with no pointers into region",
                                  p2i(_hr->bottom()), p2i(_hr->end()), p2i(nm));
           _failures = true;
         } else if (oop_cl.failures()) {
-          gclog_or_tty->print_cr("region ["PTR_FORMAT","PTR_FORMAT"] has other "
-                                 "failures for nmethod "PTR_FORMAT,
+          gclog_or_tty->print_cr("region [" PTR_FORMAT "," PTR_FORMAT "] has other "
+                                 "failures for nmethod " PTR_FORMAT,
                                  p2i(_hr->bottom()), p2i(_hr->end()), p2i(nm));
           _failures = true;
         }
@@ -589,8 +589,8 @@
   // on its strong code root list
   if (is_empty()) {
     if (strong_code_roots_length > 0) {
-      gclog_or_tty->print_cr("region ["PTR_FORMAT","PTR_FORMAT"] is empty "
-                             "but has "SIZE_FORMAT" code root entries",
+      gclog_or_tty->print_cr("region [" PTR_FORMAT "," PTR_FORMAT "] is empty "
+                             "but has " SIZE_FORMAT " code root entries",
                              p2i(bottom()), p2i(end()), strong_code_roots_length);
       *failures = true;
     }
@@ -599,8 +599,8 @@
 
   if (is_continues_humongous()) {
     if (strong_code_roots_length > 0) {
-      gclog_or_tty->print_cr("region "HR_FORMAT" is a continuation of a humongous "
-                             "region but has "SIZE_FORMAT" code root entries",
+      gclog_or_tty->print_cr("region " HR_FORMAT " is a continuation of a humongous "
+                             "region but has " SIZE_FORMAT " code root entries",
                              HR_FORMAT_PARAMS(this), strong_code_roots_length);
       *failures = true;
     }
@@ -625,7 +625,7 @@
   else
     st->print("   ");
   st->print(" TS %5d", _gc_time_stamp);
-  st->print(" PTAMS "PTR_FORMAT" NTAMS "PTR_FORMAT,
+  st->print(" PTAMS " PTR_FORMAT " NTAMS " PTR_FORMAT,
             p2i(prev_top_at_mark_start()), p2i(next_top_at_mark_start()));
   G1OffsetTableContigSpace::print_on(st);
 }
@@ -686,25 +686,25 @@
         }
         if (!_g1h->is_in_closed_subset(obj)) {
           HeapRegion* from = _g1h->heap_region_containing((HeapWord*)p);
-          gclog_or_tty->print_cr("Field "PTR_FORMAT
-                                 " of live obj "PTR_FORMAT" in region "
-                                 "["PTR_FORMAT", "PTR_FORMAT")",
+          gclog_or_tty->print_cr("Field " PTR_FORMAT
+                                 " of live obj " PTR_FORMAT " in region "
+                                 "[" PTR_FORMAT ", " PTR_FORMAT ")",
                                  p2i(p), p2i(_containing_obj),
                                  p2i(from->bottom()), p2i(from->end()));
           print_object(gclog_or_tty, _containing_obj);
-          gclog_or_tty->print_cr("points to obj "PTR_FORMAT" not in the heap",
+          gclog_or_tty->print_cr("points to obj " PTR_FORMAT " not in the heap",
                                  p2i(obj));
         } else {
           HeapRegion* from = _g1h->heap_region_containing((HeapWord*)p);
           HeapRegion* to   = _g1h->heap_region_containing((HeapWord*)obj);
-          gclog_or_tty->print_cr("Field "PTR_FORMAT
-                                 " of live obj "PTR_FORMAT" in region "
-                                 "["PTR_FORMAT", "PTR_FORMAT")",
+          gclog_or_tty->print_cr("Field " PTR_FORMAT
+                                 " of live obj " PTR_FORMAT " in region "
+                                 "[" PTR_FORMAT ", " PTR_FORMAT ")",
                                  p2i(p), p2i(_containing_obj),
                                  p2i(from->bottom()), p2i(from->end()));
           print_object(gclog_or_tty, _containing_obj);
-          gclog_or_tty->print_cr("points to dead obj "PTR_FORMAT" in region "
-                                 "["PTR_FORMAT", "PTR_FORMAT")",
+          gclog_or_tty->print_cr("points to dead obj " PTR_FORMAT " in region "
+                                 "[" PTR_FORMAT ", " PTR_FORMAT ")",
                                  p2i(obj), p2i(to->bottom()), p2i(to->end()));
           print_object(gclog_or_tty, obj);
         }
@@ -740,14 +740,14 @@
               gclog_or_tty->print_cr("----------");
             }
             gclog_or_tty->print_cr("Missing rem set entry:");
-            gclog_or_tty->print_cr("Field "PTR_FORMAT" "
-                                   "of obj "PTR_FORMAT", "
-                                   "in region "HR_FORMAT,
+            gclog_or_tty->print_cr("Field " PTR_FORMAT " "
+                                   "of obj " PTR_FORMAT ", "
+                                   "in region " HR_FORMAT,
                                    p2i(p), p2i(_containing_obj),
                                    HR_FORMAT_PARAMS(from));
             _containing_obj->print_on(gclog_or_tty);
-            gclog_or_tty->print_cr("points to obj "PTR_FORMAT" "
-                                   "in region "HR_FORMAT,
+            gclog_or_tty->print_cr("points to obj " PTR_FORMAT " "
+                                   "in region " HR_FORMAT,
                                    p2i(obj),
                                    HR_FORMAT_PARAMS(to));
             obj->print_on(gclog_or_tty);
@@ -783,8 +783,8 @@
 
     if (is_region_humongous != g1->is_humongous(obj_size) &&
         !g1->is_obj_dead(obj, this)) { // Dead objects may have bigger block_size since they span several objects.
-      gclog_or_tty->print_cr("obj "PTR_FORMAT" is of %shumongous size ("
-                             SIZE_FORMAT" words) in a %shumongous region",
+      gclog_or_tty->print_cr("obj " PTR_FORMAT " is of %shumongous size ("
+                             SIZE_FORMAT " words) in a %shumongous region",
                              p2i(p), g1->is_humongous(obj_size) ? "" : "non-",
                              obj_size, is_region_humongous ? "" : "non-");
        *failures = true;
@@ -798,12 +798,12 @@
                                    (vo == VerifyOption_G1UsePrevMarking &&
                                    ClassLoaderDataGraph::unload_list_contains(klass));
         if (!is_metaspace_object) {
-          gclog_or_tty->print_cr("klass "PTR_FORMAT" of object "PTR_FORMAT" "
+          gclog_or_tty->print_cr("klass " PTR_FORMAT " of object " PTR_FORMAT " "
                                  "not metadata", p2i(klass), p2i(obj));
           *failures = true;
           return;
         } else if (!klass->is_klass()) {
-          gclog_or_tty->print_cr("klass "PTR_FORMAT" of object "PTR_FORMAT" "
+          gclog_or_tty->print_cr("klass " PTR_FORMAT " of object " PTR_FORMAT " "
                                  "not a klass", p2i(klass), p2i(obj));
           *failures = true;
           return;
@@ -819,7 +819,7 @@
           }
         }
       } else {
-        gclog_or_tty->print_cr(PTR_FORMAT" no an oop", p2i(obj));
+        gclog_or_tty->print_cr(PTR_FORMAT " no an oop", p2i(obj));
         *failures = true;
         return;
       }
@@ -833,8 +833,8 @@
   }
 
   if (p != top()) {
-    gclog_or_tty->print_cr("end of last object "PTR_FORMAT" "
-                           "does not match top "PTR_FORMAT, p2i(p), p2i(top()));
+    gclog_or_tty->print_cr("end of last object " PTR_FORMAT " "
+                           "does not match top " PTR_FORMAT, p2i(p), p2i(top()));
     *failures = true;
     return;
   }
@@ -849,8 +849,8 @@
     HeapWord* addr_1 = p;
     HeapWord* b_start_1 = _offsets.block_start_const(addr_1);
     if (b_start_1 != p) {
-      gclog_or_tty->print_cr("BOT look up for top: "PTR_FORMAT" "
-                             " yielded "PTR_FORMAT", expecting "PTR_FORMAT,
+      gclog_or_tty->print_cr("BOT look up for top: " PTR_FORMAT " "
+                             " yielded " PTR_FORMAT ", expecting " PTR_FORMAT,
                              p2i(addr_1), p2i(b_start_1), p2i(p));
       *failures = true;
       return;
@@ -861,8 +861,8 @@
     if (addr_2 < the_end) {
       HeapWord* b_start_2 = _offsets.block_start_const(addr_2);
       if (b_start_2 != p) {
-        gclog_or_tty->print_cr("BOT look up for top + 1: "PTR_FORMAT" "
-                               " yielded "PTR_FORMAT", expecting "PTR_FORMAT,
+        gclog_or_tty->print_cr("BOT look up for top + 1: " PTR_FORMAT " "
+                               " yielded " PTR_FORMAT ", expecting " PTR_FORMAT,
                                p2i(addr_2), p2i(b_start_2), p2i(p));
         *failures = true;
         return;
@@ -875,8 +875,8 @@
     if (addr_3 < the_end) {
       HeapWord* b_start_3 = _offsets.block_start_const(addr_3);
       if (b_start_3 != p) {
-        gclog_or_tty->print_cr("BOT look up for top + diff: "PTR_FORMAT" "
-                               " yielded "PTR_FORMAT", expecting "PTR_FORMAT,
+        gclog_or_tty->print_cr("BOT look up for top + diff: " PTR_FORMAT " "
+                               " yielded " PTR_FORMAT ", expecting " PTR_FORMAT,
                                p2i(addr_3), p2i(b_start_3), p2i(p));
         *failures = true;
         return;
@@ -887,8 +887,8 @@
     HeapWord* addr_4 = the_end - 1;
     HeapWord* b_start_4 = _offsets.block_start_const(addr_4);
     if (b_start_4 != p) {
-      gclog_or_tty->print_cr("BOT look up for end - 1: "PTR_FORMAT" "
-                             " yielded "PTR_FORMAT", expecting "PTR_FORMAT,
+      gclog_or_tty->print_cr("BOT look up for end - 1: " PTR_FORMAT " "
+                             " yielded " PTR_FORMAT ", expecting " PTR_FORMAT,
                              p2i(addr_4), p2i(b_start_4), p2i(p));
       *failures = true;
       return;
@@ -896,8 +896,8 @@
   }
 
   if (is_region_humongous && object_num > 1) {
-    gclog_or_tty->print_cr("region ["PTR_FORMAT","PTR_FORMAT"] is humongous "
-                           "but has "SIZE_FORMAT", objects",
+    gclog_or_tty->print_cr("region [" PTR_FORMAT "," PTR_FORMAT "] is humongous "
+                           "but has " SIZE_FORMAT ", objects",
                            p2i(bottom()), p2i(end()), object_num);
     *failures = true;
     return;
--- a/hotspot/src/share/vm/gc/g1/heapRegion.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/heapRegion.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -51,7 +51,7 @@
 class HeapRegionSetBase;
 class nmethod;
 
-#define HR_FORMAT "%u:(%s)["PTR_FORMAT","PTR_FORMAT","PTR_FORMAT"]"
+#define HR_FORMAT "%u:(%s)[" PTR_FORMAT "," PTR_FORMAT "," PTR_FORMAT "]"
 #define HR_FORMAT_PARAMS(_hr_) \
                 (_hr_)->hrm_index(), \
                 (_hr_)->get_short_type_str(), \
@@ -538,8 +538,8 @@
   void set_containing_set(HeapRegionSetBase* containing_set) {
     assert((containing_set == NULL && _containing_set != NULL) ||
            (containing_set != NULL && _containing_set == NULL),
-           err_msg("containing_set: "PTR_FORMAT" "
-                   "_containing_set: "PTR_FORMAT,
+           err_msg("containing_set: " PTR_FORMAT " "
+                   "_containing_set: " PTR_FORMAT,
                    p2i(containing_set), p2i(_containing_set)));
 
     _containing_set = containing_set;
--- a/hotspot/src/share/vm/gc/g1/heapRegion.inline.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/heapRegion.inline.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -113,7 +113,7 @@
 
   assert(ClassUnloadingWithConcurrentMark,
       err_msg("All blocks should be objects if G1 Class Unloading isn't used. "
-              "HR: ["PTR_FORMAT", "PTR_FORMAT", "PTR_FORMAT") "
+              "HR: [" PTR_FORMAT ", " PTR_FORMAT ", " PTR_FORMAT ") "
               "addr: " PTR_FORMAT,
               p2i(bottom()), p2i(top()), p2i(end()), p2i(addr)));
 
--- a/hotspot/src/share/vm/gc/g1/heapRegionManager.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/heapRegionManager.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -486,7 +486,7 @@
     HeapRegion* hr = _regions.get_by_index(i);
     guarantee(hr != NULL, err_msg("invariant: i: %u", i));
     guarantee(!prev_committed || hr->bottom() == prev_end,
-              err_msg("invariant i: %u "HR_FORMAT" prev_end: "PTR_FORMAT,
+              err_msg("invariant i: %u " HR_FORMAT " prev_end: " PTR_FORMAT,
                       i, HR_FORMAT_PARAMS(hr), p2i(prev_end)));
     guarantee(hr->hrm_index() == i,
               err_msg("invariant: i: %u hrm_index(): %u", i, hr->hrm_index()));
--- a/hotspot/src/share/vm/gc/g1/heapRegionManager.inline.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/heapRegionManager.inline.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -31,9 +31,9 @@
 
 inline HeapRegion* HeapRegionManager::addr_to_region(HeapWord* addr) const {
   assert(addr < heap_end(),
-        err_msg("addr: "PTR_FORMAT" end: "PTR_FORMAT, p2i(addr), p2i(heap_end())));
+        err_msg("addr: " PTR_FORMAT " end: " PTR_FORMAT, p2i(addr), p2i(heap_end())));
   assert(addr >= heap_bottom(),
-        err_msg("addr: "PTR_FORMAT" bottom: "PTR_FORMAT, p2i(addr), p2i(heap_bottom())));
+        err_msg("addr: " PTR_FORMAT " bottom: " PTR_FORMAT, p2i(addr), p2i(heap_bottom())));
 
   HeapRegion* hr = _regions.get_by_address(addr);
   return hr;
--- a/hotspot/src/share/vm/gc/g1/heapRegionRemSet.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/heapRegionRemSet.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -90,7 +90,7 @@
     // concurrency.
 
     if (G1TraceHeapRegionRememberedSet) {
-      gclog_or_tty->print_cr("    PRT::Add_reference_work(" PTR_FORMAT "->" PTR_FORMAT").",
+      gclog_or_tty->print_cr("    PRT::Add_reference_work(" PTR_FORMAT "->" PTR_FORMAT ").",
                              p2i(from),
                              UseCompressedOops
                              ? p2i(oopDesc::load_decode_heap_oop((narrowOop*)from))
@@ -376,7 +376,7 @@
 
 void FromCardCache::invalidate(uint start_idx, size_t new_num_regions) {
   guarantee((size_t)start_idx + new_num_regions <= max_uintx,
-            err_msg("Trying to invalidate beyond maximum region, from %u size "SIZE_FORMAT,
+            err_msg("Trying to invalidate beyond maximum region, from %u size " SIZE_FORMAT,
                     start_idx, new_num_regions));
   for (uint i = 0; i < HeapRegionRemSet::num_par_rem_sets(); i++) {
     uint end_idx = (start_idx + (uint)new_num_regions);
@@ -630,13 +630,13 @@
 
   assert(_coarse_map.size() == region_bm->size(), "Precondition");
   if (G1RSScrubVerbose) {
-    gclog_or_tty->print("   Coarse map: before = "SIZE_FORMAT"...",
+    gclog_or_tty->print("   Coarse map: before = " SIZE_FORMAT "...",
                         _n_coarse_entries);
   }
   _coarse_map.set_intersection(*region_bm);
   _n_coarse_entries = _coarse_map.count_one_bits();
   if (G1RSScrubVerbose) {
-    gclog_or_tty->print_cr("   after = "SIZE_FORMAT".", _n_coarse_entries);
+    gclog_or_tty->print_cr("   after = " SIZE_FORMAT ".", _n_coarse_entries);
   }
 
   // Now do the fine-grained maps.
@@ -1013,7 +1013,7 @@
 
   card_index = _cur_region_card_offset + _cur_card_in_prt;
   guarantee(_cur_card_in_prt < HeapRegion::CardsPerRegion,
-            err_msg("Card index "SIZE_FORMAT" must be within the region", _cur_card_in_prt));
+            err_msg("Card index " SIZE_FORMAT " must be within the region", _cur_card_in_prt));
   return true;
 }
 
@@ -1182,8 +1182,8 @@
 
   size_t min_prt_size = sizeof(void*) + dummy->bm()->size_in_words() * HeapWordSize;
   assert(dummy->mem_size() > min_prt_size,
-         err_msg("PerRegionTable memory usage is suspiciously small, only has "SIZE_FORMAT" bytes. "
-                 "Should be at least "SIZE_FORMAT" bytes.", dummy->mem_size(), min_prt_size));
+         err_msg("PerRegionTable memory usage is suspiciously small, only has " SIZE_FORMAT " bytes. "
+                 "Should be at least " SIZE_FORMAT " bytes.", dummy->mem_size(), min_prt_size));
   free(dummy);
   guarantee(dummy->mem_size() == fl_mem_size(), "fl_mem_size() does not return the correct element size");
   // try to reset the state
--- a/hotspot/src/share/vm/gc/g1/heapRegionSet.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/heapRegionSet.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -30,7 +30,7 @@
 uint FreeRegionList::_unrealistically_long_length = 0;
 
 void HeapRegionSetBase::fill_in_ext_msg(hrs_ext_msg* msg, const char* message) {
-  msg->append("[%s] %s ln: %u cy: "SIZE_FORMAT,
+  msg->append("[%s] %s ln: %u cy: " SIZE_FORMAT,
               name(), message, length(), total_capacity_bytes());
   fill_in_ext_msg_extra(msg);
 }
@@ -83,13 +83,13 @@
 
 void HeapRegionSetBase::print_on(outputStream* out, bool print_contents) {
   out->cr();
-  out->print_cr("Set: %s ("PTR_FORMAT")", name(), p2i(this));
+  out->print_cr("Set: %s (" PTR_FORMAT ")", name(), p2i(this));
   out->print_cr("  Region Assumptions");
   out->print_cr("    humongous         : %s", BOOL_TO_STR(regions_humongous()));
   out->print_cr("    free              : %s", BOOL_TO_STR(regions_free()));
   out->print_cr("  Attributes");
   out->print_cr("    length            : %14u", length());
-  out->print_cr("    total capacity    : "SIZE_FORMAT_W(14)" bytes",
+  out->print_cr("    total capacity    : " SIZE_FORMAT_W(14) " bytes",
                 total_capacity_bytes());
 }
 
@@ -105,7 +105,7 @@
 }
 
 void FreeRegionList::fill_in_ext_msg_extra(hrs_ext_msg* msg) {
-  msg->append(" hd: "PTR_FORMAT" tl: "PTR_FORMAT, p2i(_head), p2i(_tail));
+  msg->append(" hd: " PTR_FORMAT " tl: " PTR_FORMAT, p2i(_head), p2i(_tail));
 }
 
 void FreeRegionList::remove_all() {
@@ -276,8 +276,8 @@
 void FreeRegionList::print_on(outputStream* out, bool print_contents) {
   HeapRegionSetBase::print_on(out, print_contents);
   out->print_cr("  Linking");
-  out->print_cr("    head              : "PTR_FORMAT, p2i(_head));
-  out->print_cr("    tail              : "PTR_FORMAT, p2i(_tail));
+  out->print_cr("    head              : " PTR_FORMAT, p2i(_head));
+  out->print_cr("    tail              : " PTR_FORMAT, p2i(_tail));
 
   if (print_contents) {
     out->print_cr("  Contents");
@@ -305,7 +305,7 @@
 
     count++;
     guarantee(count < _unrealistically_long_length,
-        hrs_err_msg("[%s] the calculated length: %u seems very long, is there maybe a cycle? curr: "PTR_FORMAT" prev0: "PTR_FORMAT" " "prev1: "PTR_FORMAT" length: %u",
+        hrs_err_msg("[%s] the calculated length: %u seems very long, is there maybe a cycle? curr: " PTR_FORMAT " prev0: " PTR_FORMAT " " "prev1: " PTR_FORMAT " length: %u",
             name(), count, p2i(curr), p2i(prev0), p2i(prev1), length()));
 
     if (curr->next() != NULL) {
--- a/hotspot/src/share/vm/gc/g1/satbQueue.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/g1/satbQueue.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -200,8 +200,8 @@
 
 void ObjPtrQueue::print(const char* name,
                         void** buf, size_t index, size_t sz) {
-  gclog_or_tty->print_cr("  SATB BUFFER [%s] buf: "PTR_FORMAT" "
-                         "index: "SIZE_FORMAT" sz: "SIZE_FORMAT,
+  gclog_or_tty->print_cr("  SATB BUFFER [%s] buf: " PTR_FORMAT " "
+                         "index: " SIZE_FORMAT " sz: " SIZE_FORMAT,
                          name, p2i(buf), index, sz);
 }
 #endif // PRODUCT
--- a/hotspot/src/share/vm/gc/parallel/mutableNUMASpace.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/parallel/mutableNUMASpace.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -85,7 +85,7 @@
         while (words_left_to_fill > 0) {
           size_t words_to_fill = MIN2(words_left_to_fill, CollectedHeap::filler_array_max_size());
           assert(words_to_fill >= CollectedHeap::min_fill_size(),
-            err_msg("Remaining size ("SIZE_FORMAT ") is too small to fill (based on " SIZE_FORMAT " and " SIZE_FORMAT ")",
+            err_msg("Remaining size (" SIZE_FORMAT ") is too small to fill (based on " SIZE_FORMAT " and " SIZE_FORMAT ")",
             words_to_fill, words_left_to_fill, CollectedHeap::filler_array_max_size()));
           CollectedHeap::fill_with_object((HeapWord*)cur_top, words_to_fill);
           if (!os::numa_has_static_binding()) {
--- a/hotspot/src/share/vm/gc/parallel/psAdaptiveSizePolicy.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/parallel/psAdaptiveSizePolicy.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -130,8 +130,7 @@
   // Update the pause time.
   _major_timer.stop();
 
-  if (!GCCause::is_user_requested_gc(gc_cause) ||
-      UseAdaptiveSizePolicyWithSystemGC) {
+  if (should_update_promo_stats(gc_cause)) {
     double major_pause_in_seconds = _major_timer.seconds();
     double major_pause_in_ms = major_pause_in_seconds * MILLIUNITS;
 
--- a/hotspot/src/share/vm/gc/parallel/psMarkSweep.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/parallel/psMarkSweep.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -272,8 +272,7 @@
       // Don't check if the size_policy is ready here.  Let
       // the size_policy check that internally.
       if (UseAdaptiveGenerationSizePolicyAtMajorCollection &&
-          (!GCCause::is_user_requested_gc(gc_cause) ||
-            UseAdaptiveSizePolicyWithSystemGC)) {
+          AdaptiveSizePolicy::should_update_promo_stats(gc_cause)) {
         // Swap the survivor spaces if from_space is empty. The
         // resize_young_gen() called below is normally used after
         // a successful young GC and swapping of survivor spaces;
--- a/hotspot/src/share/vm/gc/parallel/psOldGen.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/parallel/psOldGen.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -65,9 +65,9 @@
     // Explictly capture current covered_region in a local
     MemRegion covered_region = this->start_array()->covered_region();
     assert(covered_region.contains(new_memregion),
-           err_msg("new region is not in covered_region [ "PTR_FORMAT", "PTR_FORMAT" ], "
-                   "new region [ "PTR_FORMAT", "PTR_FORMAT" ], "
-                   "object space [ "PTR_FORMAT", "PTR_FORMAT" ]",
+           err_msg("new region is not in covered_region [ " PTR_FORMAT ", " PTR_FORMAT " ], "
+                   "new region [ " PTR_FORMAT ", " PTR_FORMAT " ], "
+                   "object space [ " PTR_FORMAT ", " PTR_FORMAT " ]",
                    p2i(covered_region.start()),
                    p2i(covered_region.end()),
                    p2i(new_memregion.start()),
--- a/hotspot/src/share/vm/gc/parallel/psParallelCompact.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/parallel/psParallelCompact.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -2089,8 +2089,7 @@
       // Don't check if the size_policy is ready here.  Let
       // the size_policy check that internally.
       if (UseAdaptiveGenerationSizePolicyAtMajorCollection &&
-          (!GCCause::is_user_requested_gc(gc_cause) ||
-            UseAdaptiveSizePolicyWithSystemGC)) {
+          AdaptiveSizePolicy::should_update_promo_stats(gc_cause)) {
         // Swap the survivor spaces if from_space is empty. The
         // resize_young_gen() called below is normally used after
         // a successful young GC and swapping of survivor spaces;
--- a/hotspot/src/share/vm/gc/parallel/psScavenge.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/parallel/psScavenge.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -290,8 +290,7 @@
 
   AdaptiveSizePolicyOutput(size_policy, heap->total_collections());
 
-  if (!GCCause::is_user_requested_gc(gc_cause) ||
-       UseAdaptiveSizePolicyWithSystemGC) {
+  if (AdaptiveSizePolicy::should_update_eden_stats(gc_cause)) {
     // Gather the feedback data for eden occupancy.
     young_gen->eden_space()->accumulate_statistics();
   }
@@ -559,9 +558,7 @@
         // Don't check if the size_policy is ready at this
         // level.  Let the size_policy check that internally.
         if (UseAdaptiveGenerationSizePolicyAtMinorCollection &&
-            ((gc_cause != GCCause::_java_lang_system_gc) ||
-              UseAdaptiveSizePolicyWithSystemGC)) {
-
+            (AdaptiveSizePolicy::should_update_eden_stats(gc_cause))) {
           // Calculate optimal free space amounts
           assert(young_gen->max_size() >
             young_gen->from_space()->capacity_in_bytes() +
--- a/hotspot/src/share/vm/gc/serial/tenuredGeneration.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/serial/tenuredGeneration.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -168,8 +168,8 @@
   bool   res = (available >= av_promo) || (available >= max_promotion_in_bytes);
   if (PrintGC && Verbose) {
     gclog_or_tty->print_cr(
-      "Tenured: promo attempt is%s safe: available("SIZE_FORMAT") %s av_promo("SIZE_FORMAT"),"
-      "max_promo("SIZE_FORMAT")",
+      "Tenured: promo attempt is%s safe: available(" SIZE_FORMAT ") %s av_promo(" SIZE_FORMAT "),"
+      "max_promo(" SIZE_FORMAT ")",
       res? "":" not", available, res? ">=":"<",
       av_promo, max_promotion_in_bytes);
   }
--- a/hotspot/src/share/vm/gc/shared/adaptiveSizePolicy.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/shared/adaptiveSizePolicy.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -487,6 +487,18 @@
                                GCCause::Cause gc_cause,
                                CollectorPolicy* collector_policy);
 
+  static bool should_update_promo_stats(GCCause::Cause cause) {
+    return ((GCCause::is_user_requested_gc(cause)  &&
+               UseAdaptiveSizePolicyWithSystemGC) ||
+            GCCause::is_tenured_allocation_failure_gc(cause));
+  }
+
+  static bool should_update_eden_stats(GCCause::Cause cause) {
+    return ((GCCause::is_user_requested_gc(cause)  &&
+               UseAdaptiveSizePolicyWithSystemGC) ||
+            GCCause::is_allocation_failure_gc(cause));
+  }
+
   // Printing support
   virtual bool print_adaptive_size_policy_on(outputStream* st) const;
   bool print_adaptive_size_policy_on(outputStream* st,
--- a/hotspot/src/share/vm/gc/shared/barrierSet.inline.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/shared/barrierSet.inline.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -69,7 +69,7 @@
   assert(UseCompressedOops || (aligned_start == start && aligned_end == end),
          "Expected heap word alignment of start and end");
 #if 0
-  warning("Post:\t" INTPTR_FORMAT "[" SIZE_FORMAT "] : [" INTPTR_FORMAT","INTPTR_FORMAT")\t",
+  warning("Post:\t" INTPTR_FORMAT "[" SIZE_FORMAT "] : [" INTPTR_FORMAT "," INTPTR_FORMAT ")\t",
                    start,            count,              aligned_start,   aligned_end);
 #endif
   write_ref_array_work(MemRegion(aligned_start, aligned_end));
--- a/hotspot/src/share/vm/gc/shared/blockOffsetTable.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/shared/blockOffsetTable.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -560,7 +560,7 @@
     q = n;
     n += _sp->block_size(n);
     assert(n > q,
-           err_msg("Looping at n = " PTR_FORMAT " with last = " PTR_FORMAT","
+           err_msg("Looping at n = " PTR_FORMAT " with last = " PTR_FORMAT ","
                    " while querying blk_start(" PTR_FORMAT ")"
                    " on _sp = [" PTR_FORMAT "," PTR_FORMAT ")",
                    p2i(n), p2i(last), p2i(addr), p2i(_sp->bottom()), p2i(_sp->end())));
--- a/hotspot/src/share/vm/gc/shared/cardTableModRefBS.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/shared/cardTableModRefBS.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -600,7 +600,7 @@
                       (val_equals) ? "" : "not ", val);
         failures = true;
       }
-      tty->print_cr("==   card "PTR_FORMAT" ["PTR_FORMAT","PTR_FORMAT"], "
+      tty->print_cr("==   card " PTR_FORMAT " [" PTR_FORMAT "," PTR_FORMAT "], "
                     "val: %d", p2i(curr), p2i(addr_for(curr)),
                     p2i((HeapWord*) (((size_t) addr_for(curr)) + card_size)),
                     (int) curr_val);
--- a/hotspot/src/share/vm/gc/shared/cardTableModRefBS.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/shared/cardTableModRefBS.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -158,8 +158,8 @@
   // Mapping from address to card marking array entry
   jbyte* byte_for(const void* p) const {
     assert(_whole_heap.contains(p),
-           err_msg("Attempt to access p = "PTR_FORMAT" out of bounds of "
-                   " card marking array's _whole_heap = ["PTR_FORMAT","PTR_FORMAT")",
+           err_msg("Attempt to access p = " PTR_FORMAT " out of bounds of "
+                   " card marking array's _whole_heap = [" PTR_FORMAT "," PTR_FORMAT ")",
                    p2i(p), p2i(_whole_heap.start()), p2i(_whole_heap.end())));
     jbyte* result = &byte_map_base[uintptr_t(p) >> card_shift];
     assert(result >= _byte_map && result < _byte_map + _byte_map_size,
@@ -399,8 +399,8 @@
     size_t delta = pointer_delta(p, byte_map_base, sizeof(jbyte));
     HeapWord* result = (HeapWord*) (delta << card_shift);
     assert(_whole_heap.contains(result),
-           err_msg("Returning result = "PTR_FORMAT" out of bounds of "
-                   " card marking array's _whole_heap = ["PTR_FORMAT","PTR_FORMAT")",
+           err_msg("Returning result = " PTR_FORMAT " out of bounds of "
+                   " card marking array's _whole_heap = [" PTR_FORMAT "," PTR_FORMAT ")",
                    p2i(result), p2i(_whole_heap.start()), p2i(_whole_heap.end())));
     return result;
   }
@@ -408,8 +408,8 @@
   // Mapping from address to card marking array index.
   size_t index_for(void* p) {
     assert(_whole_heap.contains(p),
-           err_msg("Attempt to access p = "PTR_FORMAT" out of bounds of "
-                   " card marking array's _whole_heap = ["PTR_FORMAT","PTR_FORMAT")",
+           err_msg("Attempt to access p = " PTR_FORMAT " out of bounds of "
+                   " card marking array's _whole_heap = [" PTR_FORMAT "," PTR_FORMAT ")",
                    p2i(p), p2i(_whole_heap.start()), p2i(_whole_heap.end())));
     return byte_for(p) - _byte_map;
   }
--- a/hotspot/src/share/vm/gc/shared/collectedHeap.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/shared/collectedHeap.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -488,19 +488,17 @@
   DEBUG_ONLY(fill_args_check(start, words);)
   HandleMark hm;  // Free handles before leaving.
 
-#ifdef _LP64
-  // A single array can fill ~8G, so multiple objects are needed only in 64-bit.
-  // First fill with arrays, ensuring that any remaining space is big enough to
-  // fill.  The remainder is filled with a single object.
+  // Multiple objects may be required depending on the filler array maximum size. Fill
+  // the range up to that with objects that are filler_array_max_size sized. The
+  // remainder is filled with a single object.
   const size_t min = min_fill_size();
   const size_t max = filler_array_max_size();
   while (words > max) {
-    const size_t cur = words - max >= min ? max : max - min;
+    const size_t cur = (words - max) >= min ? max : max - min;
     fill_with_array(start, cur, zap);
     start += cur;
     words -= cur;
   }
-#endif
 
   fill_with_object_impl(start, words, zap);
 }
--- a/hotspot/src/share/vm/gc/shared/gcCause.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/shared/gcCause.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -92,6 +92,35 @@
             cause == GCCause::_heap_dump);
   }
 
+  // Causes for collection of the tenured gernation
+  inline static bool is_tenured_allocation_failure_gc(GCCause::Cause cause) {
+    assert(cause != GCCause::_old_generation_too_full_to_scavenge &&
+      cause != GCCause::_old_generation_expanded_on_last_scavenge,
+      err_msg("This GCCause may be correct but is not expected yet: %s",
+      to_string(cause)));
+    // _tenured_generation_full or _cms_generation_full for full tenured generations
+    // _adaptive_size_policy for a full collection after a young GC
+    // _allocation_failure is the generic cause a collection which could result
+    // in the collection of the tenured generation if there is not enough space
+    // in the tenured generation to support a young GC.
+    // _last_ditch_collection is a collection done to include SoftReferences.
+    return (cause == GCCause::_tenured_generation_full ||
+            cause == GCCause::_cms_generation_full ||
+            cause == GCCause::_adaptive_size_policy ||
+            cause == GCCause::_allocation_failure ||
+            cause == GCCause::_last_ditch_collection);
+  }
+
+  // Causes for collection of the young generation
+  inline static bool is_allocation_failure_gc(GCCause::Cause cause) {
+    // _allocation_failure is the generic cause a collection for allocation failure
+    // _adaptive_size_policy is for a collecton done before a full GC
+    // _last_ditch_collection is a collection done to include SoftReferences.
+    return (cause == GCCause::_allocation_failure ||
+            cause == GCCause::_adaptive_size_policy ||
+            cause == GCCause::_last_ditch_collection);
+  }
+
   // Return a string describing the GCCause.
   static const char* to_string(GCCause::Cause cause);
 };
--- a/hotspot/src/share/vm/gc/shared/gcTrace.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/shared/gcTrace.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -221,6 +221,12 @@
 }
 
 #if INCLUDE_ALL_GCS
+void G1MMUTracer::report_mmu(const GCId& gcId, double timeSlice, double gcTime, double maxTime) {
+  assert(!gcId.is_undefined(), "Undefined GC id");
+
+  send_g1_mmu_event(gcId, timeSlice, gcTime, maxTime);
+}
+
 void G1NewTracer::report_yc_type(G1YCType type) {
   assert_set_gc_id();
 
--- a/hotspot/src/share/vm/gc/shared/gcTrace.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/shared/gcTrace.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -239,6 +239,13 @@
 };
 
 #if INCLUDE_ALL_GCS
+class G1MMUTracer : public AllStatic {
+  static void send_g1_mmu_event(const GCId& gcId, double timeSlice, double gcTime, double maxTime);
+
+ public:
+  static void report_mmu(const GCId& gcId, double timeSlice, double gcTime, double maxTime);
+};
+
 class G1NewTracer : public YoungGCTracer {
   G1YoungGCInfo _g1_young_gc_info;
 
--- a/hotspot/src/share/vm/gc/shared/gcTraceSend.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/shared/gcTraceSend.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -199,6 +199,17 @@
   }
 }
 
+void G1MMUTracer::send_g1_mmu_event(const GCId& gcId, double timeSlice, double gcTime, double maxTime) {
+  EventGCG1MMU e;
+  if (e.should_commit()) {
+    e.set_gcId(gcId.id());
+    e.set_timeSlice(timeSlice);
+    e.set_gcTime(gcTime);
+    e.set_maxGcTime(maxTime);
+    e.commit();
+  }
+}
+
 void G1NewTracer::send_evacuation_info_event(EvacuationInfo* info) {
   EventEvacuationInfo e;
   if (e.should_commit()) {
--- a/hotspot/src/share/vm/gc/shared/generation.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/shared/generation.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -173,7 +173,7 @@
   bool   res = (available >= max_promotion_in_bytes);
   if (PrintGC && Verbose) {
     gclog_or_tty->print_cr(
-      "Generation: promo attempt is%s safe: available("SIZE_FORMAT") %s max_promo("SIZE_FORMAT")",
+      "Generation: promo attempt is%s safe: available(" SIZE_FORMAT ") %s max_promo(" SIZE_FORMAT ")",
       res? "":" not", available, res? ">=":"<",
       max_promotion_in_bytes);
   }
--- a/hotspot/src/share/vm/gc/shared/plab.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/shared/plab.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -45,7 +45,7 @@
   // ArrayOopDesc::header_size depends on command line initialization.
   AlignmentReserve = oopDesc::header_size() > MinObjAlignment ? align_object_size(arrayOopDesc::header_size(T_INT)) : 0;
   assert(min_size() > AlignmentReserve,
-         err_msg("Minimum PLAB size " SIZE_FORMAT" must be larger than alignment reserve " SIZE_FORMAT" "
+         err_msg("Minimum PLAB size " SIZE_FORMAT " must be larger than alignment reserve " SIZE_FORMAT " "
                  "to be able to contain objects", min_size(), AlignmentReserve));
 }
 
@@ -109,10 +109,15 @@
   }
 }
 
-// Compute desired plab size and latch result for later
+// Calculates plab size for current number of gc worker threads.
+size_t PLABStats::desired_plab_sz(uint no_of_gc_workers) {
+  return MAX2(min_size(), (size_t)align_object_size(_desired_net_plab_sz / no_of_gc_workers));
+}
+
+// Compute desired plab size for one gc worker thread and latch result for later
 // use. This should be called once at the end of parallel
 // scavenge; it clears the sensor accumulators.
-void PLABStats::adjust_desired_plab_sz(uint no_of_gc_workers) {
+void PLABStats::adjust_desired_plab_sz() {
   assert(ResizePLAB, "Not set");
 
   assert(is_object_aligned(max_size()) && min_size() <= max_size(),
@@ -121,10 +126,10 @@
   if (_allocated == 0) {
     assert(_unused == 0,
            err_msg("Inconsistency in PLAB stats: "
-                   "_allocated: "SIZE_FORMAT", "
-                   "_wasted: "SIZE_FORMAT", "
-                   "_unused: "SIZE_FORMAT", "
-                   "_undo_wasted: "SIZE_FORMAT,
+                   "_allocated: " SIZE_FORMAT ", "
+                   "_wasted: " SIZE_FORMAT ", "
+                   "_unused: " SIZE_FORMAT ", "
+                   "_undo_wasted: " SIZE_FORMAT,
                    _allocated, _wasted, _unused, _undo_wasted));
 
     _allocated = 1;
@@ -135,7 +140,8 @@
     target_refills = 1;
   }
   size_t used = _allocated - _wasted - _unused;
-  size_t recent_plab_sz = used / (target_refills * no_of_gc_workers);
+  // Assumed to have 1 gc worker thread
+  size_t recent_plab_sz = used / target_refills;
   // Take historical weighted average
   _filter.sample(recent_plab_sz);
   // Clip from above and below, and align to object boundary
@@ -144,9 +150,9 @@
   new_plab_sz = align_object_size(new_plab_sz);
   // Latch the result
   if (PrintPLAB) {
-    gclog_or_tty->print(" (plab_sz = " SIZE_FORMAT" desired_plab_sz = " SIZE_FORMAT") ", recent_plab_sz, new_plab_sz);
+    gclog_or_tty->print(" (plab_sz = " SIZE_FORMAT " desired_net_plab_sz = " SIZE_FORMAT ") ", recent_plab_sz, new_plab_sz);
   }
-  _desired_plab_sz = new_plab_sz;
+  _desired_net_plab_sz = new_plab_sz;
 
   reset();
 }
--- a/hotspot/src/share/vm/gc/shared/plab.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/shared/plab.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -150,13 +150,13 @@
 
 // PLAB book-keeping.
 class PLABStats VALUE_OBJ_CLASS_SPEC {
-  size_t _allocated;      // Total allocated
-  size_t _wasted;         // of which wasted (internal fragmentation)
-  size_t _undo_wasted;    // of which wasted on undo (is not used for calculation of PLAB size)
-  size_t _unused;         // Unused in last buffer
-  size_t _desired_plab_sz;// Output of filter (below), suitably trimmed and quantized
+  size_t _allocated;          // Total allocated
+  size_t _wasted;             // of which wasted (internal fragmentation)
+  size_t _undo_wasted;        // of which wasted on undo (is not used for calculation of PLAB size)
+  size_t _unused;             // Unused in last buffer
+  size_t _desired_net_plab_sz;// Output of filter (below), suitably trimmed and quantized
   AdaptiveWeightedAverage
-         _filter;         // Integrator with decay
+         _filter;             // Integrator with decay
 
   void reset() {
     _allocated   = 0;
@@ -165,12 +165,12 @@
     _unused      = 0;
   }
  public:
-  PLABStats(size_t desired_plab_sz_, unsigned wt) :
+  PLABStats(size_t desired_net_plab_sz_, unsigned wt) :
     _allocated(0),
     _wasted(0),
     _undo_wasted(0),
     _unused(0),
-    _desired_plab_sz(desired_plab_sz_),
+    _desired_net_plab_sz(desired_net_plab_sz_),
     _filter(wt)
   { }
 
@@ -182,13 +182,12 @@
     return PLAB::max_size();
   }
 
-  size_t desired_plab_sz() {
-    return _desired_plab_sz;
-  }
+  // Calculates plab size for current number of gc worker threads.
+  size_t desired_plab_sz(uint no_of_gc_workers);
 
-  // Updates the current desired PLAB size. Computes the new desired PLAB size,
+  // Updates the current desired PLAB size. Computes the new desired PLAB size with one gc worker thread,
   // updates _desired_plab_sz and clears sensor accumulators.
-  void adjust_desired_plab_sz(uint no_of_gc_workers);
+  void adjust_desired_plab_sz();
 
   void add_allocated(size_t v) {
     Atomic::add_ptr(v, &_allocated);
--- a/hotspot/src/share/vm/gc/shared/threadLocalAllocBuffer.inline.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/gc/shared/threadLocalAllocBuffer.inline.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -93,10 +93,10 @@
 
   if (PrintTLAB && Verbose) {
     Thread* thrd = myThread();
-    gclog_or_tty->print("TLAB: %s thread: "INTPTR_FORMAT" [id: %2d]"
-                        " obj: "SIZE_FORMAT
-                        " free: "SIZE_FORMAT
-                        " waste: "SIZE_FORMAT"\n",
+    gclog_or_tty->print("TLAB: %s thread: " INTPTR_FORMAT " [id: %2d]"
+                        " obj: " SIZE_FORMAT
+                        " free: " SIZE_FORMAT
+                        " waste: " SIZE_FORMAT "\n",
                         "slow", p2i(thrd), thrd->osthread()->thread_id(),
                         obj_size, free(), refill_waste_limit());
   }
--- a/hotspot/src/share/vm/interpreter/interpreter.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/interpreter/interpreter.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 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
@@ -134,8 +134,10 @@
   tty->print_cr("wasted space     = %6dK bytes", (int)_code->available_space()/1024);
   tty->cr();
   tty->print_cr("# of codelets    = %6d"      , _code->number_of_stubs());
-  tty->print_cr("avg codelet size = %6d bytes", _code->used_space() / _code->number_of_stubs());
-  tty->cr();
+  if (_code->number_of_stubs() != 0) {
+    tty->print_cr("avg codelet size = %6d bytes", _code->used_space() / _code->number_of_stubs());
+    tty->cr();
+  }
   _code->print();
   tty->print_cr("----------------------------------------------------------------------");
   tty->cr();
--- a/hotspot/src/share/vm/interpreter/interpreter.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/interpreter/interpreter.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -45,6 +45,7 @@
 
 class InterpreterCodelet: public Stub {
   friend class VMStructs;
+  friend class CodeCacheDumper; // possible extension [do not remove]
  private:
   int         _size;                             // the size in bytes
   const char* _description;                      // a description of the codelet, for debugging & printing
--- a/hotspot/src/share/vm/interpreter/interpreterRuntime.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/interpreter/interpreterRuntime.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -27,6 +27,7 @@
 #include "classfile/systemDictionary.hpp"
 #include "classfile/vmSymbols.hpp"
 #include "code/codeCache.hpp"
+#include "code/codeCacheExtensions.hpp"
 #include "compiler/compileBroker.hpp"
 #include "compiler/disassembler.hpp"
 #include "gc/shared/collectedHeap.hpp"
@@ -1178,6 +1179,7 @@
     ICache::invalidate_range(handler, insts_size);
     _handler = handler + insts_size;
   }
+  CodeCacheExtensions::handle_generated_handler(handler, buffer->name(), _handler);
   return handler;
 }
 
@@ -1186,7 +1188,7 @@
     // use slow signature handler if we can't do better
     int handler_index = -1;
     // check if we can use customized (fast) signature handler
-    if (UseFastSignatureHandlers && method->size_of_parameters() <= Fingerprinter::max_size_of_parameters) {
+    if (UseFastSignatureHandlers && CodeCacheExtensions::support_fast_signature_handlers() && method->size_of_parameters() <= Fingerprinter::max_size_of_parameters) {
       // use customized signature handler
       MutexLocker mu(SignatureHandlerLibrary_lock);
       // make sure data structure is initialized
@@ -1203,14 +1205,23 @@
           round_to((intptr_t)_buffer, CodeEntryAlignment) - (address)_buffer;
         CodeBuffer buffer((address)(_buffer + align_offset),
                           SignatureHandlerLibrary::buffer_size - align_offset);
+        if (!CodeCacheExtensions::support_dynamic_code()) {
+          // we need a name for the signature (for lookups or saving)
+          const int SYMBOL_SIZE = 50;
+          char *symbolName = NEW_RESOURCE_ARRAY(char, SYMBOL_SIZE);
+          // support for named signatures
+          jio_snprintf(symbolName, SYMBOL_SIZE,
+                       "native_" UINT64_FORMAT, fingerprint);
+          buffer.set_name(symbolName);
+        }
         InterpreterRuntime::SignatureHandlerGenerator(method, &buffer).generate(fingerprint);
         // copy into code heap
         address handler = set_handler(&buffer);
         if (handler == NULL) {
-          // use slow signature handler
+          // use slow signature handler (without memorizing it in the fingerprints)
         } else {
           // debugging suppport
-          if (PrintSignatureHandlers) {
+          if (PrintSignatureHandlers && (handler != Interpreter::slow_signature_handler())) {
             tty->cr();
             tty->print_cr("argument handler #%d for: %s %s (fingerprint = " UINT64_FORMAT ", %d bytes generated)",
                           _handlers->length(),
@@ -1218,7 +1229,10 @@
                           method->name_and_sig_as_C_string(),
                           fingerprint,
                           buffer.insts_size());
-            Disassembler::decode(handler, handler + buffer.insts_size());
+            if (buffer.insts_size() > 0) {
+              // buffer may be empty for pregenerated handlers
+              Disassembler::decode(handler, handler + buffer.insts_size());
+            }
 #ifndef PRODUCT
             address rh_begin = Interpreter::result_handler(method()->result_type());
             if (CodeCache::contains(rh_begin)) {
@@ -1277,6 +1291,37 @@
 #endif // ASSERT
 }
 
+void SignatureHandlerLibrary::add(uint64_t fingerprint, address handler) {
+  int handler_index = -1;
+  // use customized signature handler
+  MutexLocker mu(SignatureHandlerLibrary_lock);
+  // make sure data structure is initialized
+  initialize();
+  fingerprint = InterpreterRuntime::normalize_fast_native_fingerprint(fingerprint);
+  handler_index = _fingerprints->find(fingerprint);
+  // create handler if necessary
+  if (handler_index < 0) {
+    if (PrintSignatureHandlers && (handler != Interpreter::slow_signature_handler())) {
+      tty->cr();
+      tty->print_cr("argument handler #%d at "PTR_FORMAT" for fingerprint " UINT64_FORMAT,
+                    _handlers->length(),
+                    handler,
+                    fingerprint);
+    }
+    _fingerprints->append(fingerprint);
+    _handlers->append(handler);
+  } else {
+    if (PrintSignatureHandlers) {
+      tty->cr();
+      tty->print_cr("duplicate argument handler #%d for fingerprint " UINT64_FORMAT "(old: "PTR_FORMAT", new : "PTR_FORMAT")",
+                    _handlers->length(),
+                    fingerprint,
+                    _handlers->at(handler_index),
+                    handler);
+    }
+  }
+}
+
 
 BufferBlob*              SignatureHandlerLibrary::_handler_blob = NULL;
 address                  SignatureHandlerLibrary::_handler      = NULL;
--- a/hotspot/src/share/vm/interpreter/interpreterRuntime.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/interpreter/interpreterRuntime.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -219,6 +219,7 @@
 
  public:
   static void add(methodHandle method);
+  static void add(uint64_t fingerprint, address handler);
 };
 
 #endif // SHARE_VM_INTERPRETER_INTERPRETERRUNTIME_HPP
--- a/hotspot/src/share/vm/interpreter/rewriter.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/interpreter/rewriter.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -107,7 +107,7 @@
 // more complicated solution is required.  A special return bytecode
 // is used only by Object.<init> to signal the finalization
 // registration point.  Additionally local 0 must be preserved so it's
-// available to pass to the registration function.  For simplicty we
+// available to pass to the registration function.  For simplicity we
 // require that local 0 is never overwritten so it's available as an
 // argument for registration.
 
--- a/hotspot/src/share/vm/interpreter/templateInterpreter.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/interpreter/templateInterpreter.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 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
@@ -23,6 +23,7 @@
  */
 
 #include "precompiled.hpp"
+#include "code/codeCacheExtensions.hpp"
 #include "interpreter/interpreter.hpp"
 #include "interpreter/interpreterGenerator.hpp"
 #include "interpreter/interpreterRuntime.hpp"
@@ -49,10 +50,33 @@
     TraceTime timer("Interpreter generation", TraceStartupTime);
     int code_size = InterpreterCodeSize;
     NOT_PRODUCT(code_size *= 4;)  // debug uses extra interpreter code space
+#if INCLUDE_JVMTI
+    if (CodeCacheExtensions::saving_generated_interpreter()) {
+      // May requires several versions of the codelets.
+      // Final size will automatically be optimized.
+      code_size *= 2;
+    }
+#endif
     _code = new StubQueue(new InterpreterCodeletInterface, code_size, NULL,
                           "Interpreter");
     InterpreterGenerator g(_code);
-    if (PrintInterpreter) print();
+  }
+  if (PrintInterpreter) {
+    if (CodeCacheExtensions::saving_generated_interpreter() &&
+        CodeCacheExtensions::use_pregenerated_interpreter()) {
+      ResourceMark rm;
+      tty->print("Printing the newly generated interpreter first");
+      print();
+      tty->print("Printing the pregenerated interpreter next");
+    }
+  }
+
+  // Install the pregenerated interpreter code before printing it
+  CodeCacheExtensions::complete_step(CodeCacheExtensionsSteps::TemplateInterpreter);
+
+  if (PrintInterpreter) {
+    ResourceMark rm;
+    print();
   }
 
   // initialize dispatch table
@@ -214,194 +238,203 @@
 };
 
 void TemplateInterpreterGenerator::generate_all() {
-  AbstractInterpreterGenerator::generate_all();
+  // Loop, in case we need several variants of the interpreter entries
+  do {
+    if (!CodeCacheExtensions::skip_code_generation()) {
+      // bypass code generation when useless
+      AbstractInterpreterGenerator::generate_all();
 
-  { CodeletMark cm(_masm, "error exits");
-    _unimplemented_bytecode    = generate_error_exit("unimplemented bytecode");
-    _illegal_bytecode_sequence = generate_error_exit("illegal bytecode sequence - method not verified");
-  }
+      { CodeletMark cm(_masm, "error exits");
+        _unimplemented_bytecode    = generate_error_exit("unimplemented bytecode");
+        _illegal_bytecode_sequence = generate_error_exit("illegal bytecode sequence - method not verified");
+      }
 
 #ifndef PRODUCT
-  if (TraceBytecodes) {
-    CodeletMark cm(_masm, "bytecode tracing support");
-    Interpreter::_trace_code =
-      EntryPoint(
-        generate_trace_code(btos),
-        generate_trace_code(ctos),
-        generate_trace_code(stos),
-        generate_trace_code(atos),
-        generate_trace_code(itos),
-        generate_trace_code(ltos),
-        generate_trace_code(ftos),
-        generate_trace_code(dtos),
-        generate_trace_code(vtos)
-      );
-  }
+      if (TraceBytecodes) {
+        CodeletMark cm(_masm, "bytecode tracing support");
+        Interpreter::_trace_code =
+          EntryPoint(
+                     generate_trace_code(btos),
+                     generate_trace_code(ctos),
+                     generate_trace_code(stos),
+                     generate_trace_code(atos),
+                     generate_trace_code(itos),
+                     generate_trace_code(ltos),
+                     generate_trace_code(ftos),
+                     generate_trace_code(dtos),
+                     generate_trace_code(vtos)
+                     );
+      }
 #endif // !PRODUCT
 
-  { CodeletMark cm(_masm, "return entry points");
-    const int index_size = sizeof(u2);
-    for (int i = 0; i < Interpreter::number_of_return_entries; i++) {
-      Interpreter::_return_entry[i] =
-        EntryPoint(
-          generate_return_entry_for(itos, i, index_size),
-          generate_return_entry_for(itos, i, index_size),
-          generate_return_entry_for(itos, i, index_size),
-          generate_return_entry_for(atos, i, index_size),
-          generate_return_entry_for(itos, i, index_size),
-          generate_return_entry_for(ltos, i, index_size),
-          generate_return_entry_for(ftos, i, index_size),
-          generate_return_entry_for(dtos, i, index_size),
-          generate_return_entry_for(vtos, i, index_size)
-        );
-    }
-  }
+      { CodeletMark cm(_masm, "return entry points");
+        const int index_size = sizeof(u2);
+        for (int i = 0; i < Interpreter::number_of_return_entries; i++) {
+          Interpreter::_return_entry[i] =
+            EntryPoint(
+                       generate_return_entry_for(itos, i, index_size),
+                       generate_return_entry_for(itos, i, index_size),
+                       generate_return_entry_for(itos, i, index_size),
+                       generate_return_entry_for(atos, i, index_size),
+                       generate_return_entry_for(itos, i, index_size),
+                       generate_return_entry_for(ltos, i, index_size),
+                       generate_return_entry_for(ftos, i, index_size),
+                       generate_return_entry_for(dtos, i, index_size),
+                       generate_return_entry_for(vtos, i, index_size)
+                       );
+        }
+      }
 
-  { CodeletMark cm(_masm, "invoke return entry points");
-    const TosState states[] = {itos, itos, itos, itos, ltos, ftos, dtos, atos, vtos};
-    const int invoke_length = Bytecodes::length_for(Bytecodes::_invokestatic);
-    const int invokeinterface_length = Bytecodes::length_for(Bytecodes::_invokeinterface);
-    const int invokedynamic_length = Bytecodes::length_for(Bytecodes::_invokedynamic);
+      { CodeletMark cm(_masm, "invoke return entry points");
+        const TosState states[] = {itos, itos, itos, itos, ltos, ftos, dtos, atos, vtos};
+        const int invoke_length = Bytecodes::length_for(Bytecodes::_invokestatic);
+        const int invokeinterface_length = Bytecodes::length_for(Bytecodes::_invokeinterface);
+        const int invokedynamic_length = Bytecodes::length_for(Bytecodes::_invokedynamic);
 
-    for (int i = 0; i < Interpreter::number_of_return_addrs; i++) {
-      TosState state = states[i];
-      Interpreter::_invoke_return_entry[i] = generate_return_entry_for(state, invoke_length, sizeof(u2));
-      Interpreter::_invokeinterface_return_entry[i] = generate_return_entry_for(state, invokeinterface_length, sizeof(u2));
-      Interpreter::_invokedynamic_return_entry[i] = generate_return_entry_for(state, invokedynamic_length, sizeof(u4));
-    }
-  }
+        for (int i = 0; i < Interpreter::number_of_return_addrs; i++) {
+          TosState state = states[i];
+          Interpreter::_invoke_return_entry[i] = generate_return_entry_for(state, invoke_length, sizeof(u2));
+          Interpreter::_invokeinterface_return_entry[i] = generate_return_entry_for(state, invokeinterface_length, sizeof(u2));
+          Interpreter::_invokedynamic_return_entry[i] = generate_return_entry_for(state, invokedynamic_length, sizeof(u4));
+        }
+      }
 
-  { CodeletMark cm(_masm, "earlyret entry points");
-    Interpreter::_earlyret_entry =
-      EntryPoint(
-        generate_earlyret_entry_for(btos),
-        generate_earlyret_entry_for(ctos),
-        generate_earlyret_entry_for(stos),
-        generate_earlyret_entry_for(atos),
-        generate_earlyret_entry_for(itos),
-        generate_earlyret_entry_for(ltos),
-        generate_earlyret_entry_for(ftos),
-        generate_earlyret_entry_for(dtos),
-        generate_earlyret_entry_for(vtos)
-      );
-  }
+      { CodeletMark cm(_masm, "earlyret entry points");
+        Interpreter::_earlyret_entry =
+          EntryPoint(
+                     generate_earlyret_entry_for(btos),
+                     generate_earlyret_entry_for(ctos),
+                     generate_earlyret_entry_for(stos),
+                     generate_earlyret_entry_for(atos),
+                     generate_earlyret_entry_for(itos),
+                     generate_earlyret_entry_for(ltos),
+                     generate_earlyret_entry_for(ftos),
+                     generate_earlyret_entry_for(dtos),
+                     generate_earlyret_entry_for(vtos)
+                     );
+      }
 
-  { CodeletMark cm(_masm, "deoptimization entry points");
-    for (int i = 0; i < Interpreter::number_of_deopt_entries; i++) {
-      Interpreter::_deopt_entry[i] =
-        EntryPoint(
-          generate_deopt_entry_for(itos, i),
-          generate_deopt_entry_for(itos, i),
-          generate_deopt_entry_for(itos, i),
-          generate_deopt_entry_for(atos, i),
-          generate_deopt_entry_for(itos, i),
-          generate_deopt_entry_for(ltos, i),
-          generate_deopt_entry_for(ftos, i),
-          generate_deopt_entry_for(dtos, i),
-          generate_deopt_entry_for(vtos, i)
-        );
-    }
-  }
+      { CodeletMark cm(_masm, "deoptimization entry points");
+        for (int i = 0; i < Interpreter::number_of_deopt_entries; i++) {
+          Interpreter::_deopt_entry[i] =
+            EntryPoint(
+                       generate_deopt_entry_for(itos, i),
+                       generate_deopt_entry_for(itos, i),
+                       generate_deopt_entry_for(itos, i),
+                       generate_deopt_entry_for(atos, i),
+                       generate_deopt_entry_for(itos, i),
+                       generate_deopt_entry_for(ltos, i),
+                       generate_deopt_entry_for(ftos, i),
+                       generate_deopt_entry_for(dtos, i),
+                       generate_deopt_entry_for(vtos, i)
+                       );
+        }
+      }
 
-  { CodeletMark cm(_masm, "result handlers for native calls");
-    // The various result converter stublets.
-    int is_generated[Interpreter::number_of_result_handlers];
-    memset(is_generated, 0, sizeof(is_generated));
+      { CodeletMark cm(_masm, "result handlers for native calls");
+        // The various result converter stublets.
+        int is_generated[Interpreter::number_of_result_handlers];
+        memset(is_generated, 0, sizeof(is_generated));
 
-    for (int i = 0; i < Interpreter::number_of_result_handlers; i++) {
-      BasicType type = types[i];
-      if (!is_generated[Interpreter::BasicType_as_index(type)]++) {
-        Interpreter::_native_abi_to_tosca[Interpreter::BasicType_as_index(type)] = generate_result_handler_for(type);
+        for (int i = 0; i < Interpreter::number_of_result_handlers; i++) {
+          BasicType type = types[i];
+          if (!is_generated[Interpreter::BasicType_as_index(type)]++) {
+            Interpreter::_native_abi_to_tosca[Interpreter::BasicType_as_index(type)] = generate_result_handler_for(type);
+          }
+        }
       }
-    }
-  }
 
-  { CodeletMark cm(_masm, "continuation entry points");
-    Interpreter::_continuation_entry =
-      EntryPoint(
-        generate_continuation_for(btos),
-        generate_continuation_for(ctos),
-        generate_continuation_for(stos),
-        generate_continuation_for(atos),
-        generate_continuation_for(itos),
-        generate_continuation_for(ltos),
-        generate_continuation_for(ftos),
-        generate_continuation_for(dtos),
-        generate_continuation_for(vtos)
-      );
-  }
+      { CodeletMark cm(_masm, "continuation entry points");
+        Interpreter::_continuation_entry =
+          EntryPoint(
+                     generate_continuation_for(btos),
+                     generate_continuation_for(ctos),
+                     generate_continuation_for(stos),
+                     generate_continuation_for(atos),
+                     generate_continuation_for(itos),
+                     generate_continuation_for(ltos),
+                     generate_continuation_for(ftos),
+                     generate_continuation_for(dtos),
+                     generate_continuation_for(vtos)
+                     );
+      }
 
-  { CodeletMark cm(_masm, "safepoint entry points");
-    Interpreter::_safept_entry =
-      EntryPoint(
-        generate_safept_entry_for(btos, CAST_FROM_FN_PTR(address, InterpreterRuntime::at_safepoint)),
-        generate_safept_entry_for(ctos, CAST_FROM_FN_PTR(address, InterpreterRuntime::at_safepoint)),
-        generate_safept_entry_for(stos, CAST_FROM_FN_PTR(address, InterpreterRuntime::at_safepoint)),
-        generate_safept_entry_for(atos, CAST_FROM_FN_PTR(address, InterpreterRuntime::at_safepoint)),
-        generate_safept_entry_for(itos, CAST_FROM_FN_PTR(address, InterpreterRuntime::at_safepoint)),
-        generate_safept_entry_for(ltos, CAST_FROM_FN_PTR(address, InterpreterRuntime::at_safepoint)),
-        generate_safept_entry_for(ftos, CAST_FROM_FN_PTR(address, InterpreterRuntime::at_safepoint)),
-        generate_safept_entry_for(dtos, CAST_FROM_FN_PTR(address, InterpreterRuntime::at_safepoint)),
-        generate_safept_entry_for(vtos, CAST_FROM_FN_PTR(address, InterpreterRuntime::at_safepoint))
-      );
-  }
+      { CodeletMark cm(_masm, "safepoint entry points");
+        Interpreter::_safept_entry =
+          EntryPoint(
+                     generate_safept_entry_for(btos, CAST_FROM_FN_PTR(address, InterpreterRuntime::at_safepoint)),
+                     generate_safept_entry_for(ctos, CAST_FROM_FN_PTR(address, InterpreterRuntime::at_safepoint)),
+                     generate_safept_entry_for(stos, CAST_FROM_FN_PTR(address, InterpreterRuntime::at_safepoint)),
+                     generate_safept_entry_for(atos, CAST_FROM_FN_PTR(address, InterpreterRuntime::at_safepoint)),
+                     generate_safept_entry_for(itos, CAST_FROM_FN_PTR(address, InterpreterRuntime::at_safepoint)),
+                     generate_safept_entry_for(ltos, CAST_FROM_FN_PTR(address, InterpreterRuntime::at_safepoint)),
+                     generate_safept_entry_for(ftos, CAST_FROM_FN_PTR(address, InterpreterRuntime::at_safepoint)),
+                     generate_safept_entry_for(dtos, CAST_FROM_FN_PTR(address, InterpreterRuntime::at_safepoint)),
+                     generate_safept_entry_for(vtos, CAST_FROM_FN_PTR(address, InterpreterRuntime::at_safepoint))
+                     );
+      }
 
-  { CodeletMark cm(_masm, "exception handling");
-    // (Note: this is not safepoint safe because thread may return to compiled code)
-    generate_throw_exception();
-  }
+      { CodeletMark cm(_masm, "exception handling");
+        // (Note: this is not safepoint safe because thread may return to compiled code)
+        generate_throw_exception();
+      }
 
-  { CodeletMark cm(_masm, "throw exception entrypoints");
-    Interpreter::_throw_ArrayIndexOutOfBoundsException_entry = generate_ArrayIndexOutOfBounds_handler("java/lang/ArrayIndexOutOfBoundsException");
-    Interpreter::_throw_ArrayStoreException_entry            = generate_klass_exception_handler("java/lang/ArrayStoreException"                 );
-    Interpreter::_throw_ArithmeticException_entry            = generate_exception_handler("java/lang/ArithmeticException"           , "/ by zero");
-    Interpreter::_throw_ClassCastException_entry             = generate_ClassCastException_handler();
-    Interpreter::_throw_NullPointerException_entry           = generate_exception_handler("java/lang/NullPointerException"          , NULL       );
-    Interpreter::_throw_StackOverflowError_entry             = generate_StackOverflowError_handler();
-  }
+      { CodeletMark cm(_masm, "throw exception entrypoints");
+        Interpreter::_throw_ArrayIndexOutOfBoundsException_entry = generate_ArrayIndexOutOfBounds_handler("java/lang/ArrayIndexOutOfBoundsException");
+        Interpreter::_throw_ArrayStoreException_entry            = generate_klass_exception_handler("java/lang/ArrayStoreException"                 );
+        Interpreter::_throw_ArithmeticException_entry            = generate_exception_handler("java/lang/ArithmeticException"           , "/ by zero");
+        Interpreter::_throw_ClassCastException_entry             = generate_ClassCastException_handler();
+        Interpreter::_throw_NullPointerException_entry           = generate_exception_handler("java/lang/NullPointerException"          , NULL       );
+        Interpreter::_throw_StackOverflowError_entry             = generate_StackOverflowError_handler();
+      }
 
 
 
-#define method_entry(kind)                                                                    \
-  { CodeletMark cm(_masm, "method entry point (kind = " #kind ")");                    \
-    Interpreter::_entry_table[Interpreter::kind] = ((InterpreterGenerator*)this)->generate_method_entry(Interpreter::kind);  \
-  }
+#define method_entry(kind)                                              \
+      { CodeletMark cm(_masm, "method entry point (kind = " #kind ")"); \
+        Interpreter::_entry_table[Interpreter::kind] = ((InterpreterGenerator*)this)->generate_method_entry(Interpreter::kind); \
+      }
 
-  // all non-native method kinds
-  method_entry(zerolocals)
-  method_entry(zerolocals_synchronized)
-  method_entry(empty)
-  method_entry(accessor)
-  method_entry(abstract)
-  method_entry(java_lang_math_sin  )
-  method_entry(java_lang_math_cos  )
-  method_entry(java_lang_math_tan  )
-  method_entry(java_lang_math_abs  )
-  method_entry(java_lang_math_sqrt )
-  method_entry(java_lang_math_log  )
-  method_entry(java_lang_math_log10)
-  method_entry(java_lang_math_exp  )
-  method_entry(java_lang_math_pow  )
-  method_entry(java_lang_ref_reference_get)
+      // all non-native method kinds
+      method_entry(zerolocals)
+        method_entry(zerolocals_synchronized)
+        method_entry(empty)
+        method_entry(accessor)
+        method_entry(abstract)
+        method_entry(java_lang_math_sin  )
+        method_entry(java_lang_math_cos  )
+        method_entry(java_lang_math_tan  )
+        method_entry(java_lang_math_abs  )
+        method_entry(java_lang_math_sqrt )
+        method_entry(java_lang_math_log  )
+        method_entry(java_lang_math_log10)
+        method_entry(java_lang_math_exp  )
+        method_entry(java_lang_math_pow  )
+        method_entry(java_lang_ref_reference_get)
 
-  if (UseCRC32Intrinsics) {
-    method_entry(java_util_zip_CRC32_update)
-    method_entry(java_util_zip_CRC32_updateBytes)
-    method_entry(java_util_zip_CRC32_updateByteBuffer)
-  }
+        if (UseCRC32Intrinsics) {
+          method_entry(java_util_zip_CRC32_update)
+            method_entry(java_util_zip_CRC32_updateBytes)
+            method_entry(java_util_zip_CRC32_updateByteBuffer)
+            }
 
-  initialize_method_handle_entries();
+      initialize_method_handle_entries();
 
-  // all native method kinds (must be one contiguous block)
-  Interpreter::_native_entry_begin = Interpreter::code()->code_end();
-  method_entry(native)
-  method_entry(native_synchronized)
-  Interpreter::_native_entry_end = Interpreter::code()->code_end();
+      // all native method kinds (must be one contiguous block)
+      Interpreter::_native_entry_begin = Interpreter::code()->code_end();
+      method_entry(native)
+        method_entry(native_synchronized)
+        Interpreter::_native_entry_end = Interpreter::code()->code_end();
 
 #undef method_entry
 
-  // Bytecodes
-  set_entry_points_for_all_bytes();
+      // Bytecodes
+      set_entry_points_for_all_bytes();
+    }
+  } while (CodeCacheExtensions::needs_other_interpreter_variant());
+
+  // installation of code in other places in the runtime
+  // (ExcutableCodeManager calls not needed to copy the entries)
   set_safepoints_for_all_bytes();
 }
 
@@ -445,6 +478,9 @@
 
 
 void TemplateInterpreterGenerator::set_entry_points(Bytecodes::Code code) {
+  if (CodeCacheExtensions::skip_template_interpreter_entries(code)) {
+    return;
+  }
   CodeletMark cm(_masm, Bytecodes::name(code), code);
   // initialize entry points
   assert(_unimplemented_bytecode    != NULL, "should have been generated before");
@@ -474,6 +510,7 @@
   EntryPoint entry(bep, cep, sep, aep, iep, lep, fep, dep, vep);
   Interpreter::_normal_table.set_entry(code, entry);
   Interpreter::_wentry_point[code] = wep;
+  CodeCacheExtensions::completed_template_interpreter_entries(_masm, code);
 }
 
 
--- a/hotspot/src/share/vm/interpreter/templateInterpreter.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/interpreter/templateInterpreter.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -87,6 +87,7 @@
   friend class TemplateInterpreterGenerator;
   friend class InterpreterGenerator;
   friend class TemplateTable;
+  friend class CodeCacheExtensions;
   // friend class Interpreter;
  public:
 
--- a/hotspot/src/share/vm/memory/allocation.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/memory/allocation.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -752,7 +752,7 @@
 julong  AllocStats::resource_bytes() { return Arena::_bytes_allocated - start_res_bytes; }
 void    AllocStats::print() {
   tty->print_cr(UINT64_FORMAT " mallocs (" UINT64_FORMAT "MB), "
-                UINT64_FORMAT" frees (" UINT64_FORMAT "MB), " UINT64_FORMAT "MB resrc",
+                UINT64_FORMAT " frees (" UINT64_FORMAT "MB), " UINT64_FORMAT "MB resrc",
                 num_mallocs(), alloc_bytes()/M, num_frees(), free_bytes()/M, resource_bytes()/M);
 }
 
--- a/hotspot/src/share/vm/memory/heap.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/memory/heap.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -28,6 +28,7 @@
 #include "code/codeBlob.hpp"
 #include "memory/allocation.hpp"
 #include "memory/virtualspace.hpp"
+#include "utilities/macros.hpp"
 
 // Blocks
 
@@ -80,6 +81,7 @@
 
 class CodeHeap : public CHeapObj<mtCode> {
   friend class VMStructs;
+  friend class PregeneratedCodeHeap;
  private:
   VirtualSpace _memory;                          // the memory holding the blocks
   VirtualSpace _segmap;                          // the memory holding the segment map
@@ -148,8 +150,8 @@
   char* high() const                             { return _memory.high(); }
   char* high_boundary() const                    { return _memory.high_boundary(); }
 
-  bool  contains(const void* p) const            { return low_boundary() <= p && p < high(); }
-  void* find_start(void* p)     const;           // returns the block containing p or NULL
+  virtual bool  contains(const void* p) const    { return low_boundary() <= p && p < high(); }
+  virtual void* find_start(void* p)     const;   // returns the block containing p or NULL
   size_t alignment_unit()       const;           // alignment of any block
   size_t alignment_offset()     const;           // offset of first byte of any block, within the enclosing alignment unit
   static size_t header_size();                   // returns the header size for each heap block
@@ -158,9 +160,9 @@
   int    freelist_length()       const           { return _freelist_length; } // number of elements in the freelist
 
   // returns the first block or NULL
-  void* first() const       { return next_used(first_block()); }
+  virtual void* first() const                    { return next_used(first_block()); }
   // returns the next block given a block p or NULL
-  void* next(void* p) const { return next_used(next_block(block_start(p))); }
+  virtual void* next(void* p) const              { return next_used(next_block(block_start(p))); }
 
   // Statistics
   size_t capacity() const;
--- a/hotspot/src/share/vm/memory/universe.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/memory/universe.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -805,7 +805,7 @@
 ReservedSpace Universe::reserve_heap(size_t heap_size, size_t alignment) {
 
   assert(alignment <= Arguments::conservative_max_heap_alignment(),
-      err_msg("actual alignment "SIZE_FORMAT" must be within maximum heap alignment "SIZE_FORMAT,
+      err_msg("actual alignment " SIZE_FORMAT " must be within maximum heap alignment " SIZE_FORMAT,
           alignment, Arguments::conservative_max_heap_alignment()));
 
   size_t total_reserved = align_size_up(heap_size, alignment);
--- a/hotspot/src/share/vm/memory/virtualspace.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/memory/virtualspace.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -23,6 +23,7 @@
  */
 
 #include "precompiled.hpp"
+#include "code/codeCacheExtensions.hpp"
 #include "memory/virtualspace.hpp"
 #include "oops/markOop.hpp"
 #include "oops/oop.inline.hpp"
@@ -603,7 +604,7 @@
 ReservedCodeSpace::ReservedCodeSpace(size_t r_size,
                                      size_t rs_align,
                                      bool large) :
-  ReservedSpace(r_size, rs_align, large, /*executable*/ true) {
+  ReservedSpace(r_size, rs_align, large, /*executable*/ CodeCacheExtensions::support_dynamic_code()) {
   MemTracker::record_virtual_memory_type((address)base(), mtCode);
 }
 
--- a/hotspot/src/share/vm/oops/constantPool.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/oops/constantPool.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1467,7 +1467,7 @@
       }
       case JVM_CONSTANT_Long: {
         u8 val = Bytes::get_Java_u8(bytes);
-        printf("long         "INT64_FORMAT, (int64_t) *(jlong *) &val);
+        printf("long         " INT64_FORMAT, (int64_t) *(jlong *) &val);
         ent_size = 8;
         idx++; // Long takes two cpool slots
         break;
--- a/hotspot/src/share/vm/oops/cpCache.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/oops/cpCache.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -308,7 +308,7 @@
                    adapter->size_of_parameters());
 
   if (TraceInvokeDynamic) {
-    tty->print_cr("set_method_handle bc=%d appendix="PTR_FORMAT"%s method_type="PTR_FORMAT"%s method="PTR_FORMAT" ",
+    tty->print_cr("set_method_handle bc=%d appendix=" PTR_FORMAT "%s method_type=" PTR_FORMAT "%s method=" PTR_FORMAT " ",
                   invoke_code,
                   (void *)appendix(),    (has_appendix    ? "" : " (unused)"),
                   (void *)method_type(), (has_method_type ? "" : " (unused)"),
@@ -538,12 +538,12 @@
   // print separator
   if (index == 0) st->print_cr("                 -------------");
   // print entry
-  st->print("%3d  ("PTR_FORMAT")  ", index, (intptr_t)this);
+  st->print("%3d  (" PTR_FORMAT ")  ", index, (intptr_t)this);
   st->print_cr("[%02x|%02x|%5d]", bytecode_2(), bytecode_1(),
                constant_pool_index());
-  st->print_cr("                 [   "PTR_FORMAT"]", (intptr_t)_f1);
-  st->print_cr("                 [   "PTR_FORMAT"]", (intptr_t)_f2);
-  st->print_cr("                 [   "PTR_FORMAT"]", (intptr_t)_flags);
+  st->print_cr("                 [   " PTR_FORMAT "]", (intptr_t)_f1);
+  st->print_cr("                 [   " PTR_FORMAT "]", (intptr_t)_f2);
+  st->print_cr("                 [   " PTR_FORMAT "]", (intptr_t)_flags);
   st->print_cr("                 -------------");
 }
 
--- a/hotspot/src/share/vm/oops/markOop.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/oops/markOop.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -49,7 +49,7 @@
         st->print("monitor=NULL");
       else {
         BasicLock * bl = (BasicLock *) mon->owner();
-        st->print("monitor={count="INTPTR_FORMAT",waiters="INTPTR_FORMAT",recursions="INTPTR_FORMAT",owner="INTPTR_FORMAT"}",
+        st->print("monitor={count=" INTPTR_FORMAT ",waiters=" INTPTR_FORMAT ",recursions=" INTPTR_FORMAT ",owner=" INTPTR_FORMAT "}",
                 mon->count(), mon->waiters(), mon->recursions(), p2i(bl));
       }
     } else {
--- a/hotspot/src/share/vm/oops/method.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/oops/method.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -2019,9 +2019,9 @@
   assert(is_method(), "must be method");
   st->print_cr("%s", internal_name());
   // get the effect of PrintOopAddress, always, for methods:
-  st->print_cr(" - this oop:          "INTPTR_FORMAT, (intptr_t)this);
+  st->print_cr(" - this oop:          " INTPTR_FORMAT, (intptr_t)this);
   st->print   (" - method holder:     "); method_holder()->print_value_on(st); st->cr();
-  st->print   (" - constants:         "INTPTR_FORMAT" ", (address)constants());
+  st->print   (" - constants:         " INTPTR_FORMAT " ", (address)constants());
   constants()->print_value_on(st); st->cr();
   st->print   (" - access:            0x%x  ", access_flags().as_int()); access_flags().print_on(st); st->cr();
   st->print   (" - name:              ");    name()->print_value_on(st); st->cr();
--- a/hotspot/src/share/vm/oops/method.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/oops/method.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -82,7 +82,8 @@
     _dont_inline          = 1 << 3,
     _hidden               = 1 << 4,
     _has_injected_profile = 1 << 5,
-    _running_emcp         = 1 << 6
+    _running_emcp         = 1 << 6,
+    _intrinsic_candidate  = 1 << 7
   };
   u1 _flags;
 
@@ -815,6 +816,13 @@
     _flags = x ? (_flags | _hidden) : (_flags & ~_hidden);
   }
 
+  bool intrinsic_candidate() {
+    return (_flags & _intrinsic_candidate) != 0;
+  }
+  void set_intrinsic_candidate(bool x) {
+    _flags = x ? (_flags | _intrinsic_candidate) : (_flags & ~_intrinsic_candidate);
+  }
+
   bool has_injected_profile() {
     return (_flags & _has_injected_profile) != 0;
   }
--- a/hotspot/src/share/vm/oops/objArrayKlass.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/oops/objArrayKlass.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -466,7 +466,7 @@
       if (i > max_objArray_print_length) {
         st->print("..."); break;
       }
-      st->print(" "INTPTR_FORMAT, (intptr_t)(void*)objArrayOop(obj)->obj_at(i));
+      st->print(" " INTPTR_FORMAT, (intptr_t)(void*)objArrayOop(obj)->obj_at(i));
     }
     st->print(" }");
   }
--- a/hotspot/src/share/vm/oops/oop.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/oops/oop.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -47,7 +47,7 @@
 
 void oopDesc::print_address_on(outputStream* st) const {
   if (PrintOopAddress) {
-    st->print("{"INTPTR_FORMAT"}", this);
+    st->print("{" INTPTR_FORMAT "}", this);
   }
 }
 
--- a/hotspot/src/share/vm/opto/c2_globals.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/opto/c2_globals.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -688,6 +688,12 @@
   product(bool, UseMulAddIntrinsic, false,                                  \
           "Enables intrinsification of BigInteger.mulAdd()")                \
                                                                             \
+  product(bool, UseMontgomeryMultiplyIntrinsic, false,                      \
+          "Enables intrinsification of BigInteger.montgomeryMultiply()")    \
+                                                                            \
+  product(bool, UseMontgomerySquareIntrinsic, false,                        \
+          "Enables intrinsification of BigInteger.montgomerySquare()")      \
+                                                                            \
   product(bool, UseTypeSpeculation, true,                                   \
           "Speculatively propagate types from profiles")                    \
                                                                             \
--- a/hotspot/src/share/vm/opto/callnode.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/opto/callnode.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -342,7 +342,7 @@
     const Type *t = n->bottom_type();
     switch (t->base()) {
     case Type::Int:
-      st->print(" %s%d]=#"INT32_FORMAT,msg,i,t->is_int()->get_con());
+      st->print(" %s%d]=#" INT32_FORMAT,msg,i,t->is_int()->get_con());
       break;
     case Type::AnyPtr:
       assert( t == TypePtr::NULL_PTR || n->in_dump(), "" );
@@ -371,7 +371,7 @@
       st->print(" %s%d]=#%fF",msg,i,t->is_float_constant()->_f);
       break;
     case Type::Long:
-      st->print(" %s%d]=#"INT64_FORMAT,msg,i,(int64_t)(t->is_long()->get_con()));
+      st->print(" %s%d]=#" INT64_FORMAT,msg,i,(int64_t)(t->is_long()->get_con()));
       break;
     case Type::Half:
     case Type::Top:
--- a/hotspot/src/share/vm/opto/escape.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/opto/escape.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -976,8 +976,10 @@
                   strcmp(call->as_CallLeaf()->_name, "sha512_implCompressMB") == 0 ||
                   strcmp(call->as_CallLeaf()->_name, "multiplyToLen") == 0 ||
                   strcmp(call->as_CallLeaf()->_name, "squareToLen") == 0 ||
-                  strcmp(call->as_CallLeaf()->_name, "mulAdd") == 0)
-                  ))) {
+                  strcmp(call->as_CallLeaf()->_name, "mulAdd") == 0 ||
+                  strcmp(call->as_CallLeaf()->_name, "montgomery_multiply") == 0 ||
+                  strcmp(call->as_CallLeaf()->_name, "montgomery_square") == 0)
+                 ))) {
             call->dump();
             fatal(err_msg_res("EA unexpected CallLeaf %s", call->as_CallLeaf()->_name));
           }
--- a/hotspot/src/share/vm/opto/generateOptoStub.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/opto/generateOptoStub.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1999, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1999, 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
@@ -118,19 +118,14 @@
   // The C routines gets the base of thread-local storage passed in as an
   // extra argument.  Not all calls need it, but its cheap to add here.
   for (uint pcnt = cnt; pcnt < parm_cnt; pcnt++, cnt++) {
-    // Convert ints to longs if required.
-    if (CCallingConventionRequiresIntsAsLongs && jdomain->field_at(pcnt)->isa_int()) {
-      fields[cnt++] = TypeLong::LONG;
-      fields[cnt]   = Type::HALF; // must add an additional half for a long
-    } else {
-      fields[cnt] = jdomain->field_at(pcnt);
-    }
+    fields[cnt] = jdomain->field_at(pcnt);
   }
 
   fields[cnt++] = TypeRawPtr::BOTTOM; // Thread-local storage
   // Also pass in the caller's PC, if asked for.
-  if( return_pc )
+  if (return_pc) {
     fields[cnt++] = TypeRawPtr::BOTTOM; // Return PC
+  }
 
   const TypeTuple* domain = TypeTuple::make(cnt,fields);
   // The C routine we are about to call cannot return an oop; it can block on
@@ -143,21 +138,22 @@
   const Type **rfields = TypeTuple::fields(jrange->cnt() - TypeFunc::Parms);
   // Fixup oop returns
   int retval_ptr = retval->isa_oop_ptr();
-  if( retval_ptr ) {
+  if (retval_ptr) {
     assert( pass_tls, "Oop must be returned thru TLS" );
     // Fancy-jumps return address; others return void
     rfields[TypeFunc::Parms] = is_fancy_jump ? TypeRawPtr::BOTTOM : Type::TOP;
 
-  } else if( retval->isa_int() ) { // Returning any integer subtype?
+  } else if (retval->isa_int()) { // Returning any integer subtype?
     // "Fatten" byte, char & short return types to 'int' to show that
     // the native C code can return values with junk high order bits.
     // We'll sign-extend it below later.
     rfields[TypeFunc::Parms] = TypeInt::INT; // It's "dirty" and needs sign-ext
 
-  } else if( jrange->cnt() >= TypeFunc::Parms+1 ) { // Else copy other types
+  } else if (jrange->cnt() >= TypeFunc::Parms+1) { // Else copy other types
     rfields[TypeFunc::Parms] = jrange->field_at(TypeFunc::Parms);
-    if( jrange->cnt() == TypeFunc::Parms+2 )
+    if (jrange->cnt() == TypeFunc::Parms+2) {
       rfields[TypeFunc::Parms+1] = jrange->field_at(TypeFunc::Parms+1);
+    }
   }
   const TypeTuple* range = TypeTuple::make(jrange->cnt(),rfields);
 
@@ -181,14 +177,7 @@
   // A little too aggressive on the parm copy; return address is not an input
   call->set_req(TypeFunc::ReturnAdr, top());
   for (; i < parm_cnt; i++) { // Regular input arguments
-    // Convert ints to longs if required.
-    if (CCallingConventionRequiresIntsAsLongs && jdomain->field_at(i)->isa_int()) {
-      Node* int_as_long = _gvn.transform(new ConvI2LNode(map()->in(i)));
-      call->init_req(cnt++, int_as_long); // long
-      call->init_req(cnt++, top());       // half
-    } else {
-      call->init_req(cnt++, map()->in(i));
-    }
+    call->init_req(cnt++, map()->in(i));
   }
 
   call->init_req( cnt++, thread );
--- a/hotspot/src/share/vm/opto/library_call.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/opto/library_call.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -297,6 +297,8 @@
   bool inline_multiplyToLen();
   bool inline_squareToLen();
   bool inline_mulAdd();
+  bool inline_montgomeryMultiply();
+  bool inline_montgomerySquare();
 
   bool inline_profileBoolean();
   bool inline_isCompileConstant();
@@ -508,6 +510,13 @@
     if (!UseMulAddIntrinsic) return NULL;
     break;
 
+  case vmIntrinsics::_montgomeryMultiply:
+     if (!UseMontgomeryMultiplyIntrinsic) return NULL;
+    break;
+  case vmIntrinsics::_montgomerySquare:
+     if (!UseMontgomerySquareIntrinsic) return NULL;
+    break;
+
   case vmIntrinsics::_cipherBlockChaining_encryptAESCrypt:
   case vmIntrinsics::_cipherBlockChaining_decryptAESCrypt:
     if (!UseAESIntrinsics) return NULL;
@@ -642,7 +651,8 @@
   const int bci    = kit.bci();
 
   // Try to inline the intrinsic.
-  if (kit.try_to_inline(_last_predicate)) {
+  if ((CheckIntrinsics ? callee->intrinsic_candidate() : true) &&
+      kit.try_to_inline(_last_predicate)) {
     if (C->print_intrinsics() || C->print_inlining()) {
       C->print_inlining(callee, jvms->depth() - 1, bci, is_virtual() ? "(intrinsic, virtual)" : "(intrinsic)");
     }
@@ -663,7 +673,13 @@
   if (C->print_intrinsics() || C->print_inlining()) {
     if (jvms->has_method()) {
       // Not a root compile.
-      const char* msg = is_virtual() ? "failed to inline (intrinsic, virtual)" : "failed to inline (intrinsic)";
+      const char* msg;
+      if (callee->intrinsic_candidate()) {
+        msg = is_virtual() ? "failed to inline (intrinsic, virtual)" : "failed to inline (intrinsic)";
+      } else {
+        msg = is_virtual() ? "failed to inline (intrinsic, virtual), method not annotated"
+                           : "failed to inline (intrinsic), method not annotated";
+      }
       C->print_inlining(callee, jvms->depth() - 1, bci, msg);
     } else {
       // Root compile
@@ -942,6 +958,11 @@
   case vmIntrinsics::_mulAdd:
     return inline_mulAdd();
 
+  case vmIntrinsics::_montgomeryMultiply:
+    return inline_montgomeryMultiply();
+  case vmIntrinsics::_montgomerySquare:
+    return inline_montgomerySquare();
+
   case vmIntrinsics::_ghash_processBlocks:
     return inline_ghash_processBlocks();
 
@@ -5244,7 +5265,7 @@
 
 //-------------inline_multiplyToLen-----------------------------------
 bool LibraryCallKit::inline_multiplyToLen() {
-  assert(UseMultiplyToLenIntrinsic, "not implementated on this platform");
+  assert(UseMultiplyToLenIntrinsic, "not implemented on this platform");
 
   address stubAddr = StubRoutines::multiplyToLen();
   if (stubAddr == NULL) {
@@ -5254,11 +5275,12 @@
 
   assert(callee()->signature()->size() == 5, "multiplyToLen has 5 parameters");
 
-  Node* x    = argument(1);
-  Node* xlen = argument(2);
-  Node* y    = argument(3);
-  Node* ylen = argument(4);
-  Node* z    = argument(5);
+  // no receiver because it is a static method
+  Node* x    = argument(0);
+  Node* xlen = argument(1);
+  Node* y    = argument(2);
+  Node* ylen = argument(3);
+  Node* z    = argument(4);
 
   const Type* x_type = x->Value(&_gvn);
   const Type* y_type = y->Value(&_gvn);
@@ -5437,6 +5459,121 @@
   return true;
 }
 
+//-------------inline_montgomeryMultiply-----------------------------------
+bool LibraryCallKit::inline_montgomeryMultiply() {
+  address stubAddr = StubRoutines::montgomeryMultiply();
+  if (stubAddr == NULL) {
+    return false; // Intrinsic's stub is not implemented on this platform
+  }
+
+  assert(UseMontgomeryMultiplyIntrinsic, "not implemented on this platform");
+  const char* stubName = "montgomery_square";
+
+  assert(callee()->signature()->size() == 7, "montgomeryMultiply has 7 parameters");
+
+  Node* a    = argument(0);
+  Node* b    = argument(1);
+  Node* n    = argument(2);
+  Node* len  = argument(3);
+  Node* inv  = argument(4);
+  Node* m    = argument(6);
+
+  const Type* a_type = a->Value(&_gvn);
+  const TypeAryPtr* top_a = a_type->isa_aryptr();
+  const Type* b_type = b->Value(&_gvn);
+  const TypeAryPtr* top_b = b_type->isa_aryptr();
+  const Type* n_type = a->Value(&_gvn);
+  const TypeAryPtr* top_n = n_type->isa_aryptr();
+  const Type* m_type = a->Value(&_gvn);
+  const TypeAryPtr* top_m = m_type->isa_aryptr();
+  if (top_a  == NULL || top_a->klass()  == NULL ||
+      top_b == NULL || top_b->klass()  == NULL ||
+      top_n == NULL || top_n->klass()  == NULL ||
+      top_m == NULL || top_m->klass()  == NULL) {
+    // failed array check
+    return false;
+  }
+
+  BasicType a_elem = a_type->isa_aryptr()->klass()->as_array_klass()->element_type()->basic_type();
+  BasicType b_elem = b_type->isa_aryptr()->klass()->as_array_klass()->element_type()->basic_type();
+  BasicType n_elem = n_type->isa_aryptr()->klass()->as_array_klass()->element_type()->basic_type();
+  BasicType m_elem = m_type->isa_aryptr()->klass()->as_array_klass()->element_type()->basic_type();
+  if (a_elem != T_INT || b_elem != T_INT || n_elem != T_INT || m_elem != T_INT) {
+    return false;
+  }
+
+  // Make the call
+  {
+    Node* a_start = array_element_address(a, intcon(0), a_elem);
+    Node* b_start = array_element_address(b, intcon(0), b_elem);
+    Node* n_start = array_element_address(n, intcon(0), n_elem);
+    Node* m_start = array_element_address(m, intcon(0), m_elem);
+
+    Node* call = make_runtime_call(RC_LEAF,
+                                   OptoRuntime::montgomeryMultiply_Type(),
+                                   stubAddr, stubName, TypePtr::BOTTOM,
+                                   a_start, b_start, n_start, len, inv, top(),
+                                   m_start);
+    set_result(m);
+  }
+
+  return true;
+}
+
+bool LibraryCallKit::inline_montgomerySquare() {
+  address stubAddr = StubRoutines::montgomerySquare();
+  if (stubAddr == NULL) {
+    return false; // Intrinsic's stub is not implemented on this platform
+  }
+
+  assert(UseMontgomerySquareIntrinsic, "not implemented on this platform");
+  const char* stubName = "montgomery_square";
+
+  assert(callee()->signature()->size() == 6, "montgomerySquare has 6 parameters");
+
+  Node* a    = argument(0);
+  Node* n    = argument(1);
+  Node* len  = argument(2);
+  Node* inv  = argument(3);
+  Node* m    = argument(5);
+
+  const Type* a_type = a->Value(&_gvn);
+  const TypeAryPtr* top_a = a_type->isa_aryptr();
+  const Type* n_type = a->Value(&_gvn);
+  const TypeAryPtr* top_n = n_type->isa_aryptr();
+  const Type* m_type = a->Value(&_gvn);
+  const TypeAryPtr* top_m = m_type->isa_aryptr();
+  if (top_a  == NULL || top_a->klass()  == NULL ||
+      top_n == NULL || top_n->klass()  == NULL ||
+      top_m == NULL || top_m->klass()  == NULL) {
+    // failed array check
+    return false;
+  }
+
+  BasicType a_elem = a_type->isa_aryptr()->klass()->as_array_klass()->element_type()->basic_type();
+  BasicType n_elem = n_type->isa_aryptr()->klass()->as_array_klass()->element_type()->basic_type();
+  BasicType m_elem = m_type->isa_aryptr()->klass()->as_array_klass()->element_type()->basic_type();
+  if (a_elem != T_INT || n_elem != T_INT || m_elem != T_INT) {
+    return false;
+  }
+
+  // Make the call
+  {
+    Node* a_start = array_element_address(a, intcon(0), a_elem);
+    Node* n_start = array_element_address(n, intcon(0), n_elem);
+    Node* m_start = array_element_address(m, intcon(0), m_elem);
+
+    Node* call = make_runtime_call(RC_LEAF,
+                                   OptoRuntime::montgomerySquare_Type(),
+                                   stubAddr, stubName, TypePtr::BOTTOM,
+                                   a_start, n_start, len, inv, top(),
+                                   m_start);
+    set_result(m);
+  }
+
+  return true;
+}
+
 
 /**
  * Calculate CRC32 for byte.
--- a/hotspot/src/share/vm/opto/loopTransform.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/opto/loopTransform.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -2941,13 +2941,6 @@
     _igvn.register_new_node_with_optimizer(store_value);
   }
 
-  if (CCallingConventionRequiresIntsAsLongs &&
-      // See StubRoutines::select_fill_function for types. FLOAT has been converted to INT.
-      (t == T_FLOAT || t == T_INT ||  is_subword_type(t))) {
-    store_value = new ConvI2LNode(store_value);
-    _igvn.register_new_node_with_optimizer(store_value);
-  }
-
   Node* mem_phi = store->in(MemNode::Memory);
   Node* result_ctrl;
   Node* result_mem;
@@ -2957,9 +2950,6 @@
   uint cnt = 0;
   call->init_req(TypeFunc::Parms + cnt++, from);
   call->init_req(TypeFunc::Parms + cnt++, store_value);
-  if (CCallingConventionRequiresIntsAsLongs) {
-    call->init_req(TypeFunc::Parms + cnt++, C->top());
-  }
 #ifdef _LP64
   len = new ConvI2LNode(len);
   _igvn.register_new_node_with_optimizer(len);
--- a/hotspot/src/share/vm/opto/regmask.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/opto/regmask.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -25,6 +25,8 @@
 #include "precompiled.hpp"
 #include "opto/ad.hpp"
 #include "opto/compile.hpp"
+#include "opto/matcher.hpp"
+#include "opto/node.hpp"
 #include "opto/regmask.hpp"
 
 #define RM_SIZE _RM_SIZE /* a constant private to the class RegMask */
--- a/hotspot/src/share/vm/opto/runtime.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/opto/runtime.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -779,18 +779,10 @@
 const TypeFunc* OptoRuntime::array_fill_Type() {
   const Type** fields;
   int argp = TypeFunc::Parms;
-  if (CCallingConventionRequiresIntsAsLongs) {
   // create input type (domain): pointer, int, size_t
-    fields = TypeTuple::fields(3 LP64_ONLY( + 2));
-    fields[argp++] = TypePtr::NOTNULL;
-    fields[argp++] = TypeLong::LONG;
-    fields[argp++] = Type::HALF;
-  } else {
-    // create input type (domain): pointer, int, size_t
-    fields = TypeTuple::fields(3 LP64_ONLY( + 1));
-    fields[argp++] = TypePtr::NOTNULL;
-    fields[argp++] = TypeInt::INT;
-  }
+  fields = TypeTuple::fields(3 LP64_ONLY( + 1));
+  fields[argp++] = TypePtr::NOTNULL;
+  fields[argp++] = TypeInt::INT;
   fields[argp++] = TypeX_X;               // size in whatevers (size_t)
   LP64_ONLY(fields[argp++] = Type::HALF); // other half of long length
   const TypeTuple *domain = TypeTuple::make(argp, fields);
@@ -1010,6 +1002,53 @@
   return TypeFunc::make(domain, range);
 }
 
+const TypeFunc* OptoRuntime::montgomeryMultiply_Type() {
+  // create input type (domain)
+  int num_args      = 7;
+  int argcnt = num_args;
+  const Type** fields = TypeTuple::fields(argcnt);
+  int argp = TypeFunc::Parms;
+  fields[argp++] = TypePtr::NOTNULL;    // a
+  fields[argp++] = TypePtr::NOTNULL;    // b
+  fields[argp++] = TypePtr::NOTNULL;    // n
+  fields[argp++] = TypeInt::INT;        // len
+  fields[argp++] = TypeLong::LONG;      // inv
+  fields[argp++] = Type::HALF;
+  fields[argp++] = TypePtr::NOTNULL;    // result
+  assert(argp == TypeFunc::Parms+argcnt, "correct decoding");
+  const TypeTuple* domain = TypeTuple::make(TypeFunc::Parms+argcnt, fields);
+
+  // result type needed
+  fields = TypeTuple::fields(1);
+  fields[TypeFunc::Parms+0] = TypePtr::NOTNULL;
+
+  const TypeTuple* range = TypeTuple::make(TypeFunc::Parms, fields);
+  return TypeFunc::make(domain, range);
+}
+
+const TypeFunc* OptoRuntime::montgomerySquare_Type() {
+  // create input type (domain)
+  int num_args      = 6;
+  int argcnt = num_args;
+  const Type** fields = TypeTuple::fields(argcnt);
+  int argp = TypeFunc::Parms;
+  fields[argp++] = TypePtr::NOTNULL;    // a
+  fields[argp++] = TypePtr::NOTNULL;    // n
+  fields[argp++] = TypeInt::INT;        // len
+  fields[argp++] = TypeLong::LONG;      // inv
+  fields[argp++] = Type::HALF;
+  fields[argp++] = TypePtr::NOTNULL;    // result
+  assert(argp == TypeFunc::Parms+argcnt, "correct decoding");
+  const TypeTuple* domain = TypeTuple::make(TypeFunc::Parms+argcnt, fields);
+
+  // result type needed
+  fields = TypeTuple::fields(1);
+  fields[TypeFunc::Parms+0] = TypePtr::NOTNULL;
+
+  const TypeTuple* range = TypeTuple::make(TypeFunc::Parms, fields);
+  return TypeFunc::make(domain, range);
+}
+
 // GHASH block processing
 const TypeFunc* OptoRuntime::ghash_processBlocks_Type() {
     int argcnt = 4;
--- a/hotspot/src/share/vm/opto/runtime.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/opto/runtime.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -311,6 +311,8 @@
   static const TypeFunc* digestBase_implCompressMB_Type();
 
   static const TypeFunc* multiplyToLen_Type();
+  static const TypeFunc* montgomeryMultiply_Type();
+  static const TypeFunc* montgomerySquare_Type();
 
   static const TypeFunc* squareToLen_Type();
 
--- a/hotspot/src/share/vm/precompiled/precompiled.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/precompiled/precompiled.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -57,12 +57,15 @@
 # include "classfile/classFileParser.hpp"
 # include "classfile/classFileStream.hpp"
 # include "classfile/classLoader.hpp"
+# include "classfile/imageDecompressor.hpp"
+# include "classfile/imageFile.hpp"
 # include "classfile/javaClasses.hpp"
 # include "classfile/symbolTable.hpp"
 # include "classfile/systemDictionary.hpp"
 # include "classfile/vmSymbols.hpp"
 # include "code/codeBlob.hpp"
 # include "code/codeCache.hpp"
+# include "code/codeCacheExtensions.hpp"
 # include "code/compressedStream.hpp"
 # include "code/debugInfo.hpp"
 # include "code/debugInfoRec.hpp"
@@ -229,6 +232,7 @@
 # include "utilities/constantTag.hpp"
 # include "utilities/copy.hpp"
 # include "utilities/debug.hpp"
+# include "utilities/endian.hpp"
 # include "utilities/exceptions.hpp"
 # include "utilities/globalDefinitions.hpp"
 # include "utilities/growableArray.hpp"
--- a/hotspot/src/share/vm/prims/jni.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/prims/jni.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -3848,6 +3848,7 @@
   unit_test_function_call
 
 // Forward declaration
+void test_semaphore();
 void TestOS_test();
 void TestReservedSpace_test();
 void TestReserveMemorySpecial_test();
@@ -3873,6 +3874,7 @@
 void execute_internal_vm_tests() {
   if (ExecuteInternalVMTests) {
     tty->print_cr("Running internal VM tests");
+    run_unit_test(test_semaphore());
     run_unit_test(TestOS_test());
     run_unit_test(TestReservedSpace_test());
     run_unit_test(TestReserveMemorySpecial_test());
--- a/hotspot/src/share/vm/prims/jvm.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/prims/jvm.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -24,6 +24,8 @@
 
 #include "precompiled.hpp"
 #include "classfile/classLoader.hpp"
+#include "classfile/imageDecompressor.hpp"
+#include "classfile/imageFile.hpp"
 #include "classfile/javaAssertions.hpp"
 #include "classfile/javaClasses.inline.hpp"
 #include "classfile/stringTable.hpp"
@@ -69,6 +71,7 @@
 #include "utilities/copy.hpp"
 #include "utilities/defaultStream.hpp"
 #include "utilities/dtrace.hpp"
+#include "utilities/endian.hpp"
 #include "utilities/events.hpp"
 #include "utilities/histogram.hpp"
 #include "utilities/macros.hpp"
@@ -3665,3 +3668,244 @@
   info->is_attachable = AttachListener::is_attach_supported();
 }
 JVM_END
+
+// jdk.internal.jimage /////////////////////////////////////////////////////////
+// WARNING: This API is experimental and temporary during JDK 9 development
+// cycle. It will not be supported in the eventual JDK 9 release.
+
+// Java entry to open an image file for sharing.
+// WARNING: This API is experimental and temporary during JDK 9 development
+// cycle. It will not be supported in the eventual JDK 9 release.
+JVM_ENTRY(jlong,
+JVM_ImageOpen(JNIEnv *env, const char *nativePath, jboolean big_endian)) {
+  JVMWrapper("JVM_ImageOpen");
+  // Open image file for reading.
+  ImageFileReader* reader = ImageFileReader::open(nativePath, big_endian != JNI_FALSE);
+  // Return image ID as a jlong.
+  return ImageFileReader::readerToID(reader);
+}
+JVM_END
+
+// Java entry for closing a shared image file.
+// WARNING: This API is experimental and temporary during JDK 9 development
+// cycle. It will not be supported in the eventual JDK 9 release.
+JVM_ENTRY(void,
+JVM_ImageClose(JNIEnv *env, jlong id)) {
+  JVMWrapper("JVM_ImageClose");
+  // Convert image ID to image reader structure.
+  ImageFileReader* reader = ImageFileReader::idToReader(id);
+  // If valid reader the close.
+  if (reader != NULL) {
+    ImageFileReader::close(reader);
+  }
+}
+JVM_END
+
+// Java entry for accessing the base address of the image index.
+// WARNING: This API is experimental and temporary during JDK 9 development
+// cycle. It will not be supported in the eventual JDK 9 release.
+JVM_ENTRY(jlong,
+JVM_ImageGetIndexAddress(JNIEnv *env, jlong id)) {
+  JVMWrapper("JVM_ImageGetIndexAddress");
+  // Convert image ID to image reader structure.
+  ImageFileReader* reader = ImageFileReader::idToReader(id);
+  // If valid reader return index base address (as jlong) else zero.
+  return  reader != NULL ? (jlong)reader->get_index_address() : 0L;
+}
+JVM_END
+
+// Java entry for accessing the base address of the image data.
+// WARNING: This API is experimental and temporary during JDK 9 development
+// cycle. It will not be supported in the eventual JDK 9 release.
+JVM_ENTRY(jlong,
+JVM_ImageGetDataAddress(JNIEnv *env, jlong id)) {
+  JVMWrapper("JVM_ImageGetDataAddress");
+  // Convert image ID to image reader structure.
+  ImageFileReader* reader = ImageFileReader::idToReader(id);
+  // If valid reader return data base address (as jlong) else zero.
+  return MemoryMapImage && reader != NULL ? (jlong)reader->get_data_address() : 0L;
+}
+JVM_END
+
+// Java entry for reading an uncompressed resource from the image.
+// WARNING: This API is experimental and temporary during JDK 9 development
+// cycle. It will not be supported in the eventual JDK 9 release.
+JVM_ENTRY(jboolean,
+JVM_ImageRead(JNIEnv *env, jlong id, jlong offset,
+              unsigned char* uncompressedAddress, jlong uncompressed_size)) {
+  JVMWrapper("JVM_ImageRead");
+  // Convert image ID to image reader structure.
+  ImageFileReader* reader = ImageFileReader::idToReader(id);\
+  // If not a valid reader the fail the read.
+  if (reader == NULL) return false;
+  // Get the file offset of resource data.
+  u8 file_offset = reader->get_index_size() + offset;
+  // Check validity of arguments.
+  if (offset < 0 ||
+      uncompressed_size < 0 ||
+      file_offset > reader->file_size() - uncompressed_size) {
+      return false;
+  }
+  // Read file content into buffer.
+  return (jboolean)reader->read_at((u1*)uncompressedAddress, uncompressed_size,
+                                   file_offset);
+}
+JVM_END
+
+// Java entry for reading a compressed resource from the image.
+// WARNING: This API is experimental and temporary during JDK 9 development
+// cycle. It will not be supported in the eventual JDK 9 release.
+JVM_ENTRY(jboolean,
+JVM_ImageReadCompressed(JNIEnv *env,
+                    jlong id, jlong offset,
+                    unsigned char* compressedAddress, jlong compressed_size,
+                    unsigned char* uncompressedAddress, jlong uncompressed_size)) {
+  JVMWrapper("JVM_ImageReadCompressed");
+  // Convert image ID to image reader structure.
+  ImageFileReader* reader = ImageFileReader::idToReader(id);
+  // If not a valid reader the fail the read.
+  if (reader == NULL) return false;
+  // Get the file offset of resource data.
+  u8 file_offset = reader->get_index_size() + offset;
+  // Check validity of arguments.
+  if (offset < 0 ||
+      compressed_size < 0 ||
+      uncompressed_size < 0 ||
+      file_offset > reader->file_size() - compressed_size) {
+      return false;
+  }
+
+  // Read file content into buffer.
+  bool is_read = reader->read_at(compressedAddress, compressed_size,
+                                 file_offset);
+  // If successfully read then decompress.
+  if (is_read) {
+    const ImageStrings strings = reader->get_strings();
+    ImageDecompressor::decompress_resource(compressedAddress, uncompressedAddress,
+    uncompressed_size, &strings, true);
+  }
+  return (jboolean)is_read;
+}
+JVM_END
+
+// Java entry for retrieving UTF-8 bytes from image string table.
+// WARNING: This API is experimental and temporary during JDK 9 development
+// cycle. It will not be supported in the eventual JDK 9 release.
+JVM_ENTRY(const char*, JVM_ImageGetStringBytes(JNIEnv *env, jlong id, jint offset)) {
+  JVMWrapper("JVM_ImageGetStringBytes");
+  // Convert image ID to image reader structure.
+  ImageFileReader* reader = ImageFileReader::idToReader(id);
+  // Fail if not valid reader.
+  if (reader == NULL) return NULL;
+  // Manage image string table.
+  ImageStrings strings = reader->get_strings();
+  // Retrieve string adrress from table.
+  const char* data = strings.get(offset);
+  return data;
+}
+JVM_END
+
+// Utility function to copy location information into a jlong array.
+// WARNING: This function is experimental and temporary during JDK 9 development
+// cycle. It will not be supported in the eventual JDK 9 release.
+static void image_expand_location(JNIEnv *env, jlong* rawAttributes, ImageLocation& location) {
+  // Copy attributes from location.
+  for (int kind = ImageLocation::ATTRIBUTE_END + 1;
+           kind < ImageLocation::ATTRIBUTE_COUNT;
+           kind++) {
+    rawAttributes[kind] = location.get_attribute(kind);
+  }
+}
+
+// Java entry for retrieving location attributes for attribute offset.
+// WARNING: This API is experimental and temporary during JDK 9 development
+// cycle. It will not be supported in the eventual JDK 9 release.
+JVM_ENTRY(jlong*, JVM_ImageGetAttributes(JNIEnv *env, jlong* rawAttributes, jlong id, jint offset)) {
+  JVMWrapper("JVM_ImageGetAttributes");
+  // Convert image ID to image reader structure.
+  ImageFileReader* reader = ImageFileReader::idToReader(id);
+  // Fail if not valid reader.
+  if (reader == NULL) return NULL;
+  // Retrieve first byte address of resource's location attribute stream.
+  u1* data = reader->get_location_offset_data(offset);
+  // Fail if not valid offset.
+  if (data == NULL) return NULL;
+  // Expand stream into array.
+  ImageLocation location(data);
+  image_expand_location(env, rawAttributes, location);
+  return rawAttributes;
+}
+JVM_END
+
+// Java entry for retrieving location attributes count for attribute offset.
+// WARNING: This API is experimental and temporary during JDK 9 development
+// cycle. It will not be supported in the eventual JDK 9 release.
+JVM_ENTRY(jsize, JVM_ImageGetAttributesCount(JNIEnv *env)) {
+  JVMWrapper("JVM_ImageGetAttributesCount");
+  return ImageLocation::ATTRIBUTE_COUNT;
+}
+JVM_END
+
+// Java entry for retrieving location attributes for named resource.
+// WARNING: This API is experimental and temporary during JDK 9 development
+// cycle. It will not be supported in the eventual JDK 9 release.
+JVM_ENTRY(jlong*,
+JVM_ImageFindAttributes(JNIEnv *env, jlong* rawAttributes, jbyte* rawBytes, jsize size, jlong id)) {
+  JVMWrapper("JVM_ImageFindAttributes");
+  // Mark for temporary buffers.
+  ResourceMark rm;
+  // Convert image ID to image reader structure.
+  ImageFileReader* reader = ImageFileReader::idToReader(id);
+  // Fail if not valid reader.
+  if (reader == NULL) return NULL;
+  // Convert byte array to a cstring.
+  char* path = NEW_RESOURCE_ARRAY(char, size + 1);
+  memcpy(path, rawBytes, size);
+  path[size] = '\0';
+  // Locate resource location data.
+  ImageLocation location;
+  bool found = reader->find_location(path, location);
+  // Resource not found.
+  if (!found) return NULL;
+  // Expand stream into array.
+  image_expand_location(env, rawAttributes, location);
+  return rawAttributes;
+}
+JVM_END
+
+// Java entry for retrieving all the attribute stream offsets from an image.
+// WARNING: This API is experimental and temporary during JDK 9 development
+// cycle. It will not be supported in the eventual JDK 9 release.
+JVM_ENTRY(jint*, JVM_ImageAttributeOffsets(JNIEnv *env, jint* rawOffsets, unsigned int length, jlong id)) {
+  JVMWrapper("JVM_ImageAttributeOffsets");
+  // Convert image ID to image reader structure.
+  ImageFileReader* reader = ImageFileReader::idToReader(id);
+  // Fail if not valid reader.
+  if (reader == NULL) return NULL;
+  // Determine endian for reader.
+  Endian* endian = reader->endian();
+  // Get base address of attribute stream offsets table.
+  u4* offsets_table = reader->offsets_table();
+  // Allocate int array result.
+  // Copy values to result (converting endian.)
+  for (u4 i = 0; i < length; i++) {
+    rawOffsets[i] = endian->get(offsets_table[i]);
+  }
+  return rawOffsets;
+}
+JVM_END
+
+// Java entry for retrieving all the attribute stream offsets length from an image.
+// WARNING: This API is experimental and temporary during JDK 9 development
+// cycle. It will not be supported in the eventual JDK 9 release.
+JVM_ENTRY(unsigned int, JVM_ImageAttributeOffsetsLength(JNIEnv *env, jlong id)) {
+  JVMWrapper("JVM_ImageAttributeOffsetsLength");
+  // Convert image ID to image reader structure.
+  ImageFileReader* reader = ImageFileReader::idToReader(id);
+  // Fail if not valid reader.
+  if (reader == NULL) return 0;
+  // Get perfect hash table length.
+  u4 length = reader->table_length();
+  return (jint) length;
+}
+JVM_END
--- a/hotspot/src/share/vm/prims/jvm.h	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/prims/jvm.h	Wed Jul 05 20:42:36 2017 +0200
@@ -571,6 +571,52 @@
 JNIEXPORT jboolean JNICALL
 JVM_SupportsCX8(void);
 
+/*
+ * jdk.internal.jimage
+ * WARNING: This API is experimental and temporary during JDK 9 development
+ * cycle. It will not be supported in the eventual JDK 9 release.
+ */
+
+JNIEXPORT jlong JNICALL
+JVM_ImageOpen(JNIEnv *env, const char *nativePath, jboolean big_endian);
+
+JNIEXPORT void JNICALL
+JVM_ImageClose(JNIEnv *env, jlong id);
+
+JNIEXPORT jlong JNICALL
+JVM_ImageGetIndexAddress(JNIEnv *env, jlong id);
+
+JNIEXPORT jlong JNICALL
+JVM_ImageGetDataAddress(JNIEnv *env,jlong id);
+
+JNIEXPORT jboolean JNICALL
+JVM_ImageRead(JNIEnv *env, jlong id, jlong offset,
+            unsigned char* uncompressedAddress, jlong uncompressed_size);
+
+
+JNIEXPORT jboolean JNICALL
+JVM_ImageReadCompressed(JNIEnv *env, jlong id, jlong offset,
+            unsigned char* compressedBuffer, jlong compressed_size,
+            unsigned char* uncompressedBuffer, jlong uncompressed_size);
+
+JNIEXPORT const char* JNICALL
+JVM_ImageGetStringBytes(JNIEnv *env, jlong id, jint offset);
+
+JNIEXPORT jlong* JNICALL
+JVM_ImageGetAttributes(JNIEnv *env, jlong* rawAttributes, jlong id, jint offset);
+
+JNIEXPORT jsize JNICALL
+JVM_ImageGetAttributesCount(JNIEnv *env);
+
+JNIEXPORT jlong* JNICALL
+JVM_ImageFindAttributes(JNIEnv *env, jlong* rawAttributes, jbyte* rawBytes, jsize size, jlong id);
+
+JNIEXPORT jint* JNICALL
+JVM_ImageAttributeOffsets(JNIEnv *env, jint* rawOffsets, unsigned int length, jlong id);
+
+JNIEXPORT unsigned int JNICALL
+JVM_ImageAttributeOffsetsLength(JNIEnv *env, jlong id);
+
 /*************************************************************************
  PART 2: Support for the Verifier and Class File Format Checker
  ************************************************************************/
--- a/hotspot/src/share/vm/prims/methodHandles.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/prims/methodHandles.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -26,6 +26,7 @@
 #include "classfile/javaClasses.inline.hpp"
 #include "classfile/stringTable.hpp"
 #include "code/codeCache.hpp"
+#include "code/codeCacheExtensions.hpp"
 #include "compiler/compileBroker.hpp"
 #include "interpreter/interpreter.hpp"
 #include "interpreter/oopMapCache.hpp"
@@ -100,6 +101,7 @@
     StubCodeMark mark(this, "MethodHandle::interpreter_entry", vmIntrinsics::name_at(iid));
     address entry = MethodHandles::generate_method_handle_interpreter_entry(_masm, iid);
     if (entry != NULL) {
+      CodeCacheExtensions::handle_generated_pc(entry, vmIntrinsics::name_at(iid));
       Interpreter::set_entry_for_kind(mk, entry);
     }
     // If the entry is not set, it will throw AbstractMethodError.
@@ -1389,41 +1391,41 @@
 #define LANG "Ljava/lang/"
 #define JLINV "Ljava/lang/invoke/"
 
-#define OBJ   LANG"Object;"
-#define CLS   LANG"Class;"
-#define STRG  LANG"String;"
-#define CS    JLINV"CallSite;"
-#define MT    JLINV"MethodType;"
-#define MH    JLINV"MethodHandle;"
-#define MEM   JLINV"MemberName;"
-#define CTX   JLINV"MethodHandleNatives$CallSiteContext;"
+#define OBJ   LANG "Object;"
+#define CLS   LANG "Class;"
+#define STRG  LANG "String;"
+#define CS    JLINV "CallSite;"
+#define MT    JLINV "MethodType;"
+#define MH    JLINV "MethodHandle;"
+#define MEM   JLINV "MemberName;"
+#define CTX   JLINV "MethodHandleNatives$CallSiteContext;"
 
 #define CC (char*)  /*cast a literal from (const char*)*/
 #define FN_PTR(f) CAST_FROM_FN_PTR(void*, &f)
 
 // These are the native methods on java.lang.invoke.MethodHandleNatives.
 static JNINativeMethod MHN_methods[] = {
-  {CC"init",                      CC"("MEM""OBJ")V",                     FN_PTR(MHN_init_Mem)},
-  {CC"expand",                    CC"("MEM")V",                          FN_PTR(MHN_expand_Mem)},
-  {CC"resolve",                   CC"("MEM""CLS")"MEM,                   FN_PTR(MHN_resolve_Mem)},
+  {CC "init",                      CC "(" MEM "" OBJ ")V",                   FN_PTR(MHN_init_Mem)},
+  {CC "expand",                    CC "(" MEM ")V",                          FN_PTR(MHN_expand_Mem)},
+  {CC "resolve",                   CC "(" MEM "" CLS ")" MEM,                FN_PTR(MHN_resolve_Mem)},
   //  static native int getNamedCon(int which, Object[] name)
-  {CC"getNamedCon",               CC"(I["OBJ")I",                        FN_PTR(MHN_getNamedCon)},
+  {CC "getNamedCon",               CC "(I[" OBJ ")I",                        FN_PTR(MHN_getNamedCon)},
   //  static native int getMembers(Class<?> defc, String matchName, String matchSig,
   //          int matchFlags, Class<?> caller, int skip, MemberName[] results);
-  {CC"getMembers",                CC"("CLS""STRG""STRG"I"CLS"I["MEM")I", FN_PTR(MHN_getMembers)},
-  {CC"objectFieldOffset",         CC"("MEM")J",                          FN_PTR(MHN_objectFieldOffset)},
-  {CC"setCallSiteTargetNormal",   CC"("CS""MH")V",                       FN_PTR(MHN_setCallSiteTargetNormal)},
-  {CC"setCallSiteTargetVolatile", CC"("CS""MH")V",                       FN_PTR(MHN_setCallSiteTargetVolatile)},
-  {CC"clearCallSiteContext",      CC"("CTX")V",                          FN_PTR(MHN_clearCallSiteContext)},
-  {CC"staticFieldOffset",         CC"("MEM")J",                          FN_PTR(MHN_staticFieldOffset)},
-  {CC"staticFieldBase",           CC"("MEM")"OBJ,                        FN_PTR(MHN_staticFieldBase)},
-  {CC"getMemberVMInfo",           CC"("MEM")"OBJ,                        FN_PTR(MHN_getMemberVMInfo)}
+  {CC "getMembers",                CC "(" CLS "" STRG "" STRG "I" CLS "I[" MEM ")I", FN_PTR(MHN_getMembers)},
+  {CC "objectFieldOffset",         CC "(" MEM ")J",                          FN_PTR(MHN_objectFieldOffset)},
+  {CC "setCallSiteTargetNormal",   CC "(" CS "" MH ")V",                     FN_PTR(MHN_setCallSiteTargetNormal)},
+  {CC "setCallSiteTargetVolatile", CC "(" CS "" MH ")V",                     FN_PTR(MHN_setCallSiteTargetVolatile)},
+  {CC "clearCallSiteContext",      CC "(" CTX ")V",                          FN_PTR(MHN_clearCallSiteContext)},
+  {CC "staticFieldOffset",         CC "(" MEM ")J",                          FN_PTR(MHN_staticFieldOffset)},
+  {CC "staticFieldBase",           CC "(" MEM ")" OBJ,                        FN_PTR(MHN_staticFieldBase)},
+  {CC "getMemberVMInfo",           CC "(" MEM ")" OBJ,                        FN_PTR(MHN_getMemberVMInfo)}
 };
 
 static JNINativeMethod MH_methods[] = {
   // UnsupportedOperationException throwers
-  {CC"invoke",                    CC"(["OBJ")"OBJ,                       FN_PTR(MH_invoke_UOE)},
-  {CC"invokeExact",               CC"(["OBJ")"OBJ,                       FN_PTR(MH_invokeExact_UOE)}
+  {CC "invoke",                    CC "([" OBJ ")" OBJ,                       FN_PTR(MH_invoke_UOE)},
+  {CC "invokeExact",               CC "([" OBJ ")" OBJ,                       FN_PTR(MH_invokeExact_UOE)}
 };
 
 /**
--- a/hotspot/src/share/vm/prims/perf.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/prims/perf.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -295,17 +295,17 @@
 #define FN_PTR(f) CAST_FROM_FN_PTR(void*, &f)
 #define BB "Ljava/nio/ByteBuffer;"
 #define JLS "Ljava/lang/String;"
-#define CL_ARGS     CC"("JLS"IIJ)"BB
-#define CBA_ARGS    CC"("JLS"II[BI)"BB
+#define CL_ARGS     CC "(" JLS "IIJ)" BB
+#define CBA_ARGS    CC "(" JLS "II[BI)" BB
 
 static JNINativeMethod perfmethods[] = {
 
-  {CC"attach",              CC"("JLS"II)"BB,  FN_PTR(Perf_Attach)},
-  {CC"detach",              CC"("BB")V",      FN_PTR(Perf_Detach)},
-  {CC"createLong",          CL_ARGS,          FN_PTR(Perf_CreateLong)},
-  {CC"createByteArray",     CBA_ARGS,         FN_PTR(Perf_CreateByteArray)},
-  {CC"highResCounter",      CC"()J",          FN_PTR(Perf_HighResCounter)},
-  {CC"highResFrequency",    CC"()J",          FN_PTR(Perf_HighResFrequency)}
+  {CC "attach",              CC "(" JLS "II)" BB, FN_PTR(Perf_Attach)},
+  {CC "detach",              CC "(" BB ")V",      FN_PTR(Perf_Detach)},
+  {CC "createLong",          CL_ARGS,             FN_PTR(Perf_CreateLong)},
+  {CC "createByteArray",     CBA_ARGS,            FN_PTR(Perf_CreateByteArray)},
+  {CC "highResCounter",      CC "()J",            FN_PTR(Perf_HighResCounter)},
+  {CC "highResFrequency",    CC "()J",            FN_PTR(Perf_HighResFrequency)}
 };
 
 #undef CBA_ARGS
--- a/hotspot/src/share/vm/prims/unsafe.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/prims/unsafe.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1206,39 +1206,39 @@
 
 #define LANG "Ljava/lang/"
 
-#define OBJ LANG"Object;"
-#define CLS LANG"Class;"
-#define FLD LANG"reflect/Field;"
-#define THR LANG"Throwable;"
+#define OBJ LANG "Object;"
+#define CLS LANG "Class;"
+#define FLD LANG "reflect/Field;"
+#define THR LANG "Throwable;"
 
-#define DC_Args  LANG"String;[BII" LANG"ClassLoader;" "Ljava/security/ProtectionDomain;"
-#define DAC_Args CLS"[B["OBJ
+#define DC_Args  LANG "String;[BII" LANG "ClassLoader;" "Ljava/security/ProtectionDomain;"
+#define DAC_Args CLS "[B[" OBJ
 
 #define CC (char*)  /*cast a literal from (const char*)*/
 #define FN_PTR(f) CAST_FROM_FN_PTR(void*, &f)
 
 #define DECLARE_GETPUTOOP(Boolean, Z) \
-    {CC"get"#Boolean,      CC"("OBJ"J)"#Z,      FN_PTR(Unsafe_Get##Boolean)}, \
-    {CC"put"#Boolean,      CC"("OBJ"J"#Z")V",   FN_PTR(Unsafe_Set##Boolean)}, \
-    {CC"get"#Boolean"Volatile",      CC"("OBJ"J)"#Z,      FN_PTR(Unsafe_Get##Boolean##Volatile)}, \
-    {CC"put"#Boolean"Volatile",      CC"("OBJ"J"#Z")V",   FN_PTR(Unsafe_Set##Boolean##Volatile)}
+    {CC "get" #Boolean,      CC "(" OBJ "J)" #Z,       FN_PTR(Unsafe_Get##Boolean)}, \
+    {CC "put" #Boolean,      CC "(" OBJ "J" #Z ")V",   FN_PTR(Unsafe_Set##Boolean)}, \
+    {CC "get" #Boolean "Volatile",      CC "(" OBJ "J)" #Z,       FN_PTR(Unsafe_Get##Boolean##Volatile)}, \
+    {CC "put" #Boolean "Volatile",      CC "(" OBJ "J" #Z ")V",   FN_PTR(Unsafe_Set##Boolean##Volatile)}
 
 
 #define DECLARE_GETPUTNATIVE(Byte, B) \
-    {CC"get"#Byte,         CC"("ADR")"#B,       FN_PTR(Unsafe_GetNative##Byte)}, \
-    {CC"put"#Byte,         CC"("ADR#B")V",      FN_PTR(Unsafe_SetNative##Byte)}
+    {CC "get" #Byte,         CC "(" ADR ")" #B,       FN_PTR(Unsafe_GetNative##Byte)}, \
+    {CC "put" #Byte,         CC "(" ADR#B ")V",       FN_PTR(Unsafe_SetNative##Byte)}
 
 
 
 static JNINativeMethod methods[] = {
-    {CC"getObject",        CC"("OBJ"J)"OBJ"",   FN_PTR(Unsafe_GetObject)},
-    {CC"putObject",        CC"("OBJ"J"OBJ")V",  FN_PTR(Unsafe_SetObject)},
-    {CC"getObjectVolatile",CC"("OBJ"J)"OBJ"",   FN_PTR(Unsafe_GetObjectVolatile)},
-    {CC"putObjectVolatile",CC"("OBJ"J"OBJ")V",  FN_PTR(Unsafe_SetObjectVolatile)},
+    {CC "getObject",        CC "(" OBJ "J)" OBJ "",   FN_PTR(Unsafe_GetObject)},
+    {CC "putObject",        CC "(" OBJ "J" OBJ ")V",  FN_PTR(Unsafe_SetObject)},
+    {CC "getObjectVolatile",CC "(" OBJ "J)" OBJ "",   FN_PTR(Unsafe_GetObjectVolatile)},
+    {CC "putObjectVolatile",CC "(" OBJ "J" OBJ ")V",  FN_PTR(Unsafe_SetObjectVolatile)},
 
-    {CC"getUncompressedObject", CC"("ADR")"OBJ, FN_PTR(Unsafe_GetUncompressedObject)},
-    {CC"getJavaMirror",         CC"("ADR")"CLS, FN_PTR(Unsafe_GetJavaMirror)},
-    {CC"getKlassPointer",       CC"("OBJ")"ADR, FN_PTR(Unsafe_GetKlassPointer)},
+    {CC "getUncompressedObject", CC "(" ADR ")" OBJ,  FN_PTR(Unsafe_GetUncompressedObject)},
+    {CC "getJavaMirror",         CC "(" ADR ")" CLS,  FN_PTR(Unsafe_GetJavaMirror)},
+    {CC "getKlassPointer",       CC "(" OBJ ")" ADR,  FN_PTR(Unsafe_GetKlassPointer)},
 
     DECLARE_GETPUTOOP(Boolean, Z),
     DECLARE_GETPUTOOP(Byte, B),
@@ -1257,49 +1257,49 @@
     DECLARE_GETPUTNATIVE(Float, F),
     DECLARE_GETPUTNATIVE(Double, D),
 
-    {CC"getAddress",         CC"("ADR")"ADR,             FN_PTR(Unsafe_GetNativeAddress)},
-    {CC"putAddress",         CC"("ADR""ADR")V",          FN_PTR(Unsafe_SetNativeAddress)},
+    {CC "getAddress",         CC "(" ADR ")" ADR,        FN_PTR(Unsafe_GetNativeAddress)},
+    {CC "putAddress",         CC "(" ADR "" ADR ")V",    FN_PTR(Unsafe_SetNativeAddress)},
 
-    {CC"allocateMemory",     CC"(J)"ADR,                 FN_PTR(Unsafe_AllocateMemory)},
-    {CC"reallocateMemory",   CC"("ADR"J)"ADR,            FN_PTR(Unsafe_ReallocateMemory)},
-    {CC"freeMemory",         CC"("ADR")V",               FN_PTR(Unsafe_FreeMemory)},
+    {CC "allocateMemory",     CC "(J)" ADR,              FN_PTR(Unsafe_AllocateMemory)},
+    {CC "reallocateMemory",   CC "(" ADR "J)" ADR,       FN_PTR(Unsafe_ReallocateMemory)},
+    {CC "freeMemory",         CC "(" ADR ")V",           FN_PTR(Unsafe_FreeMemory)},
 
-    {CC"objectFieldOffset",  CC"("FLD")J",               FN_PTR(Unsafe_ObjectFieldOffset)},
-    {CC"staticFieldOffset",  CC"("FLD")J",               FN_PTR(Unsafe_StaticFieldOffset)},
-    {CC"staticFieldBase",    CC"("FLD")"OBJ,             FN_PTR(Unsafe_StaticFieldBaseFromField)},
-    {CC"ensureClassInitialized",CC"("CLS")V",            FN_PTR(Unsafe_EnsureClassInitialized)},
-    {CC"arrayBaseOffset",    CC"("CLS")I",               FN_PTR(Unsafe_ArrayBaseOffset)},
-    {CC"arrayIndexScale",    CC"("CLS")I",               FN_PTR(Unsafe_ArrayIndexScale)},
-    {CC"addressSize",        CC"()I",                    FN_PTR(Unsafe_AddressSize)},
-    {CC"pageSize",           CC"()I",                    FN_PTR(Unsafe_PageSize)},
+    {CC "objectFieldOffset",  CC "(" FLD ")J",           FN_PTR(Unsafe_ObjectFieldOffset)},
+    {CC "staticFieldOffset",  CC "(" FLD ")J",           FN_PTR(Unsafe_StaticFieldOffset)},
+    {CC "staticFieldBase",    CC "(" FLD ")" OBJ,        FN_PTR(Unsafe_StaticFieldBaseFromField)},
+    {CC "ensureClassInitialized",CC "(" CLS ")V",        FN_PTR(Unsafe_EnsureClassInitialized)},
+    {CC "arrayBaseOffset",    CC "(" CLS ")I",           FN_PTR(Unsafe_ArrayBaseOffset)},
+    {CC "arrayIndexScale",    CC "(" CLS ")I",           FN_PTR(Unsafe_ArrayIndexScale)},
+    {CC "addressSize",        CC "()I",                  FN_PTR(Unsafe_AddressSize)},
+    {CC "pageSize",           CC "()I",                  FN_PTR(Unsafe_PageSize)},
 
-    {CC"defineClass",        CC"("DC_Args")"CLS,         FN_PTR(Unsafe_DefineClass)},
-    {CC"allocateInstance",   CC"("CLS")"OBJ,             FN_PTR(Unsafe_AllocateInstance)},
-    {CC"throwException",     CC"("THR")V",               FN_PTR(Unsafe_ThrowException)},
-    {CC"compareAndSwapObject", CC"("OBJ"J"OBJ""OBJ")Z",  FN_PTR(Unsafe_CompareAndSwapObject)},
-    {CC"compareAndSwapInt",  CC"("OBJ"J""I""I"")Z",      FN_PTR(Unsafe_CompareAndSwapInt)},
-    {CC"compareAndSwapLong", CC"("OBJ"J""J""J"")Z",      FN_PTR(Unsafe_CompareAndSwapLong)},
-    {CC"putOrderedObject",   CC"("OBJ"J"OBJ")V",         FN_PTR(Unsafe_SetOrderedObject)},
-    {CC"putOrderedInt",      CC"("OBJ"JI)V",             FN_PTR(Unsafe_SetOrderedInt)},
-    {CC"putOrderedLong",     CC"("OBJ"JJ)V",             FN_PTR(Unsafe_SetOrderedLong)},
-    {CC"park",               CC"(ZJ)V",                  FN_PTR(Unsafe_Park)},
-    {CC"unpark",             CC"("OBJ")V",               FN_PTR(Unsafe_Unpark)},
+    {CC "defineClass",        CC "(" DC_Args ")" CLS,    FN_PTR(Unsafe_DefineClass)},
+    {CC "allocateInstance",   CC "(" CLS ")" OBJ,        FN_PTR(Unsafe_AllocateInstance)},
+    {CC "throwException",     CC "(" THR ")V",           FN_PTR(Unsafe_ThrowException)},
+    {CC "compareAndSwapObject", CC "(" OBJ "J" OBJ "" OBJ ")Z", FN_PTR(Unsafe_CompareAndSwapObject)},
+    {CC "compareAndSwapInt",  CC "(" OBJ "J""I""I"")Z",  FN_PTR(Unsafe_CompareAndSwapInt)},
+    {CC "compareAndSwapLong", CC "(" OBJ "J""J""J"")Z",  FN_PTR(Unsafe_CompareAndSwapLong)},
+    {CC "putOrderedObject",   CC "(" OBJ "J" OBJ ")V",   FN_PTR(Unsafe_SetOrderedObject)},
+    {CC "putOrderedInt",      CC "(" OBJ "JI)V",         FN_PTR(Unsafe_SetOrderedInt)},
+    {CC "putOrderedLong",     CC "(" OBJ "JJ)V",         FN_PTR(Unsafe_SetOrderedLong)},
+    {CC "park",               CC "(ZJ)V",                FN_PTR(Unsafe_Park)},
+    {CC "unpark",             CC "(" OBJ ")V",           FN_PTR(Unsafe_Unpark)},
 
-    {CC"getLoadAverage",     CC"([DI)I",                 FN_PTR(Unsafe_Loadavg)},
+    {CC "getLoadAverage",     CC "([DI)I",               FN_PTR(Unsafe_Loadavg)},
 
-    {CC"copyMemory",         CC"("OBJ"J"OBJ"JJ)V",       FN_PTR(Unsafe_CopyMemory)},
-    {CC"setMemory",          CC"("OBJ"JJB)V",            FN_PTR(Unsafe_SetMemory)},
+    {CC "copyMemory",         CC "(" OBJ "J" OBJ "JJ)V", FN_PTR(Unsafe_CopyMemory)},
+    {CC "setMemory",          CC "(" OBJ "JJB)V",        FN_PTR(Unsafe_SetMemory)},
 
-    {CC"defineAnonymousClass", CC"("DAC_Args")"CLS,      FN_PTR(Unsafe_DefineAnonymousClass)},
+    {CC "defineAnonymousClass", CC "(" DAC_Args ")" CLS, FN_PTR(Unsafe_DefineAnonymousClass)},
 
-    {CC"shouldBeInitialized",CC"("CLS")Z",               FN_PTR(Unsafe_ShouldBeInitialized)},
+    {CC "shouldBeInitialized",CC "(" CLS ")Z",           FN_PTR(Unsafe_ShouldBeInitialized)},
 
-    {CC"loadFence",          CC"()V",                    FN_PTR(Unsafe_LoadFence)},
-    {CC"storeFence",         CC"()V",                    FN_PTR(Unsafe_StoreFence)},
-    {CC"fullFence",          CC"()V",                    FN_PTR(Unsafe_FullFence)},
+    {CC "loadFence",          CC "()V",                  FN_PTR(Unsafe_LoadFence)},
+    {CC "storeFence",         CC "()V",                  FN_PTR(Unsafe_StoreFence)},
+    {CC "fullFence",          CC "()V",                  FN_PTR(Unsafe_FullFence)},
 
-    {CC"isBigEndian0",       CC"()Z",                    FN_PTR(Unsafe_isBigEndian0)},
-    {CC"unalignedAccess0",   CC"()Z",                    FN_PTR(Unsafe_unalignedAccess0)}
+    {CC "isBigEndian0",       CC "()Z",                  FN_PTR(Unsafe_isBigEndian0)},
+    {CC "unalignedAccess0",   CC "()Z",                  FN_PTR(Unsafe_unalignedAccess0)}
 };
 
 #undef CC
--- a/hotspot/src/share/vm/prims/whitebox.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/prims/whitebox.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -27,6 +27,7 @@
 #include <new>
 
 #include "classfile/classLoaderData.hpp"
+#include "classfile/imageFile.hpp"
 #include "classfile/stringTable.hpp"
 #include "code/codeCache.hpp"
 #include "jvmtifiles/jvmtiEnv.hpp"
@@ -159,8 +160,8 @@
 
 WB_ENTRY(void, WB_PrintHeapSizes(JNIEnv* env, jobject o)) {
   CollectorPolicy * p = Universe::heap()->collector_policy();
-  gclog_or_tty->print_cr("Minimum heap "SIZE_FORMAT" Initial heap "
-    SIZE_FORMAT" Maximum heap "SIZE_FORMAT" Space alignment "SIZE_FORMAT" Heap alignment "SIZE_FORMAT,
+  gclog_or_tty->print_cr("Minimum heap " SIZE_FORMAT " Initial heap "
+    SIZE_FORMAT " Maximum heap " SIZE_FORMAT " Space alignment " SIZE_FORMAT " Heap alignment " SIZE_FORMAT,
     p->min_heap_byte_size(), p->initial_heap_byte_size(), p->max_heap_byte_size(),
     p->space_alignment(), p->heap_alignment());
 }
@@ -195,8 +196,8 @@
          Universe::narrow_oop_use_implicit_null_checks() )) {
     tty->print_cr("WB_ReadFromNoaccessArea method is useless:\n "
                   "\tUseCompressedOops is %d\n"
-                  "\trhs.base() is "PTR_FORMAT"\n"
-                  "\tUniverse::narrow_oop_base() is "PTR_FORMAT"\n"
+                  "\trhs.base() is " PTR_FORMAT "\n"
+                  "\tUniverse::narrow_oop_base() is " PTR_FORMAT "\n"
                   "\tUniverse::narrow_oop_use_implicit_null_checks() is %d",
                   UseCompressedOops,
                   rhs.base(),
@@ -249,8 +250,8 @@
 
 WB_ENTRY(jint, WB_StressVirtualSpaceResize(JNIEnv* env, jobject o,
         jlong reserved_space_size, jlong magnitude, jlong iterations))
-  tty->print_cr("reservedSpaceSize="JLONG_FORMAT", magnitude="JLONG_FORMAT", "
-                "iterations="JLONG_FORMAT"\n", reserved_space_size, magnitude,
+  tty->print_cr("reservedSpaceSize=" JLONG_FORMAT ", magnitude=" JLONG_FORMAT ", "
+                "iterations=" JLONG_FORMAT "\n", reserved_space_size, magnitude,
                 iterations);
   if (reserved_space_size < 0 || magnitude < 0 || iterations < 0) {
     tty->print_cr("One of variables printed above is negative. Can't proceed.\n");
@@ -1125,6 +1126,132 @@
   return (jlong) MetaspaceGC::capacity_until_GC();
 WB_END
 
+WB_ENTRY(jboolean, WB_ReadImageFile(JNIEnv* env, jobject wb, jstring imagefile))
+  const char* filename = java_lang_String::as_utf8_string(JNIHandles::resolve_non_null(imagefile));
+  return ImageFileReader::open(filename) != NULL;
+WB_END
+
+WB_ENTRY(jlong, WB_imageOpenImage(JNIEnv *env, jobject wb, jstring path, jboolean big_endian))
+  ThreadToNativeFromVM ttn(thread);
+  const char *nativePath = env->GetStringUTFChars(path, NULL);
+  jlong ret = JVM_ImageOpen(env, nativePath, big_endian);
+
+  env->ReleaseStringUTFChars(path, nativePath);
+  return ret;
+WB_END
+
+WB_ENTRY(void, WB_imageCloseImage(JNIEnv *env, jobject wb, jlong id))
+  ThreadToNativeFromVM ttn(thread);
+  JVM_ImageClose(env, id);
+WB_END
+
+WB_ENTRY(jlong, WB_imageGetIndexAddress(JNIEnv *env, jobject wb, jlong id))
+  ThreadToNativeFromVM ttn(thread);
+  return JVM_ImageGetIndexAddress(env, id);
+WB_END
+
+WB_ENTRY(jlong, WB_imageGetDataAddress(JNIEnv *env, jobject wb, jlong id))
+  ThreadToNativeFromVM ttn(thread);
+  return JVM_ImageGetDataAddress(env, id);
+WB_END
+
+WB_ENTRY(jboolean, WB_imageRead(JNIEnv *env, jobject wb, jlong id, jlong offset, jobject uncompressedBuffer, jlong uncompressed_size))
+  ThreadToNativeFromVM ttn(thread);
+  if (uncompressedBuffer == NULL) {
+    return JNI_FALSE;
+  }
+  unsigned char* uncompressedAddress =
+          (unsigned char*) env->GetDirectBufferAddress(uncompressedBuffer);
+  return JVM_ImageRead(env, id, offset, uncompressedAddress, uncompressed_size);
+WB_END
+
+WB_ENTRY(jboolean, WB_imageReadCompressed(JNIEnv *env, jobject wb, jlong id, jlong offset, jobject compressedBuffer, jlong compressed_size, jobject uncompressedBuffer, jlong uncompressed_size))
+  ThreadToNativeFromVM ttn(thread);
+  if (uncompressedBuffer == NULL || compressedBuffer == NULL) {
+    return false;
+  }
+  // Get address of read direct buffer.
+  unsigned char* compressedAddress =
+        (unsigned char*) env->GetDirectBufferAddress(compressedBuffer);
+  // Get address of decompression direct buffer.
+  unsigned char* uncompressedAddress =
+        (unsigned char*) env->GetDirectBufferAddress(uncompressedBuffer);
+  return JVM_ImageReadCompressed(env, id, offset, compressedAddress, compressed_size, uncompressedAddress, uncompressed_size);
+WB_END
+
+WB_ENTRY(jbyteArray, WB_imageGetStringBytes(JNIEnv *env, jobject wb, jlong id, jlong offset))
+  ThreadToNativeFromVM ttn(thread);
+  const char* data = JVM_ImageGetStringBytes(env, id, offset);
+  // Determine String length.
+  size_t size = strlen(data);
+  // Allocate byte array.
+  jbyteArray byteArray = env->NewByteArray((jsize) size);
+  // Get array base address.
+  jbyte* rawBytes = env->GetByteArrayElements(byteArray, NULL);
+  // Copy bytes from image string table.
+  memcpy(rawBytes, data, size);
+  // Release byte array base address.
+  env->ReleaseByteArrayElements(byteArray, rawBytes, 0);
+  return byteArray;
+WB_END
+
+WB_ENTRY(jlong, WB_imageGetStringsSize(JNIEnv *env, jobject wb, jlong id))
+  ImageFileReader* reader = ImageFileReader::idToReader(id);
+  return reader? reader->strings_size() : 0L;
+WB_END
+
+WB_ENTRY(jlongArray, WB_imageGetAttributes(JNIEnv *env, jobject wb, jlong id, jint offset))
+  ThreadToNativeFromVM ttn(thread);
+  // Allocate a jlong large enough for all location attributes.
+  jlongArray attributes = env->NewLongArray(JVM_ImageGetAttributesCount(env));
+  // Get base address for jlong array.
+  jlong* rawAttributes = env->GetLongArrayElements(attributes, NULL);
+  jlong* ret = JVM_ImageGetAttributes(env, rawAttributes, id, offset);
+  // Release jlong array base address.
+  env->ReleaseLongArrayElements(attributes, rawAttributes, 0);
+    return ret == NULL ? NULL : attributes;
+WB_END
+
+WB_ENTRY(jlongArray, WB_imageFindAttributes(JNIEnv *env, jobject wb, jlong id, jbyteArray utf8))
+  ThreadToNativeFromVM ttn(thread);
+  // Allocate a jlong large enough for all location attributes.
+  jlongArray attributes = env->NewLongArray(JVM_ImageGetAttributesCount(env));
+  // Get base address for jlong array.
+  jlong* rawAttributes = env->GetLongArrayElements(attributes, NULL);
+  jsize size = env->GetArrayLength(utf8);
+  jbyte* rawBytes = env->GetByteArrayElements(utf8, NULL);
+  jlong* ret = JVM_ImageFindAttributes(env, rawAttributes, rawBytes, size, id);
+  env->ReleaseByteArrayElements(utf8, rawBytes, 0);
+  env->ReleaseLongArrayElements(attributes, rawAttributes, 0);
+  return ret == NULL ? NULL : attributes;
+WB_END
+
+WB_ENTRY(jintArray, WB_imageAttributeOffsets(JNIEnv *env, jobject wb, jlong id))
+  ThreadToNativeFromVM ttn(thread);
+  unsigned int length = JVM_ImageAttributeOffsetsLength(env, id);
+  if (length == 0) {
+    return NULL;
+  }
+  jintArray offsets = env->NewIntArray(length);
+  // Get base address of result.
+  jint* rawOffsets = env->GetIntArrayElements(offsets, NULL);
+  jint* ret = JVM_ImageAttributeOffsets(env, rawOffsets, length, id);
+  // Release result base address.
+  env->ReleaseIntArrayElements(offsets, rawOffsets, 0);
+  return ret == NULL ? NULL : offsets;
+WB_END
+
+WB_ENTRY(jint, WB_imageGetIntAtAddress(JNIEnv *env, jobject wb, jlong address, jint offset, jboolean big_endian))
+  unsigned char* arr = (unsigned char*) address + offset;
+  jint uraw;
+  if (big_endian) {
+     uraw = arr[0] << 24 | arr[1]<<16 | (arr[2]<<8) | arr[3];
+  } else {
+      uraw = arr[0] | arr[1]<<8 | (arr[2]<<16) | arr[3]<<24;
+  }
+  return uraw;
+WB_END
+
 WB_ENTRY(void, WB_AssertMatchingSafepointCalls(JNIEnv* env, jobject o, jboolean mutexSafepointValue, jboolean attemptedNoSafepointValue))
   Monitor::SafepointCheckRequired sfpt_check_required = mutexSafepointValue ?
                                            Monitor::_safepoint_check_always :
@@ -1428,8 +1555,23 @@
   {CC"getCodeBlob",        CC"(J)[Ljava/lang/Object;",(void*)&WB_GetCodeBlob        },
   {CC"getThreadStackSize", CC"()J",                   (void*)&WB_GetThreadStackSize },
   {CC"getThreadRemainingStackSize", CC"()J",          (void*)&WB_GetThreadRemainingStackSize },
+  {CC"readImageFile",      CC"(Ljava/lang/String;)Z", (void*)&WB_ReadImageFile },
+  {CC"imageOpenImage",     CC"(Ljava/lang/String;Z)J",(void*)&WB_imageOpenImage },
+  {CC"imageCloseImage",    CC"(J)V",                  (void*)&WB_imageCloseImage },
+  {CC"imageGetIndexAddress",CC"(J)J",                 (void*)&WB_imageGetIndexAddress},
+  {CC"imageGetDataAddress",CC"(J)J",                  (void*)&WB_imageGetDataAddress},
+  {CC"imageRead",          CC"(JJLjava/nio/ByteBuffer;J)Z",
+                                                      (void*)&WB_imageRead    },
+  {CC"imageReadCompressed",CC"(JJLjava/nio/ByteBuffer;JLjava/nio/ByteBuffer;J)Z",
+                                                      (void*)&WB_imageReadCompressed},
+  {CC"imageGetStringBytes",CC"(JI)[B",                (void*)&WB_imageGetStringBytes},
+  {CC"imageGetStringsSize",CC"(J)J",                  (void*)&WB_imageGetStringsSize},
+  {CC"imageGetAttributes", CC"(JI)[J",                (void*)&WB_imageGetAttributes},
+  {CC"imageFindAttributes",CC"(J[B)[J",               (void*)&WB_imageFindAttributes},
+  {CC"imageAttributeOffsets",CC"(J)[I",               (void*)&WB_imageAttributeOffsets},
+  {CC"imageGetIntAtAddress",CC"(JIZ)I",                (void*)&WB_imageGetIntAtAddress},
   {CC"assertMatchingSafepointCalls", CC"(ZZ)V",       (void*)&WB_AssertMatchingSafepointCalls },
-  {CC"isMonitorInflated0",  CC"(Ljava/lang/Object;)Z", (void*)&WB_IsMonitorInflated  },
+  {CC"isMonitorInflated0", CC"(Ljava/lang/Object;)Z", (void*)&WB_IsMonitorInflated  },
   {CC"forceSafepoint",     CC"()V",                   (void*)&WB_ForceSafepoint     },
   {CC"getMethodBooleanOption",
       CC"(Ljava/lang/reflect/Executable;Ljava/lang/String;)Ljava/lang/Boolean;",
--- a/hotspot/src/share/vm/runtime/arguments.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/arguments.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -27,6 +27,7 @@
 #include "classfile/javaAssertions.hpp"
 #include "classfile/stringTable.hpp"
 #include "classfile/symbolTable.hpp"
+#include "code/codeCacheExtensions.hpp"
 #include "compiler/compilerOracle.hpp"
 #include "gc/shared/cardTableRS.hpp"
 #include "gc/shared/genCollectedHeap.hpp"
@@ -275,6 +276,7 @@
   { "AdaptiveSizePausePolicy",       JDK_Version::jdk(9), JDK_Version::jdk(10) },
   { "ParallelGCRetainPLAB",          JDK_Version::jdk(9), JDK_Version::jdk(10) },
   { "ThreadSafetyMargin",            JDK_Version::jdk(9), JDK_Version::jdk(10) },
+  { "LazyBootClassLoader",           JDK_Version::jdk(9), JDK_Version::jdk(10) },
   { NULL, JDK_Version(0), JDK_Version(0) }
 };
 
@@ -835,16 +837,19 @@
     arg_len = equal_sign - argname;
   }
 
-  // Construct a string which consists only of the argument name without '+', '-', or '='.
-  char stripped_argname[256];
-  strncpy(stripped_argname, argname, arg_len);
-  stripped_argname[arg_len] = '\0'; //strncpy doesn't null terminate.
-
-  if (is_newly_obsolete(stripped_argname, &since)) {
-    char version[256];
-    since.to_string(version, sizeof(version));
-    warning("ignoring option %s; support was removed in %s", stripped_argname, version);
-    return true;
+  // Only make the obsolete check for valid arguments.
+  if (arg_len <= BUFLEN) {
+    // Construct a string which consists only of the argument name without '+', '-', or '='.
+    char stripped_argname[BUFLEN+1];
+    strncpy(stripped_argname, argname, arg_len);
+    stripped_argname[arg_len] = '\0';  // strncpy may not null terminate.
+
+    if (is_newly_obsolete(stripped_argname, &since)) {
+      char version[256];
+      since.to_string(version, sizeof(version));
+      warning("ignoring option %s; support was removed in %s", stripped_argname, version);
+      return true;
+    }
   }
 
   // For locked flags, report a custom error message if available.
@@ -1582,6 +1587,11 @@
   // in vm_version initialization code.
 #endif // _LP64
 #endif // !ZERO
+
+  // Set up runtime image flags.
+  set_runtime_image_flags();
+
+  CodeCacheExtensions::set_ergonomics_flags();
 }
 
 void Arguments::set_parallel_gc_flags() {
@@ -1837,6 +1847,16 @@
   }
 }
 
+  // Set up runtime image flags
+void Arguments::set_runtime_image_flags() {
+#ifdef _LP64
+  // Memory map image file by default on 64 bit machines.
+  if (FLAG_IS_DEFAULT(MemoryMapImage)) {
+    FLAG_SET_ERGO(bool, MemoryMapImage, true);
+  }
+#endif
+}
+
 // This must be called after ergonomics.
 void Arguments::set_bytecode_flags() {
   if (!RewriteBytecodes) {
@@ -2558,9 +2578,15 @@
                        round_to((int)long_ThreadStackSize, K) / K) != Flag::SUCCESS) {
         return JNI_EINVAL;
       }
-    // -Xoss
-    } else if (match_option(option, "-Xoss", &tail)) {
-          // HotSpot does not have separate native and Java stacks, ignore silently for compatibility
+    // -Xoss, -Xsqnopause, -Xoptimize, -Xboundthreads
+    } else if (match_option(option, "-Xoss", &tail) ||
+               match_option(option, "-Xsqnopause") ||
+               match_option(option, "-Xoptimize") ||
+               match_option(option, "-Xboundthreads")) {
+      // All these options are deprecated in JDK 9 and will be removed in a future release
+      char version[256];
+      JDK_Version::jdk(9).to_string(version, sizeof(version));
+      warning("ignoring option %s; support was removed in %s", option->optionString, version);
     } else if (match_option(option, "-XX:CodeCacheExpansionSize=", &tail)) {
       julong long_CodeCacheExpansionSize = 0;
       ArgsRange errcode = parse_memory_size(tail, &long_CodeCacheExpansionSize, os::vm_page_size());
@@ -2633,9 +2659,6 @@
     // -native
     } else if (match_option(option, "-native")) {
           // HotSpot always uses native threads, ignore silently for compatibility
-    // -Xsqnopause
-    } else if (match_option(option, "-Xsqnopause")) {
-          // EVM option, ignore silently for compatibility
     // -Xrs
     } else if (match_option(option, "-Xrs")) {
           // Classic/EVM option, new functionality
@@ -2647,9 +2670,6 @@
       if (FLAG_SET_CMDLINE(bool, UseAltSigs, true) != Flag::SUCCESS) {
         return JNI_EINVAL;
       }
-    // -Xoptimize
-    } else if (match_option(option, "-Xoptimize")) {
-          // EVM option, ignore silently for compatibility
     // -Xprof
     } else if (match_option(option, "-Xprof")) {
 #if INCLUDE_FPROF
@@ -2795,8 +2815,6 @@
     // -Xnoagent
     } else if (match_option(option, "-Xnoagent")) {
       // For compatibility with classic. HotSpot refuses to load the old style agent.dll.
-    } else if (match_option(option, "-Xboundthreads")) {
-      // Ignore silently for compatibility
     } else if (match_option(option, "-Xloggc:", &tail)) {
       // Redirect GC output to the file. -Xloggc:<filename>
       // ostream_init_log(), when called will use this filename
--- a/hotspot/src/share/vm/runtime/arguments.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/arguments.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -224,6 +224,7 @@
 class Arguments : AllStatic {
   friend class VMStructs;
   friend class JvmtiExport;
+  friend class CodeCacheExtensions;
  public:
   // Operation modi
   enum Mode {
@@ -347,6 +348,8 @@
   static julong limit_by_allocatable_memory(julong size);
   // Setup heap size
   static void set_heap_size();
+  // Set up runtime image flags
+  static void set_runtime_image_flags();
   // Based on automatic selection criteria, should the
   // low pause collector be used.
   static bool should_auto_select_low_pause_collector();
--- a/hotspot/src/share/vm/runtime/commandLineFlagRangeList.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/commandLineFlagRangeList.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -84,7 +84,7 @@
   }
 
   void print(outputStream* st) {
-    st->print("[ "INTX_FORMAT_W(-25)" ... "INTX_FORMAT_W(25)" ]", _min, _max);
+    st->print("[ " INTX_FORMAT_W(-25) " ... " INTX_FORMAT_W(25) " ]", _min, _max);
   }
 };
 
@@ -140,7 +140,7 @@
   }
 
   void print(outputStream* st) {
-    st->print("[ "UINTX_FORMAT_W(-25)" ... "UINTX_FORMAT_W(25)" ]", _min, _max);
+    st->print("[ " UINTX_FORMAT_W(-25) " ... " UINTX_FORMAT_W(25) " ]", _min, _max);
   }
 };
 
@@ -168,7 +168,7 @@
   }
 
   void print(outputStream* st) {
-    st->print("[ "UINT64_FORMAT_W(-25)" ... "UINT64_FORMAT_W(25)" ]", _min, _max);
+    st->print("[ " UINT64_FORMAT_W(-25) " ... " UINT64_FORMAT_W(25) " ]", _min, _max);
   }
 };
 
@@ -196,7 +196,7 @@
   }
 
   void print(outputStream* st) {
-    st->print("[ "SIZE_FORMAT_W(-25)" ... "SIZE_FORMAT_W(25)" ]", _min, _max);
+    st->print("[ " SIZE_FORMAT_W(-25) " ... " SIZE_FORMAT_W(25) " ]", _min, _max);
   }
 };
 
--- a/hotspot/src/share/vm/runtime/deoptimization.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/deoptimization.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1340,7 +1340,7 @@
       ttyLocker ttyl;
       char buf[100];
       if (xtty != NULL) {
-        xtty->begin_head("uncommon_trap thread='" UINTX_FORMAT"' %s",
+        xtty->begin_head("uncommon_trap thread='" UINTX_FORMAT "' %s",
                          os::current_thread_id(),
                          format_trap_request(buf, sizeof(buf), trap_request));
         nm->log_identity(xtty);
--- a/hotspot/src/share/vm/runtime/globals.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/globals.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1240,7 +1240,7 @@
         size_ranges += sizeof(CommandLineFlagRange*);
       }
     }
-    fprintf(stderr, "Size of %d ranges: "SIZE_FORMAT" bytes\n",
+    fprintf(stderr, "Size of %d ranges: " SIZE_FORMAT " bytes\n",
             CommandLineFlagRangeList::length(), size_ranges);
   }
   {
@@ -1270,7 +1270,7 @@
         size_constraints += sizeof(CommandLineFlagConstraint*);
       }
     }
-    fprintf(stderr, "Size of %d constraints: "SIZE_FORMAT" bytes\n",
+    fprintf(stderr, "Size of %d constraints: " SIZE_FORMAT " bytes\n",
             CommandLineFlagConstraintList::length(), size_constraints);
   }
 #endif // PRINT_RANGES_AND_CONSTRAINTS_SIZES
--- a/hotspot/src/share/vm/runtime/globals.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/globals.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -728,7 +728,8 @@
           "Control whether AES instructions can be used on x86/x64")        \
                                                                             \
   product(bool, UseSHA, false,                                              \
-          "Control whether SHA instructions can be used on SPARC")          \
+          "Control whether SHA instructions can be used "                   \
+          "on SPARC and on ARM")                                            \
                                                                             \
   product(bool, UseGHASHIntrinsics, false,                                  \
           "Use intrinsics for GHASH versions of crypto")                    \
@@ -837,13 +838,16 @@
           "Use intrinsics for AES versions of crypto")                      \
                                                                             \
   product(bool, UseSHA1Intrinsics, false,                                   \
-          "Use intrinsics for SHA-1 crypto hash function")                  \
+          "Use intrinsics for SHA-1 crypto hash function. "                 \
+          "Requires that UseSHA is enabled.")                                \
                                                                             \
   product(bool, UseSHA256Intrinsics, false,                                 \
-          "Use intrinsics for SHA-224 and SHA-256 crypto hash functions")   \
+          "Use intrinsics for SHA-224 and SHA-256 crypto hash functions. "  \
+          "Requires that UseSHA is enabled.")                               \
                                                                             \
   product(bool, UseSHA512Intrinsics, false,                                 \
-          "Use intrinsics for SHA-384 and SHA-512 crypto hash functions")   \
+          "Use intrinsics for SHA-384 and SHA-512 crypto hash functions. "  \
+          "Requires that UseSHA is enabled.")                               \
                                                                             \
   product(bool, UseCRC32Intrinsics, false,                                  \
           "use intrinsics for java.util.zip.CRC32")                         \
@@ -1032,6 +1036,10 @@
   product(bool, CreateCoredumpOnCrash, true,                                \
           "Create core/mini dump on VM fatal error")                        \
                                                                             \
+  product(uintx, ErrorLogTimeout, 2 * 60,                                   \
+          "Timeout, in seconds, to limit the time spent on writing an "     \
+          "error log in case of a crash.")                                  \
+                                                                            \
   product_pd(bool, UseOSErrorReporting,                                     \
           "Let VM fatal error propagate to the OS (ie. WER on Windows)")    \
                                                                             \
@@ -1099,6 +1107,9 @@
   product(bool, AlwaysRestoreFPU, false,                                    \
           "Restore the FPU control word after every JNI call (expensive)")  \
                                                                             \
+  product(bool, MemoryMapImage, false,                                      \
+          "Memory map entire runtime image")                                \
+                                                                            \
   diagnostic(bool, PrintCompilation2, false,                                \
           "Print additional statistics per compilation")                    \
                                                                             \
@@ -1361,9 +1372,6 @@
   develop(uintx, PreallocatedOutOfMemoryErrorCount, 4,                      \
           "Number of OutOfMemoryErrors preallocated with backtrace")        \
                                                                             \
-  product(bool, LazyBootClassLoader, true,                                  \
-          "Enable/disable lazy opening of boot class path entries")         \
-                                                                            \
   product(bool, UseXMMForArrayCopy, false,                                  \
           "Use SSE2 MOVQ instruction for Arraycopy")                        \
                                                                             \
@@ -4120,7 +4128,16 @@
                                                                             \
   product_pd(bool, PreserveFramePointer,                                    \
              "Use the FP register for holding the frame pointer "           \
-             "and not as a general purpose register.")
+             "and not as a general purpose register.")                      \
+                                                                            \
+  diagnostic(bool, CheckIntrinsics, trueInDebug,                            \
+             "When a class C is loaded, check that "                        \
+             "(1) all intrinsics defined by the VM for class C are present "\
+             "in the loaded class file and are marked with the "            \
+             "@HotSpotIntrinsicCandidate annotation and also that "         \
+             "(2) there is an intrinsic registered for all loaded methods " \
+             "that are annotated with the @HotSpotIntrinsicCandidate "      \
+             "annotation.")
 
 /*
  *  Macros for factoring of globals
--- a/hotspot/src/share/vm/runtime/init.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/init.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -24,6 +24,7 @@
 
 #include "precompiled.hpp"
 #include "classfile/stringTable.hpp"
+#include "code/codeCacheExtensions.hpp"
 #include "code/icBuffer.hpp"
 #include "gc/shared/collectedHeap.hpp"
 #include "interpreter/bytecodes.hpp"
@@ -82,6 +83,7 @@
 // during VM shutdown
 void perfMemory_exit();
 void ostream_exit();
+bool image_decompressor_init();
 
 void vm_init_globals() {
   check_ThreadShadow();
@@ -100,21 +102,29 @@
   classLoader_init();
   compilationPolicy_init();
   codeCache_init();
+  CodeCacheExtensions::initialize();
   VM_Version_init();
+  CodeCacheExtensions::complete_step(CodeCacheExtensionsSteps::VMVersion);
   os_init_globals();
   stubRoutines_init1();
+  CodeCacheExtensions::complete_step(CodeCacheExtensionsSteps::StubRoutines1);
   jint status = universe_init();  // dependent on codeCache_init and
                                   // stubRoutines_init1 and metaspace_init.
   if (status != JNI_OK)
     return status;
 
+  CodeCacheExtensions::complete_step(CodeCacheExtensionsSteps::Universe);
   interpreter_init();  // before any methods loaded
+  CodeCacheExtensions::complete_step(CodeCacheExtensionsSteps::Interpreter);
   invocationCounter_init();  // before any methods loaded
   marksweep_init();
   accessFlags_init();
   templateTable_init();
   InterfaceSupport_init();
   SharedRuntime::generate_stubs();
+  if (!image_decompressor_init()) {
+    return JNI_ERR;
+  }
   universe2_init();  // dependent on codeCache_init and stubRoutines_init1
   referenceProcessor_init();
   jni_handles_init();
@@ -133,6 +143,7 @@
   }
   javaClasses_init();   // must happen after vtable initialization
   stubRoutines_init2(); // note: StubRoutines need 2-phase init
+  CodeCacheExtensions::complete_step(CodeCacheExtensionsSteps::StubRoutines2);
 
 #if INCLUDE_NMT
   // Solaris stack is walkable only after stubRoutines are set up.
@@ -146,6 +157,7 @@
     CommandLineFlags::printFlags(tty, false, PrintFlagsRanges);
   }
 
+  CodeCacheExtensions::complete_step(CodeCacheExtensionsSteps::InitGlobals);
   return JNI_OK;
 }
 
--- a/hotspot/src/share/vm/runtime/mutexLocker.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/mutexLocker.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -100,6 +100,8 @@
 Mutex*   ExceptionCache_lock          = NULL;
 Monitor* ObjAllocPost_lock            = NULL;
 Mutex*   OsrList_lock                 = NULL;
+Mutex*   ImageFileReaderTable_lock    = NULL;
+
 #ifndef PRODUCT
 Mutex*   FullGCALot_lock              = NULL;
 #endif
@@ -227,6 +229,7 @@
   def(ProfilePrint_lock            , Mutex  , leaf,        false, Monitor::_safepoint_check_always);     // serial profile printing
   def(ExceptionCache_lock          , Mutex  , leaf,        false, Monitor::_safepoint_check_always);     // serial profile printing
   def(OsrList_lock                 , Mutex  , leaf,        true,  Monitor::_safepoint_check_never);
+  def(ImageFileReaderTable_lock    , Mutex  , nonleaf,     false, Monitor::_safepoint_check_always);     // synchronize image readers open/close
   def(Debug1_lock                  , Mutex  , leaf,        true,  Monitor::_safepoint_check_never);
 #ifndef PRODUCT
   def(FullGCALot_lock              , Mutex  , leaf,        false, Monitor::_safepoint_check_always);     // a lock to make FullGCALot MT safe
--- a/hotspot/src/share/vm/runtime/mutexLocker.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/mutexLocker.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -102,6 +102,7 @@
 extern Mutex*   ProfilePrint_lock;               // a lock used to serialize the printing of profiles
 extern Mutex*   ExceptionCache_lock;             // a lock used to synchronize exception cache updates
 extern Mutex*   OsrList_lock;                    // a lock used to serialize access to OSR queues
+extern Mutex*   ImageFileReaderTable_lock;       // a lock used to synchronize image readers open/close
 
 #ifndef PRODUCT
 extern Mutex*   FullGCALot_lock;                 // a lock to make FullGCALot MT safe
--- a/hotspot/src/share/vm/runtime/os.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/os.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1237,7 +1237,7 @@
   struct stat st;
 
   // modular image if bootmodules.jimage exists
-  char* jimage = format_boot_path("%/lib/modules/bootmodules.jimage", home, home_len, fileSep, pathSep);
+  char* jimage = format_boot_path("%/lib/modules/" BOOT_IMAGE_NAME, home, home_len, fileSep, pathSep);
   if (jimage == NULL) return false;
   bool has_jimage = (os::stat(jimage, &st) == 0);
   if (has_jimage) {
--- a/hotspot/src/share/vm/runtime/reflection.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/reflection.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1002,8 +1002,9 @@
                 vmSymbols::throwable_void_signature(),
                 &args);
   } else {
-    if (rtype == T_BOOLEAN || rtype == T_BYTE || rtype == T_CHAR || rtype == T_SHORT)
+    if (rtype == T_BOOLEAN || rtype == T_BYTE || rtype == T_CHAR || rtype == T_SHORT) {
       narrow((jvalue*) result.get_value_addr(), rtype, CHECK_NULL);
+    }
     return box((jvalue*) result.get_value_addr(), rtype, THREAD);
   }
 }
--- a/hotspot/src/share/vm/runtime/safepoint.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/safepoint.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -894,7 +894,7 @@
 
     case _running:
     default:
-       tty->print_cr("restart thread "INTPTR_FORMAT" with state %d",
+       tty->print_cr("restart thread " INTPTR_FORMAT " with state %d",
                       _thread, _type);
        _thread->print();
       ShouldNotReachHere();
@@ -1193,7 +1193,7 @@
     sstats = &_safepoint_stats[index];
     tty->print("%.3f: ", sstats->_time_stamp);
     tty->print("%-26s       ["
-               INT32_FORMAT_W(8)INT32_FORMAT_W(11)INT32_FORMAT_W(15)
+               INT32_FORMAT_W(8) INT32_FORMAT_W(11) INT32_FORMAT_W(15)
                "    ]    ",
                sstats->_vmop_type == -1 ? "no vm operation" :
                VM_Operation::name(sstats->_vmop_type),
@@ -1202,9 +1202,9 @@
                sstats->_nof_threads_wait_to_block);
     // "/ MICROUNITS " is to convert the unit from nanos to millis.
     tty->print("  ["
-               INT64_FORMAT_W(6)INT64_FORMAT_W(6)
-               INT64_FORMAT_W(6)INT64_FORMAT_W(6)
-               INT64_FORMAT_W(6)"    ]  ",
+               INT64_FORMAT_W(6) INT64_FORMAT_W(6)
+               INT64_FORMAT_W(6) INT64_FORMAT_W(6)
+               INT64_FORMAT_W(6) "    ]  ",
                sstats->_time_to_spin / MICROUNITS,
                sstats->_time_to_wait_to_block / MICROUNITS,
                sstats->_time_to_sync / MICROUNITS,
@@ -1212,9 +1212,9 @@
                sstats->_time_to_exec_vmop / MICROUNITS);
 
     if (need_to_track_page_armed_status) {
-      tty->print(INT32_FORMAT"         ", sstats->_page_armed);
+      tty->print(INT32_FORMAT "         ", sstats->_page_armed);
     }
-    tty->print_cr(INT32_FORMAT"   ", sstats->_nof_threads_hit_page_trap);
+    tty->print_cr(INT32_FORMAT "   ", sstats->_nof_threads_hit_page_trap);
   }
 }
 
@@ -1249,17 +1249,17 @@
 
   for (int index = 0; index < VM_Operation::VMOp_Terminating; index++) {
     if (_safepoint_reasons[index] != 0) {
-      tty->print_cr("%-26s"UINT64_FORMAT_W(10), VM_Operation::name(index),
+      tty->print_cr("%-26s" UINT64_FORMAT_W(10), VM_Operation::name(index),
                     _safepoint_reasons[index]);
     }
   }
 
-  tty->print_cr(UINT64_FORMAT_W(5)" VM operations coalesced during safepoint",
+  tty->print_cr(UINT64_FORMAT_W(5) " VM operations coalesced during safepoint",
                 _coalesced_vmop_count);
-  tty->print_cr("Maximum sync time  "INT64_FORMAT_W(5)" ms",
+  tty->print_cr("Maximum sync time  " INT64_FORMAT_W(5) " ms",
                 _max_sync_time / MICROUNITS);
   tty->print_cr("Maximum vm operation time (except for Exit VM operation)  "
-                INT64_FORMAT_W(5)" ms",
+                INT64_FORMAT_W(5) " ms",
                 _max_vmop_time / MICROUNITS);
 }
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/vm/runtime/semaphore.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,93 @@
+/*
+ * 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.
+ *
+ */
+
+#include "precompiled.hpp"
+#include "utilities/debug.hpp"
+#include "runtime/semaphore.hpp"
+
+/////////////// Unit tests ///////////////
+
+#ifndef PRODUCT
+
+static void test_semaphore_single_separate(uint count) {
+  Semaphore sem(0);
+
+  for (uint i = 0; i < count; i++) {
+    sem.signal();
+  }
+
+  for (uint i = 0; i < count; i++) {
+    sem.wait();
+  }
+}
+
+static void test_semaphore_single_combined(uint count) {
+  Semaphore sem(0);
+
+  for (uint i = 0; i < count; i++) {
+    sem.signal();
+    sem.wait();
+  }
+}
+
+static void test_semaphore_many(uint value, uint max, uint increments) {
+  Semaphore sem(value);
+
+  uint total = value;
+
+  for (uint i = value; i + increments <= max; i += increments) {
+    sem.signal(increments);
+
+    total += increments;
+  }
+
+  for (uint i = 0; i < total; i++) {
+    sem.wait();
+  }
+}
+
+static void test_semaphore_many() {
+  for (uint max = 0; max < 10; max++) {
+    for (uint value = 0; value < max; value++) {
+      for (uint inc = 1; inc <= max - value; inc++) {
+        test_semaphore_many(value, max, inc);
+      }
+    }
+  }
+}
+
+void test_semaphore() {
+  for (uint i = 1; i < 10; i++) {
+    test_semaphore_single_separate(i);
+  }
+
+  for (uint i = 0; i < 10; i++) {
+    test_semaphore_single_combined(i);
+  }
+
+  test_semaphore_many();
+}
+
+#endif // PRODUCT
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/vm/runtime/semaphore.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,58 @@
+/*
+ * 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.
+ *
+ */
+
+#ifndef SHARE_VM_RUNTIME_SEMAPHORE_HPP
+#define SHARE_VM_RUNTIME_SEMAPHORE_HPP
+
+#include "memory/allocation.hpp"
+
+#if defined(TARGET_OS_FAMILY_linux) || defined(TARGET_OS_FAMILY_solaris) || defined(TARGET_OS_FAMILY_aix)
+# include "semaphore_posix.hpp"
+#elif defined(TARGET_OS_FAMILY_bsd)
+# include "semaphore_bsd.hpp"
+#elif defined(TARGET_OS_FAMILY_windows)
+# include "semaphore_windows.hpp"
+#else
+# error "No semaphore implementation provided for this OS"
+#endif
+
+// Implements the limited, platform independent Semaphore API.
+class Semaphore : public CHeapObj<mtInternal> {
+  SemaphoreImpl _impl;
+
+  // Prevent copying and assignment of Semaphore instances.
+  Semaphore(const Semaphore&);
+  Semaphore& operator=(const Semaphore&);
+
+ public:
+  Semaphore(uint value = 0) : _impl(value) {}
+  ~Semaphore() {}
+
+  void signal(uint count = 1) { _impl.signal(count); }
+
+  void wait()                 { _impl.wait(); }
+};
+
+
+#endif // SHARE_VM_RUNTIME_SEMAPHORE_HPP
--- a/hotspot/src/share/vm/runtime/sharedRuntime.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/sharedRuntime.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -27,6 +27,7 @@
 #include "classfile/vmSymbols.hpp"
 #include "code/codeCache.hpp"
 #include "code/compiledIC.hpp"
+#include "code/codeCacheExtensions.hpp"
 #include "code/scopeDesc.hpp"
 #include "code/vtableStubs.hpp"
 #include "compiler/abstractCompiler.hpp"
@@ -2307,19 +2308,35 @@
   return _buffer;
 }
 
+extern "C" void unexpected_adapter_call() {
+  ShouldNotCallThis();
+}
+
 void AdapterHandlerLibrary::initialize() {
   if (_adapters != NULL) return;
   _adapters = new AdapterHandlerTable();
 
-  // Create a special handler for abstract methods.  Abstract methods
-  // are never compiled so an i2c entry is somewhat meaningless, but
-  // throw AbstractMethodError just in case.
-  // Pass wrong_method_abstract for the c2i transitions to return
-  // AbstractMethodError for invalid invocations.
-  address wrong_method_abstract = SharedRuntime::get_handle_wrong_method_abstract_stub();
-  _abstract_method_handler = AdapterHandlerLibrary::new_entry(new AdapterFingerPrint(0, NULL),
-                                                              StubRoutines::throw_AbstractMethodError_entry(),
-                                                              wrong_method_abstract, wrong_method_abstract);
+  if (!CodeCacheExtensions::skip_compiler_support()) {
+    // Create a special handler for abstract methods.  Abstract methods
+    // are never compiled so an i2c entry is somewhat meaningless, but
+    // throw AbstractMethodError just in case.
+    // Pass wrong_method_abstract for the c2i transitions to return
+    // AbstractMethodError for invalid invocations.
+    address wrong_method_abstract = SharedRuntime::get_handle_wrong_method_abstract_stub();
+    _abstract_method_handler = AdapterHandlerLibrary::new_entry(new AdapterFingerPrint(0, NULL),
+                                                                StubRoutines::throw_AbstractMethodError_entry(),
+                                                                wrong_method_abstract, wrong_method_abstract);
+  } else {
+    // Adapters are not supposed to be used.
+    // Generate a special one to cause an error if used (and store this
+    // singleton in place of the useless _abstract_method_error adapter).
+    address entry = (address) &unexpected_adapter_call;
+    _abstract_method_handler = AdapterHandlerLibrary::new_entry(new AdapterFingerPrint(0, NULL),
+                                                                entry,
+                                                                entry,
+                                                                entry);
+
+  }
 }
 
 AdapterHandlerEntry* AdapterHandlerLibrary::new_entry(AdapterFingerPrint* fingerprint,
@@ -2346,6 +2363,15 @@
     // make sure data structure is initialized
     initialize();
 
+    if (CodeCacheExtensions::skip_compiler_support()) {
+      // adapters are useless and should not be used, including the
+      // abstract_method_handler. However, some callers check that
+      // an adapter was installed.
+      // Return the singleton adapter, stored into _abstract_method_handler
+      // and modified to cause an error if we ever call it.
+      return _abstract_method_handler;
+    }
+
     if (method->is_abstract()) {
       return _abstract_method_handler;
     }
@@ -2616,71 +2642,6 @@
   GC_locker::unlock_critical(thread);
 JRT_END
 
-int SharedRuntime::convert_ints_to_longints_argcnt(int in_args_count, BasicType* in_sig_bt) {
-  int argcnt = in_args_count;
-  if (CCallingConventionRequiresIntsAsLongs) {
-    for (int in = 0; in < in_args_count; in++) {
-      BasicType bt = in_sig_bt[in];
-      switch (bt) {
-        case T_BOOLEAN:
-        case T_CHAR:
-        case T_BYTE:
-        case T_SHORT:
-        case T_INT:
-          argcnt++;
-          break;
-        default:
-          break;
-      }
-    }
-  } else {
-    assert(0, "This should not be needed on this platform");
-  }
-
-  return argcnt;
-}
-
-void SharedRuntime::convert_ints_to_longints(int i2l_argcnt, int& in_args_count,
-                                             BasicType*& in_sig_bt, VMRegPair*& in_regs) {
-  if (CCallingConventionRequiresIntsAsLongs) {
-    VMRegPair *new_in_regs   = NEW_RESOURCE_ARRAY(VMRegPair, i2l_argcnt);
-    BasicType *new_in_sig_bt = NEW_RESOURCE_ARRAY(BasicType, i2l_argcnt);
-
-    int argcnt = 0;
-    for (int in = 0; in < in_args_count; in++, argcnt++) {
-      BasicType bt  = in_sig_bt[in];
-      VMRegPair reg = in_regs[in];
-      switch (bt) {
-        case T_BOOLEAN:
-        case T_CHAR:
-        case T_BYTE:
-        case T_SHORT:
-        case T_INT:
-          // Convert (bt) to (T_LONG,bt).
-          new_in_sig_bt[argcnt] = T_LONG;
-          new_in_sig_bt[argcnt+1] = bt;
-          assert(reg.first()->is_valid() && !reg.second()->is_valid(), "");
-          new_in_regs[argcnt].set2(reg.first());
-          new_in_regs[argcnt+1].set_bad();
-          argcnt++;
-          break;
-        default:
-          // No conversion needed.
-          new_in_sig_bt[argcnt] = bt;
-          new_in_regs[argcnt]   = reg;
-          break;
-      }
-    }
-    assert(argcnt == i2l_argcnt, "must match");
-
-    in_regs = new_in_regs;
-    in_sig_bt = new_in_sig_bt;
-    in_args_count = i2l_argcnt;
-  } else {
-    assert(0, "This should not be needed on this platform");
-  }
-}
-
 // -------------------------------------------------------------------------
 // Java-Java calling convention
 // (what you use when Java calls Java)
--- a/hotspot/src/share/vm/runtime/sharedRuntime.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/sharedRuntime.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -145,6 +145,12 @@
   static double dsqrt(double f);
 #endif
 
+  // Montgomery multiplication
+  static void montgomery_multiply(jint *a_ints, jint *b_ints, jint *n_ints,
+                                  jint len, jlong inv, jint *m_ints);
+  static void montgomery_square(jint *a_ints, jint *n_ints,
+                                jint len, jlong inv, jint *m_ints);
+
 #ifdef __SOFTFP__
   // C++ compiler generates soft float instructions as well as passing
   // float and double in registers.
--- a/hotspot/src/share/vm/runtime/stubCodeGenerator.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/stubCodeGenerator.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 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
@@ -26,6 +26,7 @@
 #include "asm/macroAssembler.hpp"
 #include "asm/macroAssembler.inline.hpp"
 #include "code/codeCache.hpp"
+#include "code/codeCacheExtensions.hpp"
 #include "compiler/disassembler.hpp"
 #include "oops/oop.inline.hpp"
 #include "prims/forte.hpp"
--- a/hotspot/src/share/vm/runtime/stubCodeGenerator.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/stubCodeGenerator.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 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
@@ -67,14 +67,14 @@
   static StubCodeDesc* desc_for_index(int);      // returns the code descriptor for the index or NULL
   static const char*   name_for(address pc);     // returns the name of the code containing pc or NULL
 
-  StubCodeDesc(const char* group, const char* name, address begin) {
+  StubCodeDesc(const char* group, const char* name, address begin, address end = NULL) {
     assert(name != NULL, "no name specified");
     _next           = _list;
     _group          = group;
     _name           = name;
     _index          = ++_count; // (never zero)
     _begin          = begin;
-    _end            = NULL;
+    _end            = end;
     _list           = this;
   };
 
--- a/hotspot/src/share/vm/runtime/stubRoutines.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/stubRoutines.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -24,6 +24,7 @@
 
 #include "precompiled.hpp"
 #include "asm/codeBuffer.hpp"
+#include "code/codeCacheExtensions.hpp"
 #include "memory/resourceArea.hpp"
 #include "oops/oop.inline.hpp"
 #include "runtime/interfaceSupport.hpp"
@@ -142,6 +143,8 @@
 address StubRoutines::_multiplyToLen = NULL;
 address StubRoutines::_squareToLen = NULL;
 address StubRoutines::_mulAdd = NULL;
+address StubRoutines::_montgomeryMultiply = NULL;
+address StubRoutines::_montgomerySquare = NULL;
 
 double (* StubRoutines::_intrinsic_log   )(double) = NULL;
 double (* StubRoutines::_intrinsic_log10 )(double) = NULL;
@@ -188,6 +191,12 @@
 
 // simple tests of generated arraycopy functions
 static void test_arraycopy_func(address func, int alignment) {
+  if (CodeCacheExtensions::use_pregenerated_interpreter() || !CodeCacheExtensions::is_executable(func)) {
+    // Exit safely if stubs were generated but cannot be used.
+    // Also excluding pregenerated interpreter since the code may depend on
+    // some registers being properly initialized (for instance Rthread)
+    return;
+  }
   int v = 0xcc;
   int v2 = 0x11;
   jlong lbuffer[8];
--- a/hotspot/src/share/vm/runtime/stubRoutines.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/stubRoutines.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -202,6 +202,8 @@
   static address _multiplyToLen;
   static address _squareToLen;
   static address _mulAdd;
+  static address _montgomeryMultiply;
+  static address _montgomerySquare;
 
   // These are versions of the java.lang.Math methods which perform
   // the same operations as the intrinsic version.  They are used for
@@ -366,6 +368,8 @@
   static address multiplyToLen()       {return _multiplyToLen; }
   static address squareToLen()         {return _squareToLen; }
   static address mulAdd()              {return _mulAdd; }
+  static address montgomeryMultiply()  { return _montgomeryMultiply; }
+  static address montgomerySquare()    { return _montgomerySquare; }
 
   static address select_fill_function(BasicType t, bool aligned, const char* &name);
 
--- a/hotspot/src/share/vm/runtime/thread.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/thread.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -28,6 +28,7 @@
 #include "classfile/systemDictionary.hpp"
 #include "classfile/vmSymbols.hpp"
 #include "code/codeCache.hpp"
+#include "code/codeCacheExtensions.hpp"
 #include "code/scopeDesc.hpp"
 #include "compiler/compileBroker.hpp"
 #include "gc/shared/gcLocker.inline.hpp"
@@ -1291,7 +1292,7 @@
         if (!ShowMessageBoxOnError
             && (OnError == NULL || OnError[0] == '\0')
             && Arguments::abort_hook() == NULL) {
-          os::sleep(this, 2 * 60 * 1000, false);
+          os::sleep(this, ErrorLogTimeout * 60 * 1000, false);
           fdStream err(defaultStream::output_fd());
           err.print_raw_cr("# [ timer expired, abort... ]");
           // skip atexit/vm_exit/vm_abort hooks
@@ -3587,6 +3588,8 @@
     }
   }
 
+  CodeCacheExtensions::complete_step(CodeCacheExtensionsSteps::CreateVM);
+
   create_vm_timer.end();
 #ifdef ASSERT
   _vm_complete = true;
--- a/hotspot/src/share/vm/runtime/unhandledOops.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/unhandledOops.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -105,7 +105,7 @@
   _level --;
   if (unhandled_oop_print) {
     for (int i=0; i<_level; i++) tty->print(" ");
-    tty->print_cr("u "INTPTR_FORMAT, op);
+    tty->print_cr("u " INTPTR_FORMAT, op);
   }
 
   int i = _oop_list->find_from_end(op, match_oop_entry);
--- a/hotspot/src/share/vm/runtime/vmStructs.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/vmStructs.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -182,6 +182,8 @@
 #include "runtime/vmStructs_trace.hpp"
 #endif
 
+#include "runtime/vmStructs_ext.hpp"
+
 #ifdef COMPILER2
 #include "opto/addnode.hpp"
 #include "opto/block.hpp"
@@ -2963,6 +2965,9 @@
                 GENERATE_STATIC_VM_STRUCT_ENTRY)
 #endif
 
+  VM_STRUCTS_EXT(GENERATE_NONSTATIC_VM_STRUCT_ENTRY,
+                 GENERATE_STATIC_VM_STRUCT_ENTRY)
+
   VM_STRUCTS_CPU(GENERATE_NONSTATIC_VM_STRUCT_ENTRY,
                  GENERATE_STATIC_VM_STRUCT_ENTRY,
                  GENERATE_UNCHECKED_NONSTATIC_VM_STRUCT_ENTRY,
@@ -3013,6 +3018,9 @@
               GENERATE_TOPLEVEL_VM_TYPE_ENTRY)
 #endif
 
+  VM_TYPES_EXT(GENERATE_VM_TYPE_ENTRY,
+               GENERATE_TOPLEVEL_VM_TYPE_ENTRY)
+
   VM_TYPES_CPU(GENERATE_VM_TYPE_ENTRY,
                GENERATE_TOPLEVEL_VM_TYPE_ENTRY,
                GENERATE_OOP_VM_TYPE_ENTRY,
@@ -3122,6 +3130,9 @@
                 CHECK_STATIC_VM_STRUCT_ENTRY);
 #endif
 
+  VM_STRUCTS_EXT(CHECK_NONSTATIC_VM_STRUCT_ENTRY,
+                 CHECK_STATIC_VM_STRUCT_ENTRY);
+
   VM_STRUCTS_CPU(CHECK_NONSTATIC_VM_STRUCT_ENTRY,
                  CHECK_STATIC_VM_STRUCT_ENTRY,
                  CHECK_NO_OP,
@@ -3168,6 +3179,9 @@
               CHECK_SINGLE_ARG_VM_TYPE_NO_OP);
 #endif
 
+  VM_TYPES_EXT(CHECK_VM_TYPE_ENTRY,
+               CHECK_SINGLE_ARG_VM_TYPE_NO_OP);
+
   VM_TYPES_CPU(CHECK_VM_TYPE_ENTRY,
                CHECK_SINGLE_ARG_VM_TYPE_NO_OP,
                CHECK_SINGLE_ARG_VM_TYPE_NO_OP,
@@ -3236,6 +3250,9 @@
                            ENSURE_FIELD_TYPE_PRESENT));
 #endif
 
+  debug_only(VM_STRUCTS_EXT(ENSURE_FIELD_TYPE_PRESENT,
+                            ENSURE_FIELD_TYPE_PRESENT));
+
   debug_only(VM_STRUCTS_CPU(ENSURE_FIELD_TYPE_PRESENT,
                             ENSURE_FIELD_TYPE_PRESENT,
                             CHECK_NO_OP,
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/vm/runtime/vmStructs_ext.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,33 @@
+/*
+ * 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.
+ *
+ */
+
+#ifndef SHARE_VM_RUNTIME_VMSTRUCTS_EXT_HPP
+#define SHARE_VM_RUNTIME_VMSTRUCTS_EXT_HPP
+
+#define VM_STRUCTS_EXT(a, b)
+
+#define VM_TYPES_EXT(a, b)
+
+
+#endif // SHARE_VM_RUNTIME_VMSTRUCTS_EXT_HPP
--- a/hotspot/src/share/vm/runtime/vm_operations.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/vm_operations.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -26,6 +26,7 @@
 #include "classfile/symbolTable.hpp"
 #include "classfile/vmSymbols.hpp"
 #include "code/codeCache.hpp"
+#include "code/codeCacheExtensions.hpp"
 #include "compiler/compileBroker.hpp"
 #include "compiler/compilerOracle.hpp"
 #include "gc/shared/isGCActiveMark.hpp"
@@ -369,6 +370,8 @@
 Thread * VM_Exit::_shutdown_thread = NULL;
 
 int VM_Exit::set_vm_exited() {
+  CodeCacheExtensions::complete_step(CodeCacheExtensionsSteps::LastStep);
+
   Thread * thr_cur = ThreadLocalStorage::get_thread_slow();
 
   assert(SafepointSynchronize::is_at_safepoint(), "must be at safepoint already");
--- a/hotspot/src/share/vm/runtime/vm_version.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/runtime/vm_version.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -23,6 +23,7 @@
  */
 
 #include "precompiled.hpp"
+#include "code/codeCacheExtensions.hpp"
 #include "memory/universe.hpp"
 #include "oops/oop.inline.hpp"
 #include "runtime/arguments.hpp"
@@ -155,6 +156,9 @@
 
 
 const char* Abstract_VM_Version::vm_info_string() {
+  if (CodeCacheExtensions::use_pregenerated_interpreter()) {
+    return "interpreted mode, pregenerated";
+  }
   switch (Arguments::mode()) {
     case Arguments::_int:
       return UseSharedSpaces ? "interpreted mode, sharing" : "interpreted mode";
--- a/hotspot/src/share/vm/services/diagnosticArgument.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/services/diagnosticArgument.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -89,7 +89,7 @@
                                                   size_t len, TRAPS) {
   int scanned = -1;
   if (str == NULL
-      || sscanf(str, JLONG_FORMAT"%n", &_value, &scanned) != 1
+      || sscanf(str, JLONG_FORMAT "%n", &_value, &scanned) != 1
       || (size_t)scanned != len)
   {
     ResourceMark rm;
--- a/hotspot/src/share/vm/services/threadService.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/services/threadService.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -888,7 +888,7 @@
       st->print("  waiting to lock monitor " INTPTR_FORMAT, waitingToLockMonitor);
       oop obj = (oop)waitingToLockMonitor->object();
       if (obj != NULL) {
-        st->print(" (object "INTPTR_FORMAT ", a %s)", (address)obj,
+        st->print(" (object " INTPTR_FORMAT ", a %s)", (address)obj,
                    (InstanceKlass::cast(obj->klass()))->external_name());
 
         if (!currentThread->current_pending_monitor_is_from_java()) {
--- a/hotspot/src/share/vm/trace/trace.xml	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/trace/trace.xml	Wed Jul 05 20:42:36 2017 +0200
@@ -305,6 +305,13 @@
       <value type="G1YCTYPE" field="type" label="Type" />
     </event>
 
+    <event id="GCG1MMU" path="vm/gc/detailed/g1_mmu_info" label="G1 MMU Information" is_instant="true">
+      <value type="UINT" field="gcId" label="GC ID" relation="GC_ID"/>
+      <value type="DOUBLE" field="timeSlice" label="Time slice used to calculate MMU"/>
+      <value type="DOUBLE" field="gcTime" label="Time spent on GC during last time slice"/>
+      <value type="DOUBLE" field="maxGcTime" label="Max time allowed to be spent on GC during last time slice"/>
+    </event>
+
     <event id="EvacuationInfo" path="vm/gc/detailed/evacuation_info" label="Evacuation Information" is_instant="true">
       <value type="UINT" field="gcId" label="GC ID" relation="GC_ID"/>
       <value type="UINT" field="cSetRegions" label="Collection Set Regions"/>
--- a/hotspot/src/share/vm/trace/traceStream.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/trace/traceStream.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -40,31 +40,31 @@
   TraceStream(outputStream& stream): _st(stream) {}
 
   void print_val(const char* label, u1 val) {
-    _st.print("%s = "UINT32_FORMAT, label, val);
+    _st.print("%s = " UINT32_FORMAT, label, val);
   }
 
   void print_val(const char* label, u2 val) {
-    _st.print("%s = "UINT32_FORMAT, label, val);
+    _st.print("%s = " UINT32_FORMAT, label, val);
   }
 
   void print_val(const char* label, s2 val) {
-    _st.print("%s = "INT32_FORMAT, label, val);
+    _st.print("%s = " INT32_FORMAT, label, val);
   }
 
   void print_val(const char* label, u4 val) {
-    _st.print("%s = "UINT32_FORMAT, label, val);
+    _st.print("%s = " UINT32_FORMAT, label, val);
   }
 
   void print_val(const char* label, s4 val) {
-    _st.print("%s = "INT32_FORMAT, label, val);
+    _st.print("%s = " INT32_FORMAT, label, val);
   }
 
   void print_val(const char* label, u8 val) {
-    _st.print("%s = "UINT64_FORMAT, label, val);
+    _st.print("%s = " UINT64_FORMAT, label, val);
   }
 
   void print_val(const char* label, s8 val) {
-    _st.print("%s = "INT64_FORMAT, label, (int64_t) val);
+    _st.print("%s = " INT64_FORMAT, label, (int64_t) val);
   }
 
   void print_val(const char* label, bool val) {
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/vm/utilities/endian.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,97 @@
+/*
+ * 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.
+ *
+ */
+
+#include "precompiled.hpp"
+#include "utilities/endian.hpp"
+#include "utilities/bytes.hpp"
+
+#ifndef bswap_16
+extern "C" inline u2 bswap_16(u2 x) {
+  return ((x & 0xFF) << 8) |
+         ((x >> 8) & 0xFF);
+}
+#endif
+
+#ifndef bswap_32
+extern "C" inline u4 bswap_32(u4 x) {
+  return ((x & 0xFF) << 24) |
+       ((x & 0xFF00) << 8) |
+       ((x >> 8) & 0xFF00) |
+       ((x >> 24) & 0xFF);
+}
+#endif
+
+#ifndef bswap_64
+extern "C" inline u8 bswap_64(u8 x) {
+  return (u8)bswap_32((u4)x) << 32 |
+         (u8)bswap_32((u4)(x >> 32));
+}
+#endif
+
+u2 NativeEndian::get(u2 x) { return x; }
+u4 NativeEndian::get(u4 x) { return x; }
+u8 NativeEndian::get(u8 x) { return x; }
+s2 NativeEndian::get(s2 x) { return x; }
+s4 NativeEndian::get(s4 x) { return x; }
+s8 NativeEndian::get(s8 x) { return x; }
+
+void NativeEndian::set(u2& x, u2 y) { x = y; }
+void NativeEndian::set(u4& x, u4 y) { x = y; }
+void NativeEndian::set(u8& x, u8 y) { x = y; }
+void NativeEndian::set(s2& x, s2 y) { x = y; }
+void NativeEndian::set(s4& x, s4 y) { x = y; }
+void NativeEndian::set(s8& x, s8 y) { x = y; }
+
+NativeEndian NativeEndian::_native;
+
+u2 SwappingEndian::get(u2 x) { return bswap_16(x); }
+u4 SwappingEndian::get(u4 x) { return bswap_32(x); }
+u8 SwappingEndian::get(u8 x) { return bswap_64(x); }
+s2 SwappingEndian::get(s2 x) { return bswap_16(x); }
+s4 SwappingEndian::get(s4 x) { return bswap_32(x); }
+s8 SwappingEndian::get(s8 x) { return bswap_64(x); }
+
+void SwappingEndian::set(u2& x, u2 y) { x = bswap_16(y); }
+void SwappingEndian::set(u4& x, u4 y) { x = bswap_32(y); }
+void SwappingEndian::set(u8& x, u8 y) { x = bswap_64(y); }
+void SwappingEndian::set(s2& x, s2 y) { x = bswap_16(y); }
+void SwappingEndian::set(s4& x, s4 y) { x = bswap_32(y); }
+void SwappingEndian::set(s8& x, s8 y) { x = bswap_64(y); }
+
+SwappingEndian SwappingEndian::_swapping;
+
+Endian* Endian::get_handler(bool big_endian) {
+  // If requesting little endian on a little endian machine or
+  // big endian on a big endian machine use native handler
+  if (big_endian == is_big_endian()) {
+    return NativeEndian::get_native();
+  } else {
+    // Use swapping handler.
+    return SwappingEndian::get_swapping();
+  }
+}
+
+Endian* Endian::get_native_handler() {
+  return NativeEndian::get_native();
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/vm/utilities/endian.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,119 @@
+/*
+ * 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.
+ *
+ */
+
+#ifndef SHARE_VM_UTILITIES_ENDIAN_HPP
+#define SHARE_VM_UTILITIES_ENDIAN_HPP
+
+#include "utilities/globalDefinitions.hpp"
+
+// Selectable endian handling. Endian handlers are used when accessing values
+// that are of unknown (until runtime) endian.  The only requirement of the values
+// accessed are that they are aligned to proper size boundaries (no misalignment.)
+// To select an endian handler, one should call Endian::get_handler(big_endian);
+// Where big_endian is true if big endian is required and false otherwise.  The
+// native endian handler can be fetched with Endian::get_native_handler();
+// To retrieve a value using the approprate endian, use one of the overloaded
+// calls to get. To set a value, then use one of the overloaded set calls.
+// Ex.
+//      s4 value; // Imported value;
+//      ...
+//      Endian* endian = Endian::get_handler(true);  // Use big endian
+//      s4 corrected = endian->get(value);
+//      endian->set(value, 1);
+//
+class Endian {
+public:
+  virtual u2 get(u2 x) = 0;
+  virtual u4 get(u4 x) = 0;
+  virtual u8 get(u8 x) = 0;
+  virtual s2 get(s2 x) = 0;
+  virtual s4 get(s4 x) = 0;
+  virtual s8 get(s8 x) = 0;
+
+  virtual void set(u2& x, u2 y) = 0;
+  virtual void set(u4& x, u4 y) = 0;
+  virtual void set(u8& x, u8 y) = 0;
+  virtual void set(s2& x, s2 y) = 0;
+  virtual void set(s4& x, s4 y) = 0;
+  virtual void set(s8& x, s8 y) = 0;
+
+  // Quick little endian test.
+  static bool is_little_endian() {  u4 x = 1; return *(u1 *)&x != 0; }
+
+  // Quick big endian test.
+  static bool is_big_endian() { return !is_little_endian(); }
+
+  // Select an appropriate endian handler.
+  static Endian* get_handler(bool big_endian);
+
+  // Return the native endian handler.
+  static Endian* get_native_handler();
+};
+
+// Normal endian handling.
+class NativeEndian : public Endian {
+private:
+  static NativeEndian _native;
+
+public:
+  u2 get(u2 x);
+  u4 get(u4 x);
+  u8 get(u8 x);
+  s2 get(s2 x);
+  s4 get(s4 x);
+  s8 get(s8 x);
+
+  void set(u2& x, u2 y);
+  void set(u4& x, u4 y);
+  void set(u8& x, u8 y);
+  void set(s2& x, s2 y);
+  void set(s4& x, s4 y);
+  void set(s8& x, s8 y);
+
+  static Endian* get_native() { return &_native; }
+};
+
+// Swapping endian handling.
+class SwappingEndian : public Endian {
+private:
+  static SwappingEndian _swapping;
+
+public:
+  u2 get(u2 x);
+  u4 get(u4 x);
+  u8 get(u8 x);
+  s2 get(s2 x);
+  s4 get(s4 x);
+  s8 get(s8 x);
+
+  void set(u2& x, u2 y);
+  void set(u4& x, u4 y);
+  void set(u8& x, u8 y);
+  void set(s2& x, s2 y);
+  void set(s4& x, s4 y);
+  void set(s8& x, s8 y);
+
+  static Endian* get_swapping() { return &_swapping; }
+};
+#endif // SHARE_VM_UTILITIES_ENDIAN_HPP
--- a/hotspot/src/share/vm/utilities/globalDefinitions.hpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/utilities/globalDefinitions.hpp	Wed Jul 05 20:42:36 2017 +0200
@@ -1367,6 +1367,7 @@
 #define UINT32_FORMAT_W(width) "%" #width PRIu32
 
 #define PTR32_FORMAT           "0x%08" PRIx32
+#define PTR32_FORMAT_W(width)  "0x%" #width PRIx32
 
 // Format 64-bit quantities.
 #define INT64_FORMAT           "%" PRId64
--- a/hotspot/src/share/vm/utilities/ostream.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/utilities/ostream.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -274,7 +274,7 @@
   size_t limit = (len + 16) / 16 * 16;
   for (size_t i = 0; i < limit; ++i) {
     if (i % 16 == 0) {
-      indent().print(INTPTR_FORMAT_W(07)":", i);
+      indent().print(INTPTR_FORMAT_W(07) ":", i);
     }
     if (i % 2 == 0) {
       print(" ");
@@ -946,7 +946,7 @@
     // %%% Should be: jlong time_ms = os::start_time_milliseconds(), if
     // we ever get round to introduce that method on the os class
     xs->head("hotspot_log version='%d %d'"
-             " process='%d' time_ms='"INT64_FORMAT"'",
+             " process='%d' time_ms='" INT64_FORMAT "'",
              LOG_MAJOR_VERSION, LOG_MINOR_VERSION,
              os::current_process_id(), (int64_t)time_ms);
     // Write VM version header immediately.
--- a/hotspot/src/share/vm/utilities/vmError.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/src/share/vm/utilities/vmError.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -411,9 +411,10 @@
            }
            st->cr();
          } else {
-           if (_message != NULL)
+           if (_message != NULL) {
              st->print("# ");
              st->print_cr("%s", _message);
+           }
          }
          // In error file give some solutions
          if (_verbose) {
--- a/hotspot/test/TEST.groups	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/test/TEST.groups	Wed Jul 05 20:42:36 2017 +0200
@@ -241,7 +241,7 @@
   gc/arguments/TestParallelGCThreads.java \
   gc/arguments/TestUseCompressedOopsErgo.java \
   gc/class_unloading/TestG1ClassUnloadingHWM.java \
-  gc/ergonomics/TestDynamicNumberOfGCThreads.java
+  gc/ergonomics/TestDynamicNumberOfGCThreads.java \
   gc/g1/ \
   gc/metaspace/G1AddMetaspaceDependency.java \
   gc/metaspace/TestMetaspacePerfCounters.java \
--- a/hotspot/test/compiler/dependencies/MonomorphicObjectCall/TestMonomorphicObjectCall.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/test/compiler/dependencies/MonomorphicObjectCall/TestMonomorphicObjectCall.java	Wed Jul 05 20:42:36 2017 +0200
@@ -34,6 +34,7 @@
  * @library /testlibrary
  * @modules java.base/sun.misc
  *          java.management
+ *          java.base/jdk.internal
  * @compile -XDignore.symbol.file java/lang/Object.java TestMonomorphicObjectCall.java
  * @run main TestMonomorphicObjectCall
  */
--- a/hotspot/test/compiler/dependencies/MonomorphicObjectCall/java/lang/Object.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/test/compiler/dependencies/MonomorphicObjectCall/java/lang/Object.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,25 +25,33 @@
 
 package java.lang;
 
+import jdk.internal.HotSpotIntrinsicCandidate;
+
 /**
  * Slightly modified version of java.lang.Object that replaces
  * finalize() by finalizeObject() to avoid overriding in subclasses.
  */
 public class Object {
 
+    @HotSpotIntrinsicCandidate
+    public Object() {}
+
     private static native void registerNatives();
     static {
         registerNatives();
     }
 
+    @HotSpotIntrinsicCandidate
     public final native Class<?> getClass();
 
+    @HotSpotIntrinsicCandidate
     public native int hashCode();
 
     public boolean equals(Object obj) {
         return (this == obj);
     }
 
+    @HotSpotIntrinsicCandidate
     protected native Object clone() throws CloneNotSupportedException;
 
     public String toString() {
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/compiler/intrinsics/montgomerymultiply/MontgomeryMultiplyTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,277 @@
+//
+// Copyright (c) 2000, 2015, Oracle and/or its affiliates. All rights reserved.
+// Copyright (c) 2015, Red Hat Inc. 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.lang.invoke.MethodHandle;
+import java.lang.invoke.MethodHandles;
+import java.lang.invoke.MethodType;
+import java.lang.reflect.Constructor;
+import java.lang.reflect.Field;
+import java.lang.reflect.Method;
+import java.math.BigInteger;
+import java.util.Arrays;
+import java.util.Random;
+
+/**
+ * @test
+ * @bug 8130150
+ * @library /testlibrary
+ * @summary Verify that the Montgomery multiply intrinsic works and correctly checks its arguments.
+ */
+
+public class MontgomeryMultiplyTest {
+
+    static final MethodHandles.Lookup lookup = MethodHandles.lookup();
+
+    static final MethodHandle montgomeryMultiplyHandle, montgomerySquareHandle;
+    static final MethodHandle bigIntegerConstructorHandle;
+    static final Field bigIntegerMagField;
+
+    static {
+       // Use reflection to gain access to the methods we want to test.
+        try {
+            Method m = BigInteger.class.getDeclaredMethod("montgomeryMultiply",
+                /*a*/int[].class, /*b*/int[].class, /*n*/int[].class, /*len*/int.class,
+                /*inv*/long.class, /*product*/int[].class);
+            m.setAccessible(true);
+            montgomeryMultiplyHandle = lookup.unreflect(m);
+
+            m = BigInteger.class.getDeclaredMethod("montgomerySquare",
+                /*a*/int[].class, /*n*/int[].class, /*len*/int.class,
+                /*inv*/long.class, /*product*/int[].class);
+            m.setAccessible(true);
+            montgomerySquareHandle = lookup.unreflect(m);
+
+            Constructor c
+                = BigInteger.class.getDeclaredConstructor(int.class, int[].class);
+            c.setAccessible(true);
+            bigIntegerConstructorHandle = lookup.unreflectConstructor(c);
+
+            bigIntegerMagField = BigInteger.class.getDeclaredField("mag");
+            bigIntegerMagField.setAccessible(true);
+
+        } catch (Throwable ex) {
+            throw new RuntimeException(ex);
+        }
+    }
+
+    // Invoke either BigInteger.montgomeryMultiply or BigInteger.montgomerySquare.
+    int[] montgomeryMultiply(int[] a, int[] b, int[] n, int len, long inv,
+                             int[] product) throws Throwable {
+        int[] result =
+            (a == b) ? (int[]) montgomerySquareHandle.invokeExact(a, n, len, inv, product)
+                     : (int[]) montgomeryMultiplyHandle.invokeExact(a, b, n, len, inv, product);
+        return Arrays.copyOf(result, len);
+    }
+
+    // Invoke the private constructor BigInteger(int[]).
+    BigInteger newBigInteger(int[] val) throws Throwable {
+        return (BigInteger) bigIntegerConstructorHandle.invokeExact(1, val);
+    }
+
+    // Get the private field BigInteger.mag
+    int[] mag(BigInteger n) {
+        try {
+            return (int[]) bigIntegerMagField.get(n);
+        } catch (Exception ex) {
+            throw new RuntimeException(ex);
+        }
+    }
+
+    // Montgomery multiplication
+    // Calculate a * b * r^-1 mod n)
+    //
+    // R is a power of the word size
+    // N' = R^-1 mod N
+    //
+    // T := ab
+    // m := (T mod R)N' mod R [so 0 <= m < R]
+    // t := (T + mN)/R
+    // if t >= N then return t - N else return t
+    //
+    BigInteger montgomeryMultiply(BigInteger a, BigInteger b, BigInteger N,
+            int len, BigInteger n_prime)
+            throws Throwable {
+        BigInteger T = a.multiply(b);
+        BigInteger R = BigInteger.ONE.shiftLeft(len*32);
+        BigInteger mask = R.subtract(BigInteger.ONE);
+        BigInteger m = (T.and(mask)).multiply(n_prime);
+        m = m.and(mask); // i.e. m.mod(R)
+        T = T.add(m.multiply(N));
+        T = T.shiftRight(len*32); // i.e. T.divide(R)
+        if (T.compareTo(N) > 0) {
+            T = T.subtract(N);
+        }
+        return T;
+    }
+
+    // Call the Montgomery multiply intrinsic.
+    BigInteger montgomeryMultiply(int[] a_words, int[] b_words, int[] n_words,
+            int len, BigInteger inv)
+            throws Throwable {
+        BigInteger t = montgomeryMultiply(
+                newBigInteger(a_words),
+                newBigInteger(b_words),
+                newBigInteger(n_words),
+                len, inv);
+        return t;
+    }
+
+    // Check that the Montgomery multiply intrinsic returns the same
+    // result as the longhand calculation.
+    void check(int[] a_words, int[] b_words, int[] n_words, int len, BigInteger inv)
+            throws Throwable {
+        BigInteger n = newBigInteger(n_words);
+        BigInteger slow = montgomeryMultiply(a_words, b_words, n_words, len, inv);
+        BigInteger fast
+            = newBigInteger(montgomeryMultiply
+                            (a_words, b_words, n_words, len, inv.longValue(), null));
+        // The intrinsic may not return the same value as the longhand
+        // calculation but they must have the same residue mod N.
+        if (!slow.mod(n).equals(fast.mod(n))) {
+            throw new RuntimeException();
+        }
+    }
+
+    Random rnd = new Random(0);
+
+    // Return a random value of length <= bits in an array of even length
+    int[] random_val(int bits) {
+        int len = (bits+63)/64;  // i.e. length in longs
+        int[] val = new int[len*2];
+        for (int i = 0; i < val.length; i++)
+            val[i] = rnd.nextInt();
+        int leadingZeros = 64 - (bits & 64);
+        if (leadingZeros >= 32) {
+            val[0] = 0;
+            val[1] &= ~(-1l << (leadingZeros & 31));
+        } else {
+            val[0] &= ~(-1l << leadingZeros);
+        }
+        return val;
+    }
+
+    void testOneLength(int lenInBits, int lenInInts) throws Throwable {
+        BigInteger mod = new BigInteger(lenInBits, 2, rnd);
+        BigInteger r = BigInteger.ONE.shiftLeft(lenInInts * 32);
+        BigInteger n_prime = mod.modInverse(r).negate();
+
+        // Make n.length even, padding with a zero if necessary
+        int[] n = mag(mod);
+        if (n.length < lenInInts) {
+            int[] x = new int[lenInInts];
+            System.arraycopy(n, 0, x, lenInInts-n.length, n.length);
+            n = x;
+        }
+
+        for (int i = 0; i < 10000; i++) {
+            // multiply
+            check(random_val(lenInBits), random_val(lenInBits), n, lenInInts, n_prime);
+            // square
+            int[] tmp = random_val(lenInBits);
+            check(tmp, tmp, n, lenInInts, n_prime);
+        }
+    }
+
+    // Test the Montgomery multiply intrinsic with a bunch of random
+    // values of varying lengths.  Do this for long enough that the
+    // caller of the intrinsic is C2-compiled.
+    void testResultValues() throws Throwable {
+        // Test a couple of interesting edge cases.
+        testOneLength(1024, 32);
+        testOneLength(1025, 34);
+        for (int j = 10; j > 0; j--) {
+            // Construct a random prime whose length in words is even
+            int lenInBits = rnd.nextInt(2048) + 64;
+            int lenInInts = (lenInBits + 63)/64*2;
+            testOneLength(lenInBits, lenInInts);
+        }
+    }
+
+    // Range checks
+    void testOneMontgomeryMultiplyCheck(int[] a, int[] b, int[] n, int len, long inv,
+                                        int[] product, Class klass) {
+        try {
+            montgomeryMultiply(a, b, n, len, inv, product);
+        } catch (Throwable ex) {
+            if (klass.isAssignableFrom(ex.getClass()))
+                return;
+            throw new RuntimeException(klass + " expected, " + ex + " was thrown");
+        }
+        throw new RuntimeException(klass + " expected, was not thrown");
+    }
+
+    void testOneMontgomeryMultiplyCheck(int[] a, int[] b, BigInteger n, int len, BigInteger inv,
+            Class klass) {
+        testOneMontgomeryMultiplyCheck(a, b, mag(n), len, inv.longValue(), null, klass);
+    }
+
+    void testOneMontgomeryMultiplyCheck(int[] a, int[] b, BigInteger n, int len, BigInteger inv,
+            int[] product, Class klass) {
+        testOneMontgomeryMultiplyCheck(a, b, mag(n), len, inv.longValue(), product, klass);
+    }
+
+    void testMontgomeryMultiplyChecks() {
+        int[] blah = random_val(40);
+        int[] small = random_val(39);
+        BigInteger mod = new BigInteger(40*32 , 2, rnd);
+        BigInteger r = BigInteger.ONE.shiftLeft(40*32);
+        BigInteger n_prime = mod.modInverse(r).negate();
+
+        // Length out of range: square
+        testOneMontgomeryMultiplyCheck(blah, blah, mod, 41, n_prime, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(blah, blah, mod, 0, n_prime, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(blah, blah, mod, -1, n_prime, IllegalArgumentException.class);
+        // As above, but for multiply
+        testOneMontgomeryMultiplyCheck(blah, blah.clone(), mod, 41, n_prime, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(blah, blah.clone(), mod, 0, n_prime, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(blah, blah.clone(), mod, 0, n_prime, IllegalArgumentException.class);
+
+        // Length odd
+        testOneMontgomeryMultiplyCheck(small, small, mod, 39, n_prime, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(small, small, mod, 0, n_prime, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(small, small, mod, -1, n_prime, IllegalArgumentException.class);
+        // As above, but for multiply
+        testOneMontgomeryMultiplyCheck(small, small.clone(), mod, 39, n_prime, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(small, small.clone(), mod, 0, n_prime, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(small, small.clone(), mod, -1, n_prime, IllegalArgumentException.class);
+
+        // array too small
+        testOneMontgomeryMultiplyCheck(blah, blah, mod, 40, n_prime, small, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(blah, blah.clone(), mod, 40, n_prime, small, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(small, blah, mod, 40, n_prime, blah, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(blah, small, mod, 40, n_prime, blah, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(blah, blah, mod, 40, n_prime, small, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(small, small, mod, 40, n_prime, blah, IllegalArgumentException.class);
+    }
+
+    public static void main(String args[]) {
+        try {
+            new MontgomeryMultiplyTest().testMontgomeryMultiplyChecks();
+            new MontgomeryMultiplyTest().testResultValues();
+        } catch (Throwable ex) {
+            throw new RuntimeException(ex);
+        }
+     }
+}
--- a/hotspot/test/compiler/intrinsics/sha/cli/SHAOptionsBase.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/sha/cli/SHAOptionsBase.java	Wed Jul 05 20:42:36 2017 +0200
@@ -47,16 +47,12 @@
     // expressions, not just a plain strings.
     protected static final String SHA_INSTRUCTIONS_ARE_NOT_AVAILABLE
             = "SHA instructions are not available on this CPU";
-    protected static final String SHA1_INSTRUCTION_IS_NOT_AVAILABLE
-            = "SHA1 instruction is not available on this CPU\\.";
-    protected static final String SHA256_INSTRUCTION_IS_NOT_AVAILABLE
-            = "SHA256 instruction \\(for SHA-224 and SHA-256\\) "
-            + "is not available on this CPU\\.";
-    protected static final String SHA512_INSTRUCTION_IS_NOT_AVAILABLE
-            = "SHA512 instruction \\(for SHA-384 and SHA-512\\) "
-            + "is not available on this CPU\\.";
-    protected static final String SHA_INTRINSICS_ARE_NOT_AVAILABLE
-            = "SHA intrinsics are not available on this CPU";
+    protected static final String SHA1_INTRINSICS_ARE_NOT_AVAILABLE
+            = "Intrinsics for SHA-1 crypto hash functions not available on this CPU.";
+    protected static final String SHA256_INTRINSICS_ARE_NOT_AVAILABLE
+            = "Intrinsics for SHA-224 and SHA-256 crypto hash functions not available on this CPU.";
+    protected static final String SHA512_INTRINSICS_ARE_NOT_AVAILABLE
+            = "Intrinsics for SHA-384 and SHA-512 crypto hash functions not available on this CPU.";
 
     private final TestCase[] testCases;
 
@@ -71,33 +67,23 @@
      *         instructions required by the option are not supported.
      */
     protected static String getWarningForUnsupportedCPU(String optionName) {
-        if (Platform.isSparc() || Platform.isAArch64()) {
+        if (Platform.isSparc() || Platform.isAArch64() ||
+            Platform.isX64() || Platform.isX86()) {
             switch (optionName) {
-                case SHAOptionsBase.USE_SHA_OPTION:
-                    return SHAOptionsBase.SHA_INSTRUCTIONS_ARE_NOT_AVAILABLE;
-                case SHAOptionsBase.USE_SHA1_INTRINSICS_OPTION:
-                    return SHAOptionsBase.SHA1_INSTRUCTION_IS_NOT_AVAILABLE;
-                case SHAOptionsBase.USE_SHA256_INTRINSICS_OPTION:
-                    return SHAOptionsBase.SHA256_INSTRUCTION_IS_NOT_AVAILABLE;
-                case SHAOptionsBase.USE_SHA512_INTRINSICS_OPTION:
-                    return SHAOptionsBase.SHA512_INSTRUCTION_IS_NOT_AVAILABLE;
-                default:
-                    throw new Error("Unexpected option " + optionName);
-            }
-        } else if (Platform.isX64() || Platform.isX86()) {
-            switch (optionName) {
-                case SHAOptionsBase.USE_SHA_OPTION:
-                    return SHAOptionsBase.SHA_INSTRUCTIONS_ARE_NOT_AVAILABLE;
-                case SHAOptionsBase.USE_SHA1_INTRINSICS_OPTION:
-                case SHAOptionsBase.USE_SHA256_INTRINSICS_OPTION:
-                case SHAOptionsBase.USE_SHA512_INTRINSICS_OPTION:
-                    return SHAOptionsBase.SHA_INTRINSICS_ARE_NOT_AVAILABLE;
-                default:
-                    throw new Error("Unexpected option " + optionName);
+            case SHAOptionsBase.USE_SHA_OPTION:
+                return SHAOptionsBase.SHA_INSTRUCTIONS_ARE_NOT_AVAILABLE;
+            case SHAOptionsBase.USE_SHA1_INTRINSICS_OPTION:
+                return SHAOptionsBase.SHA1_INTRINSICS_ARE_NOT_AVAILABLE;
+            case SHAOptionsBase.USE_SHA256_INTRINSICS_OPTION:
+                return SHAOptionsBase.SHA256_INTRINSICS_ARE_NOT_AVAILABLE;
+            case SHAOptionsBase.USE_SHA512_INTRINSICS_OPTION:
+                return SHAOptionsBase.SHA512_INTRINSICS_ARE_NOT_AVAILABLE;
+            default:
+                throw new Error("Unexpected option " + optionName);
             }
         } else {
-            throw new Error("Support for CPUs other then X86 or SPARC is not "
-                    + "implemented.");
+            throw new Error("Support for CPUs different fromn X86, SPARC, and AARCH64 "
+                            + "is not implemented");
         }
     }
 
--- a/hotspot/test/compiler/intrinsics/sha/cli/testcases/GenericTestCaseForSupportedCPU.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/sha/cli/testcases/GenericTestCaseForSupportedCPU.java	Wed Jul 05 20:42:36 2017 +0200
@@ -64,18 +64,20 @@
                         SHAOptionsBase.USE_SHA_OPTION, true),
                 CommandLineOptionTest.prepareBooleanFlag(optionName, false));
 
-        // Verify that it is possible to enable the tested option and disable
-        // all SHA intrinsics via -UseSHA without any warnings.
-        CommandLineOptionTest.verifySameJVMStartup(null, new String[] {
-                        SHAOptionsBase.getWarningForUnsupportedCPU(optionName)
-                }, shouldPassMessage, String.format("It should be able to "
-                        + "enable option '%s' even if %s was passed to JVM",
-                        optionName, CommandLineOptionTest.prepareBooleanFlag(
-                            SHAOptionsBase.USE_SHA_OPTION, false)),
-                ExitCode.OK,
-                CommandLineOptionTest.prepareBooleanFlag(
-                        SHAOptionsBase.USE_SHA_OPTION, false),
-                CommandLineOptionTest.prepareBooleanFlag(optionName, true));
+        if (!optionName.equals(SHAOptionsBase.USE_SHA_OPTION)) {
+            // Verify that if -XX:-UseSHA is passed to the JVM, it is not possible
+            // to enable the tested option and a warning is printed.
+            CommandLineOptionTest.verifySameJVMStartup(
+                    new String[] { SHAOptionsBase.getWarningForUnsupportedCPU(optionName) },
+                    null,
+                    shouldPassMessage,
+                    String.format("Enabling option '%s' should not be possible and should result in a warning if %s was passed to JVM",
+                                  optionName,
+                                  CommandLineOptionTest.prepareBooleanFlag(SHAOptionsBase.USE_SHA_OPTION, false)),
+                    ExitCode.OK,
+                    CommandLineOptionTest.prepareBooleanFlag(SHAOptionsBase.USE_SHA_OPTION, false),
+                    CommandLineOptionTest.prepareBooleanFlag(optionName, true));
+        }
     }
 
     @Override
--- a/hotspot/test/compiler/intrinsics/sha/cli/testcases/GenericTestCaseForUnsupportedAArch64CPU.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/sha/cli/testcases/GenericTestCaseForUnsupportedAArch64CPU.java	Wed Jul 05 20:42:36 2017 +0200
@@ -49,14 +49,22 @@
                 }, shouldPassMessage, shouldPassMessage, ExitCode.OK,
                 CommandLineOptionTest.prepareBooleanFlag(optionName, false));
 
-        shouldPassMessage = String.format("JVM should start with '-XX:+"
-                + "%s' flag, but output should contain warning.", optionName);
-        // Verify that when the tested option is explicitly enabled, then
-        // a warning will occur in VM output.
-        CommandLineOptionTest.verifySameJVMStartup(new String[] {
-                        SHAOptionsBase.getWarningForUnsupportedCPU(optionName)
-                }, null, shouldPassMessage, shouldPassMessage, ExitCode.OK,
-                CommandLineOptionTest.prepareBooleanFlag(optionName, true));
+        shouldPassMessage = String.format("If JVM is started with '-XX:-"
+                + "%s' '-XX:+%s', output should contain warning.",
+                SHAOptionsBase.USE_SHA_OPTION, optionName);
+
+        // Verify that when the tested option is enabled, then
+        // a warning will occur in VM output if UseSHA is disabled.
+        if (!optionName.equals(SHAOptionsBase.USE_SHA_OPTION)) {
+            CommandLineOptionTest.verifySameJVMStartup(
+                    new String[] { SHAOptionsBase.getWarningForUnsupportedCPU(optionName) },
+                    null,
+                    shouldPassMessage,
+                    shouldPassMessage,
+                    ExitCode.OK,
+                    CommandLineOptionTest.prepareBooleanFlag(SHAOptionsBase.USE_SHA_OPTION, false),
+                    CommandLineOptionTest.prepareBooleanFlag(optionName, true));
+        }
     }
 
     @Override
--- a/hotspot/test/compiler/intrinsics/sha/cli/testcases/GenericTestCaseForUnsupportedSparcCPU.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/sha/cli/testcases/GenericTestCaseForUnsupportedSparcCPU.java	Wed Jul 05 20:42:36 2017 +0200
@@ -48,6 +48,19 @@
                         SHAOptionsBase.getWarningForUnsupportedCPU(optionName)
                 }, shouldPassMessage, shouldPassMessage, ExitCode.OK,
                 CommandLineOptionTest.prepareBooleanFlag(optionName, false));
+
+        // Verify that when the tested option is enabled, then
+        // a warning will occur in VM output if UseSHA is disabled.
+        if (!optionName.equals(SHAOptionsBase.USE_SHA_OPTION)) {
+            CommandLineOptionTest.verifySameJVMStartup(
+                    new String[] { SHAOptionsBase.getWarningForUnsupportedCPU(optionName) },
+                    null,
+                    shouldPassMessage,
+                    shouldPassMessage,
+                    ExitCode.OK,
+                    CommandLineOptionTest.prepareBooleanFlag(SHAOptionsBase.USE_SHA_OPTION, false),
+                    CommandLineOptionTest.prepareBooleanFlag(optionName, true));
+        }
     }
 
     @Override
--- a/hotspot/test/gc/g1/TestShrinkDefragmentedHeap.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/test/gc/g1/TestShrinkDefragmentedHeap.java	Wed Jul 05 20:42:36 2017 +0200
@@ -23,7 +23,7 @@
 
 /**
  * @test TestShrinkDefragmentedHeap
- * @bug 8038423
+ * @bug 8038423 8129590
  * @summary Verify that heap shrinks after GC in the presence of fragmentation due to humongous objects
  *     1. allocate small objects mixed with humongous ones
  *        "ssssHssssHssssHssssHssssHssssHssssH"
@@ -51,12 +51,14 @@
     // To avoid this the Eden needs to be big enough to fit all the small objects.
     private static final int INITIAL_HEAP_SIZE  = 200 * 1024 * 1024;
     private static final int MINIMAL_YOUNG_SIZE = 190 * 1024 * 1024;
+    private static final int MAXIMUM_HEAP_SIZE  = 256 * 1024 * 1024;
     private static final int REGION_SIZE        = 1 * 1024 * 1024;
 
     public static void main(String[] args) throws Exception, Throwable {
         ProcessBuilder pb = ProcessTools.createJavaProcessBuilder(
                 "-XX:InitialHeapSize=" + INITIAL_HEAP_SIZE,
                 "-Xmn" + MINIMAL_YOUNG_SIZE,
+                "-Xmx" + MAXIMUM_HEAP_SIZE,
                 "-XX:MinHeapFreeRatio=10",
                 "-XX:MaxHeapFreeRatio=11",
                 "-XX:+UseG1GC",
--- a/hotspot/test/gc/g1/TestSummarizeRSetStats.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/test/gc/g1/TestSummarizeRSetStats.java	Wed Jul 05 20:42:36 2017 +0200
@@ -23,7 +23,7 @@
 
 /*
  * @test TestSummarizeRSetStats.java
- * @bug 8013895
+ * @bug 8013895 8129977
  * @library /testlibrary
  * @modules java.base/sun.misc
  *          java.management/sun.management
--- a/hotspot/test/gc/g1/TestSummarizeRSetStatsPerRegion.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/test/gc/g1/TestSummarizeRSetStatsPerRegion.java	Wed Jul 05 20:42:36 2017 +0200
@@ -23,7 +23,7 @@
 
 /*
  * @test TestSummarizeRSetStatsPerRegion.java
- * @bug 8014078
+ * @bug 8014078 8129977
  * @library /testlibrary
  * @modules java.base/sun.misc
  *          java.management/sun.management
--- a/hotspot/test/gc/g1/TestSummarizeRSetStatsTools.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/test/gc/g1/TestSummarizeRSetStatsTools.java	Wed Jul 05 20:42:36 2017 +0200
@@ -87,6 +87,7 @@
         String[] defaultArgs = new String[] {
             "-XX:+UseG1GC",
             "-Xmn4m",
+            "-Xms20m",
             "-Xmx20m",
             "-XX:InitiatingHeapOccupancyPercent=100", // we don't want the additional GCs due to initial marking
             "-XX:+PrintGC",
--- a/hotspot/test/gc/survivorAlignment/TestPromotionFromSurvivorToTenuredAfterMinorGC.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/test/gc/survivorAlignment/TestPromotionFromSurvivorToTenuredAfterMinorGC.java	Wed Jul 05 20:42:36 2017 +0200
@@ -28,6 +28,7 @@
  *          when their age exceeded tenuring threshold are not aligned to
  *          SurvivorAlignmentInBytes value.
  * @library /testlibrary /../../test/lib
+ * @ignore 8130308
  * @modules java.base/sun.misc
  *          java.management
  * @build TestPromotionFromSurvivorToTenuredAfterMinorGC
--- a/hotspot/test/gc/survivorAlignment/TestPromotionToSurvivor.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/test/gc/survivorAlignment/TestPromotionToSurvivor.java	Wed Jul 05 20:42:36 2017 +0200
@@ -31,6 +31,7 @@
  *          java.management
  * @build TestPromotionToSurvivor
  *        SurvivorAlignmentTestMain AlignmentHelper
+ * @ignore 8129886
  * @run main ClassFileInstaller sun.hotspot.WhiteBox
  *                              sun.hotspot.WhiteBox$WhiteBoxPermission
  * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions
--- a/hotspot/test/runtime/CommandLine/OptionsValidation/common/optionsvalidation/DoubleJVMOption.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/test/runtime/CommandLine/OptionsValidation/common/optionsvalidation/DoubleJVMOption.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,6 +25,7 @@
 
 import java.util.ArrayList;
 import java.util.List;
+import java.util.Locale;
 
 public class DoubleJVMOption extends JVMOption {
 
@@ -109,7 +110,7 @@
     }
 
     private String formatValue(double value) {
-        return String.format("%f", value);
+        return String.format(Locale.US, "%f", value);
     }
 
     /**
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/runtime/CommandLine/TestLongUnrecognizedVMOption.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,48 @@
+/*
+ * 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.
+ */
+
+/*
+ * @test
+ * @bug 8129786
+ * @summary Verify that JVM correctly processes very long unrecognized VM option
+ * @library /testlibrary
+ * @modules java.management
+ * @run main TestLongUnrecognizedVMOption
+ */
+
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
+
+public class TestLongUnrecognizedVMOption {
+
+    /* Create option with very long length(greater than 500 characters) */
+    private static final String VERY_LONG_OPTION = String.format("%500s=10", "unrecognizedoption").replace(" ", "a");
+
+    public static void main(String[] args) throws Exception {
+        OutputAnalyzer output;
+
+        output = new OutputAnalyzer(ProcessTools.createJavaProcessBuilder("-XX:" + VERY_LONG_OPTION, "-version").start());
+        output.shouldHaveExitValue(1);
+        output.shouldContain(String.format("Unrecognized VM option '%s'", VERY_LONG_OPTION));
+    }
+}
--- a/hotspot/test/runtime/Metaspace/FragmentMetaspaceSimple.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/test/runtime/Metaspace/FragmentMetaspaceSimple.java	Wed Jul 05 20:42:36 2017 +0200
@@ -23,12 +23,15 @@
 
 /**
  * @test
- * @library /runtime/testlibrary
  * @library classes
- * @build test.Empty ClassUnloadCommon
+ * @build test.Empty
  * @run main/othervm/timeout=200 FragmentMetaspaceSimple
  */
 
+import java.io.DataInputStream;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.IOException;
 import java.util.ArrayList;
 
 /**
@@ -47,8 +50,14 @@
     private static void runSimple(long time) {
         long startTime = System.currentTimeMillis();
         ArrayList<ClassLoader> cls = new ArrayList<>();
-        for (int i = 0; System.currentTimeMillis() < startTime + time; ++i) {
-            ClassLoader ldr = ClassUnloadCommon.newClassLoader();
+        char sep = File.separatorChar;
+        String fileName = "classes" + sep + "test" + sep + "Empty.class";
+        File file = new File(System.getProperty("test.classes",".") + sep + fileName);
+        byte buff[] = read(file);
+
+        int i = 0;
+        for (i = 0; System.currentTimeMillis() < startTime + time; ++i) {
+            ClassLoader ldr = new MyClassLoader(buff);
             if (i % 1000 == 0) {
                 cls.clear();
             }
@@ -59,11 +68,43 @@
             Class<?> c = null;
             try {
                 c = ldr.loadClass("test.Empty");
+                c.getClass().getClassLoader(); // make sure we have a valid class.
             } catch (ClassNotFoundException ex) {
+                System.out.println("i=" + i + ", len" + buff.length);
                 throw new RuntimeException(ex);
             }
             c = null;
         }
         cls = null;
+        System.out.println("Finished " + i + " iterations in " +
+                           (System.currentTimeMillis() - startTime) + " ms");
+    }
+
+    private static byte[] read(File file) {
+        byte buff[] = new byte[(int)(file.length())];
+        try {
+            DataInputStream din = new DataInputStream(new FileInputStream(file));
+            din.readFully(buff);
+            din.close();
+        } catch (IOException ex) {
+            throw new RuntimeException(ex);
+        }
+        return buff;
+    }
+
+    static class MyClassLoader extends ClassLoader {
+        byte buff[];
+        MyClassLoader(byte buff[]) {
+            this.buff = buff;
+        }
+
+        public Class<?> loadClass() throws ClassNotFoundException {
+            String name = "test.Empty";
+            try {
+                return defineClass(name, buff, 0, buff.length);
+            } catch (Throwable e) {
+                throw new ClassNotFoundException(name, e);
+            }
+        }
     }
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/runtime/modules/ImageFile/ImageAttributeOffsetsTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,64 @@
+/*
+ * 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.
+ */
+
+/*
+ * Retrieves the array of offsets once with MemoryMapImage enabled once disabled.
+ * @test ImageAttributeOffsetsTest
+ * @summary Unit test for JVM_ImageAttributeOffsets() method
+ * @library /testlibrary /../../test/lib
+ * @build ImageAttributeOffsetsTest
+ * @run main ClassFileInstaller sun.hotspot.WhiteBox
+ *                              sun.hotspot.WhiteBox$WhiteBoxPermission
+ * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI -XX:+MemoryMapImage ImageAttributeOffsetsTest
+ * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI -XX:-MemoryMapImage ImageAttributeOffsetsTest
+ */
+
+import java.io.File;
+import java.nio.ByteOrder;
+import sun.hotspot.WhiteBox;
+import static jdk.test.lib.Asserts.*;
+
+public class ImageAttributeOffsetsTest {
+
+    public static final WhiteBox wb = WhiteBox.getWhiteBox();
+
+    public static void main(String... args) throws Exception {
+        String javaHome = System.getProperty("java.home");
+        String imageFile = javaHome + File.separator + "lib" + File.separator
+                + "modules" + File.separator + "bootmodules.jimage";
+
+        if (!(new File(imageFile)).exists()) {
+            System.out.printf("Test skipped.");
+            return;
+        }
+
+        boolean bigEndian = ByteOrder.nativeOrder() == ByteOrder.BIG_ENDIAN;
+        long id = wb.imageOpenImage(imageFile, bigEndian);
+        boolean passed = true;
+        // Get offsets
+        int[] array = wb.imageAttributeOffsets(id);
+        assertNotNull(array, "Could not retrieve offsets of array");
+
+        wb.imageCloseImage(id);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/runtime/modules/ImageFile/ImageCloseTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,68 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * 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 closing image opened multiple time. Test closing mutiple time an image.
+ * @test ImageCloseTest
+ * @summary Unit test for JVM_ImageClose() method
+ * @library /testlibrary /../../test/lib
+ * @build ImageCloseTest
+ * @run main ClassFileInstaller sun.hotspot.WhiteBox
+ *                              sun.hotspot.WhiteBox$WhiteBoxPermission
+ * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI ImageCloseTest
+ */
+
+import java.io.File;
+import java.nio.ByteOrder;
+import sun.hotspot.WhiteBox;
+
+public class ImageCloseTest {
+
+    public static final WhiteBox wb = WhiteBox.getWhiteBox();
+
+    public static void main(String... args) throws Exception {
+        String javaHome = System.getProperty("java.home");
+        String imageFile = javaHome + File.separator + "lib" + File.separator
+                + "modules" + File.separator + "bootmodules.jimage";
+
+        if (!(new File(imageFile)).exists()) {
+            System.out.printf("Test skipped.");
+            return;
+        }
+
+        boolean bigEndian = ByteOrder.nativeOrder() == ByteOrder.BIG_ENDIAN;
+        long id = 0;
+
+        // too many opens
+        for (int i = 0; i < 100; i++) {
+            id = wb.imageOpenImage(imageFile, bigEndian);
+        }
+        wb.imageCloseImage(id);
+
+        // too many closes
+        id = wb.imageOpenImage(imageFile, bigEndian);
+        for (int i = 0; i < 100; i++) {
+            wb.imageCloseImage(id);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/runtime/modules/ImageFile/ImageFileHeaderTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,126 @@
+/*
+ * 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.
+ */
+
+/*
+ * Test that opening image containing wrong headers fails.
+ * @test ImageFileHeaderTest
+ * @library /testlibrary /../../test/lib
+ * @build ImageFileHeaderTest
+ * @run main ClassFileInstaller sun.hotspot.WhiteBox
+ *                              sun.hotspot.WhiteBox$WhiteBoxPermission
+ * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI ImageFileHeaderTest
+ */
+
+import java.nio.*;
+import java.nio.file.Files;
+import java.nio.file.Paths;
+import sun.hotspot.WhiteBox;
+import static jdk.test.lib.Asserts.*;
+
+public class ImageFileHeaderTest {
+
+    public static final int MAGIC = 0xCAFEDADA;
+    public static final short MAJOR = 0;
+    public static final short MINOR = 1;
+
+    public static final WhiteBox wb = WhiteBox.getWhiteBox();
+    public static ByteBuffer buf;
+
+    public static void main(String... args) throws Exception {
+
+        ByteOrder endian = getEndian();
+
+        // Try to read a non-existing file
+        assertFalse(wb.readImageFile("bogus"));
+
+        // Incomplete header, only include the correct magic
+        buf = ByteBuffer.allocate(100);
+        buf.order(endian);
+        buf.putInt(MAGIC);
+        assertFalse(testImageFile("invalidheader.jimage"));
+
+        // Build a complete header but reverse the endian
+        buf = ByteBuffer.allocate(100);
+        buf.order(endian == ByteOrder.LITTLE_ENDIAN ? ByteOrder.BIG_ENDIAN : ByteOrder.LITTLE_ENDIAN);
+        buf.putInt(MAGIC);
+        buf.putShort(MAJOR);
+        buf.putShort(MINOR);
+        assertFalse(testImageFile("wrongendian.jimage"));
+
+        // Use the wrong magic
+        buf = ByteBuffer.allocate(100);
+        buf.order(endian);
+        buf.putInt(0xBEEFCACE);
+        buf.putShort(MAJOR);
+        buf.putShort(MINOR);
+        assertFalse(testImageFile("wrongmagic.jimage"));
+
+        // Wrong major version (current + 1)
+        buf = ByteBuffer.allocate(100);
+        buf.order(endian);
+        buf.putInt(MAGIC);
+        buf.putShort((short)(MAJOR + 1));
+        buf.putShort((short)MINOR);
+        assertFalse(testImageFile("wrongmajorversion.jimage"));
+
+        // Wrong major version (negative)
+        buf = ByteBuffer.allocate(100);
+        buf.order(endian);
+        buf.putInt(MAGIC);
+        buf.putShort((short) -17);
+        buf.putShort((short)MINOR);
+        assertFalse(testImageFile("negativemajorversion.jimage"));
+
+        // Wrong minor version (current + 1)
+        buf = ByteBuffer.allocate(100);
+        buf.order(endian);
+        buf.putInt(MAGIC);
+        buf.putShort((short)MAJOR);
+        buf.putShort((short)(MINOR + 1));
+        assertFalse(testImageFile("wrongminorversion.jimage"));
+
+        // Wrong minor version (negative)
+        buf = ByteBuffer.allocate(100);
+        buf.order(endian);
+        buf.putInt(MAGIC);
+        buf.putShort((short)MAJOR);
+        buf.putShort((short) -17);
+        assertFalse(testImageFile("negativeminorversion.jimage"));
+    }
+
+    public static boolean testImageFile(String filename) throws Exception {
+        Files.write(Paths.get(filename), buf.array());
+        System.out.println("Calling ReadImageFile on " + filename);
+        return wb.readImageFile(filename);
+    }
+
+    public static ByteOrder getEndian() {
+        String endian = System.getProperty("sun.cpu.endian");
+        if (endian.equalsIgnoreCase("little")) {
+            return ByteOrder.LITTLE_ENDIAN;
+        } else if (endian.equalsIgnoreCase("big")) {
+            return ByteOrder.BIG_ENDIAN;
+        }
+        throw new RuntimeException("Unexpected sun.cpu.endian value: " + endian);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/runtime/modules/ImageFile/ImageFindAttributesTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,75 @@
+/*
+ * 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.
+ */
+
+/*
+ * Find the attributes of existing and invalid classes.
+ * @test ImageFindAttributesTest
+ * @summary Unit test for JVM_ImageFindAttributes() method
+ * @library /testlibrary /../../test/lib
+ * @build ImageFindAttributesTest
+ * @run main ClassFileInstaller sun.hotspot.WhiteBox
+ *                              sun.hotspot.WhiteBox$WhiteBoxPermission
+ * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI ImageFindAttributesTest
+ */
+
+import java.io.File;
+import java.nio.ByteOrder;
+import sun.hotspot.WhiteBox;
+import static jdk.test.lib.Asserts.*;
+
+public class ImageFindAttributesTest {
+
+    public static final WhiteBox wb = WhiteBox.getWhiteBox();
+
+    public static void main(String... args) throws Exception {
+        String javaHome = System.getProperty("java.home");
+        String imageFile = javaHome + File.separator + "lib" + File.separator
+                + "modules" + File.separator + "bootmodules.jimage";
+
+        if (!(new File(imageFile)).exists()) {
+            System.out.printf("Test skipped.");
+            return;
+        }
+
+        boolean bigEndian = ByteOrder.nativeOrder() == ByteOrder.BIG_ENDIAN;
+        long id = wb.imageOpenImage(imageFile, bigEndian);
+
+        // class resource
+        String className = "/java.base/java/lang/String.class";
+        long[] longArr = wb.imageFindAttributes(id, className.getBytes());
+
+        assertNotNull(longArr, "Could not retrieve attributes of class " + className);
+
+        // non-existent resource
+        String neClassName = "/java.base/java/lang/NonExistentClass.class";
+        longArr = wb.imageFindAttributes(id, neClassName.getBytes());
+
+        assertNull(longArr, "Failed. Returned not null for non-existent " + neClassName);
+
+        // garbage byte array
+        byte[] buf = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9};
+        longArr = wb.imageFindAttributes(id, buf);
+
+        assertNull(longArr, "Found attributes for garbage class");
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/runtime/modules/ImageFile/ImageGetAttributesTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,128 @@
+/*
+ * 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.
+ */
+
+/*
+ * Test getting all attributes,
+ * @test ImageGetAttributesTest
+ * @summary Unit test for JVM_ImageGetAttributes() method
+ * @library /testlibrary /../../test/lib
+ * @build LocationConstants ImageGetAttributesTest
+ * @run main ClassFileInstaller sun.hotspot.WhiteBox
+ *                              sun.hotspot.WhiteBox$WhiteBoxPermission
+ * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI ImageGetAttributesTest
+ */
+
+import java.io.File;
+import java.nio.ByteOrder;
+import sun.hotspot.WhiteBox;
+import static jdk.test.lib.Asserts.*;
+
+public class ImageGetAttributesTest implements LocationConstants {
+
+    public static final WhiteBox wb = WhiteBox.getWhiteBox();
+
+    public static void main(String... args) throws Exception {
+        String javaHome = System.getProperty("java.home");
+        String imageFile = javaHome + File.separator + "lib" + File.separator
+                + "modules" + File.separator + "bootmodules.jimage";
+
+        if (!(new File(imageFile)).exists()) {
+            System.out.printf("Test skipped.");
+            return;
+        }
+
+        testImageGetAttributes(imageFile);
+    }
+
+    private static void testImageGetAttributes(String imageFile) {
+
+        boolean bigEndian = ByteOrder.nativeOrder() == ByteOrder.BIG_ENDIAN;
+        long id = wb.imageOpenImage(imageFile, bigEndian);
+        try {
+            long stringsSize = wb.imageGetStringsSize(id);
+            assertNE(stringsSize, 0, "strings size is 0");
+
+            int[] array = wb.imageAttributeOffsets(id);
+            assertNotNull(array, "Could not retrieve offsets of array");
+
+            // Get non-null attributes
+            boolean attFound = false;
+            int[] idx = {-1, -1, -1};
+            // first non-null attribute
+            for (int i = 0; i < array.length; i++) {
+                if (array[i] != 0) {
+                    attFound = true;
+                    idx[0] = i;
+                    break;
+                }
+            }
+
+            // middle non-null attribute
+            for (int i = array.length / 2; i < array.length; i++) {
+                if (array[i] != 0) {
+                    attFound = true;
+                    idx[1] = i;
+                    break;
+                }
+            }
+
+            // last non-null attribute
+            for (int i = array.length - 1; i >= 0; i--) {
+                if (array[i] != 0) {
+                    attFound = true;
+                    idx[2] = i;
+                    break;
+                }
+            }
+            assertTrue(attFound, "Failed. No non-null offset attributes");
+                // test cases above
+                for (int i = 0; i < 3; i++) {
+                    if (idx[i] != -1) {
+                        long[] attrs = wb.imageGetAttributes(id, (int) array[idx[i]]);
+                        long module = attrs[LOCATION_ATTRIBUTE_MODULE];
+                        long parent = attrs[LOCATION_ATTRIBUTE_PARENT];
+                        long base = attrs[LOCATION_ATTRIBUTE_BASE];
+                        long ext = attrs[LOCATION_ATTRIBUTE_EXTENSION];
+
+                        if ((module >= 0) && (module < stringsSize)
+                                && (parent >= 0) && (parent < stringsSize)
+                                && (base != 0)
+                                && (ext >= 0) && (ext < stringsSize)) {
+                        } else {
+                            System.out.printf("Failed. Read attribute offset %d (position %d) but wrong offsets\n",
+                                    array[idx[i]], idx[i]);
+                            System.out.printf("    offsets: module = %d parent = %d base = %d extention = %d\n",
+                                    module, parent, base, ext);
+                            throw new RuntimeException("Read attribute offset error");
+                        }
+                    } else {
+                        System.out.printf("Failed. Could not read attribute offset %d (position %d)\n",
+                                array[idx[i]], idx[i]);
+                        throw new RuntimeException("Read attribute offset error");
+                    }
+                }
+        } finally {
+            wb.imageCloseImage(id);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/runtime/modules/ImageFile/ImageGetDataAddressTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,71 @@
+/*
+ * 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.
+ */
+
+/*
+ * Test accessing the data address of a jimage. This only makes sense when the
+ * entire jimage is mapped into memory.
+ * @test ImageGetDataAddressTest
+ * @summary Unit test for JVM_ImageGetDataAddress() method
+ * @library /testlibrary /../../test/lib
+ * @build ImageGetDataAddressTest
+ * @run main ClassFileInstaller sun.hotspot.WhiteBox
+ *                              sun.hotspot.WhiteBox$WhiteBoxPermission
+ * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI -XX:+MemoryMapImage ImageGetDataAddressTest +
+ * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI -XX:-MemoryMapImage ImageGetDataAddressTest -
+ */
+
+import java.io.File;
+import java.nio.ByteOrder;
+import sun.hotspot.WhiteBox;
+import static jdk.test.lib.Asserts.*;
+
+public class ImageGetDataAddressTest {
+
+    public static final WhiteBox wb = WhiteBox.getWhiteBox();
+
+    public static void main(String... args) throws Exception {
+        String javaHome = System.getProperty("java.home");
+        String imageFile = javaHome + File.separator + "lib" + File.separator
+                + "modules" + File.separator + "bootmodules.jimage";
+
+        if (!(new File(imageFile)).exists()) {
+            System.out.printf("Test skipped.");
+            return;
+        }
+
+        boolean isMMap = args[0].equals("+");
+
+        boolean bigEndian = ByteOrder.nativeOrder() == ByteOrder.BIG_ENDIAN;
+        long id = wb.imageOpenImage(imageFile, bigEndian);
+
+        // get data for valid id
+        long dataAddr = wb.imageGetDataAddress(id);
+        assertFalse((dataAddr == 0) && isMMap, "Failed. Data address is " + dataAddr + " for valid id\n");
+
+        // get data for invalid id == 0
+        dataAddr = wb.imageGetDataAddress(0);
+        assertTrue(dataAddr == 0, "Failed. Data address is " + dataAddr + " for zero id\n");
+
+        wb.imageCloseImage(id);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/runtime/modules/ImageFile/ImageGetIndexAddressTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,67 @@
+/*
+ * 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.
+ */
+
+/*
+ * Test the address of the jimage index.
+ * @test ImageGetIndexAddressTest
+ * @summary Unit test for JVM_ImageGetIndexAddress() method
+ * @library /testlibrary /../../test/lib
+ * @build ImageGetIndexAddressTest
+ * @run main ClassFileInstaller sun.hotspot.WhiteBox
+ *                              sun.hotspot.WhiteBox$WhiteBoxPermission
+ * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI ImageGetIndexAddressTest
+ */
+
+import java.io.File;
+import java.nio.ByteOrder;
+import sun.hotspot.WhiteBox;
+import static jdk.test.lib.Asserts.*;
+
+public class ImageGetIndexAddressTest {
+
+    public static final WhiteBox wb = WhiteBox.getWhiteBox();
+
+    public static void main(String... args) throws Exception {
+        String javaHome = System.getProperty("java.home");
+        String imageFile = javaHome + File.separator + "lib" + File.separator
+                + "modules" + File.separator + "bootmodules.jimage";
+
+        if (!(new File(imageFile)).exists()) {
+            System.out.printf("Test skipped.");
+            return;
+        }
+
+        boolean bigEndian = ByteOrder.nativeOrder() == ByteOrder.BIG_ENDIAN;
+        long id = wb.imageOpenImage(imageFile, bigEndian);
+
+        // get index for valid id
+        long indexAddr = wb.imageGetIndexAddress(id);
+        assertFalse(indexAddr == 0, "Failed. Index address is zero for valid id");
+
+        // get index for invalid id == 0
+        indexAddr = wb.imageGetIndexAddress(0);
+        assertTrue(indexAddr == 0, "Failed. Index address is" + indexAddr + " for zero id\n");
+
+        wb.imageCloseImage(id);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/runtime/modules/ImageFile/ImageGetStringBytesTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,79 @@
+/*
+ * 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.
+ */
+
+/*
+ * Test that the string referenced by an attribute is retrieved.
+ * @test ImageGetStringBytesTest
+ * @summary Unit test for JVM_ImageGetStringBytes() method
+ * @library /testlibrary /../../test/lib
+ * @build LocationConstants ImageGetStringBytesTest
+ * @run main ClassFileInstaller sun.hotspot.WhiteBox
+ *                              sun.hotspot.WhiteBox$WhiteBoxPermission
+ * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI ImageGetStringBytesTest
+ */
+
+import java.io.File;
+import java.nio.ByteOrder;
+import sun.hotspot.WhiteBox;
+import static jdk.test.lib.Asserts.*;
+
+public class ImageGetStringBytesTest implements LocationConstants {
+
+    public static final WhiteBox wb = WhiteBox.getWhiteBox();
+
+    public static void main(String... args) throws Exception {
+        String javaHome = System.getProperty("java.home");
+        String imageFile = javaHome + File.separator + "lib" + File.separator
+                + "modules" + File.separator + "bootmodules.jimage";
+
+        if (!(new File(imageFile)).exists()) {
+            System.out.printf("Test skipped.");
+            return;
+        }
+
+        boolean bigEndian = ByteOrder.nativeOrder() == ByteOrder.BIG_ENDIAN;
+        long id = wb.imageOpenImage(imageFile, bigEndian);
+
+        String className = "/java.base/java/lang/String.class";
+        long[] offsetArr = wb.imageFindAttributes(id, className.getBytes());
+
+        // Module
+        assertTrue(checkAttribute(id, offsetArr, LOCATION_ATTRIBUTE_MODULE, "Module"));
+
+        // Parent
+        assertTrue(checkAttribute(id, offsetArr, LOCATION_ATTRIBUTE_PARENT, "Parent"));
+
+        // Base
+        assertTrue(checkAttribute(id, offsetArr, LOCATION_ATTRIBUTE_BASE, "Base"));
+
+        // Extension
+        assertTrue(checkAttribute(id, offsetArr, LOCATION_ATTRIBUTE_EXTENSION, "Extension"));
+
+        wb.imageCloseImage(id);
+    }
+
+    private static boolean checkAttribute(long id, long[] offsetArr, int attrId, String attrName) {
+        long offset = offsetArr[attrId];
+        return wb.imageGetStringBytes(id, (int) offset) != null;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/runtime/modules/ImageFile/ImageOpenTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,84 @@
+/*
+ * 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.
+ */
+
+/*
+ * Test image opening/closing
+ * @test ImageOpenTest
+ * @summary Unit test for JVM_ImageOpen() method
+ * @library /testlibrary /../../test/lib
+ * @build ImageOpenTest
+ * @run main ClassFileInstaller sun.hotspot.WhiteBox
+ *                              sun.hotspot.WhiteBox$WhiteBoxPermission
+ * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI ImageOpenTest
+ */
+
+import java.io.File;
+import java.nio.ByteOrder;
+import sun.hotspot.WhiteBox;
+import static jdk.test.lib.Asserts.*;
+
+public class ImageOpenTest {
+
+    public static final WhiteBox wb = WhiteBox.getWhiteBox();
+
+    public static void main(String... args) throws Exception {
+        String javaHome = System.getProperty("java.home");
+        String nonexistentImageFile = javaHome + "/lib/modules/nonexistent.jimage";
+        String bootmodulesImageFile = javaHome + File.separator + "lib" + File.separator
+                + "modules" + File.separator + "bootmodules.jimage";
+
+        if (!(new File(bootmodulesImageFile)).exists()) {
+            System.out.printf("Test skipped.");
+            return;
+        }
+
+        boolean bigEndian = ByteOrder.nativeOrder() == ByteOrder.BIG_ENDIAN;
+
+        // open nonexistent image
+        long id = wb.imageOpenImage(nonexistentImageFile, bigEndian);
+        assertTrue(id == 0L, "Failed. Get id " + id + "instead of 0 on opening nonexistent file\n");
+        wb.imageCloseImage(id);
+
+        // open bootmodules image
+        id = wb.imageOpenImage(bootmodulesImageFile, bigEndian);
+        assertFalse(id == 0, "Failed. Get id 0 on opening bootmodules.jimage");
+        wb.imageCloseImage(id);
+
+        // non-native endian
+        id = wb.imageOpenImage(bootmodulesImageFile, !bigEndian);
+        assertFalse(id == 0, "Failed. Get id 0 on opening bootmodules.jimage with non-native endian");
+        wb.imageCloseImage(id);
+
+        //
+        // open several times
+        //
+        id = wb.imageOpenImage(bootmodulesImageFile, bigEndian);
+        long id1 = wb.imageOpenImage(bootmodulesImageFile, bigEndian);
+        long id2 = wb.imageOpenImage(bootmodulesImageFile, bigEndian);
+        assertTrue((id == id1) && (id == id2), "Failed. Open thee times with ids " + id + " " + id1 + " " + id1);
+
+        wb.imageCloseImage(id);
+        wb.imageCloseImage(id1);
+        wb.imageCloseImage(id2);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/runtime/modules/ImageFile/ImageReadTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,97 @@
+/*
+ * 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.
+ */
+
+/*
+ * Test reading resource content.
+ * @test ImageReadTest
+ * @summary Unit test for JVM_ImageRead() method
+ * @library /testlibrary /../../test/lib
+ * @build LocationConstants ImageReadTest
+ * @run main ClassFileInstaller sun.hotspot.WhiteBox
+ *                              sun.hotspot.WhiteBox$WhiteBoxPermission
+ * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI -XX:+MemoryMapImage ImageReadTest +
+ * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI -XX:-MemoryMapImage ImageReadTest -
+ */
+
+import java.io.File;
+import java.nio.ByteBuffer;
+import sun.hotspot.WhiteBox;
+import static jdk.test.lib.Asserts.*;
+
+public class ImageReadTest implements LocationConstants {
+
+    public static final WhiteBox wb = WhiteBox.getWhiteBox();
+
+    public static void main(String... args) throws Exception {
+        String javaHome = System.getProperty("java.home");
+        String imageFile = javaHome + File.separator + "lib"
+                + File.separator + "modules" + File.separator
+                + "bootmodules.jimage";
+
+        if (!(new File(imageFile)).exists()) {
+            System.out.printf("Test skipped.");
+            return;
+        }
+
+        boolean isMMap = args[0].equals("+");
+
+        long id = wb.imageOpenImage(imageFile, isMMap);
+
+        final String mm = isMMap ? "-XX:+MemoryMapImage" : "-XX:-MemoryMapImage";
+        final int magic = 0xCAFEBABE;
+
+        String className = "/java.base/java/lang/String.class";
+        long[] offsetArr = wb.imageFindAttributes(id, className.getBytes());
+        long offset = offsetArr[LOCATION_ATTRIBUTE_OFFSET];
+        long size = offsetArr[LOCATION_ATTRIBUTE_UNCOMPRESSED];
+
+        // positive: read
+        ByteBuffer buf = ByteBuffer.allocateDirect((int) size);
+        assertTrue(wb.imageRead(id, offset, buf, size), "Failed. Read operation returned false, should be true");
+        int m = buf.getInt();
+        assertTrue(m == magic, "Failed. Read operation returned true but wrong magic = " + magic);
+
+        // positive: mmap
+        if (isMMap) {
+            long dataAddr = wb.imageGetDataAddress(id);
+            assertFalse(dataAddr == 0L, "Failed. Did not obtain data address on mmapped test");
+            int data = wb.imageGetIntAtAddress(dataAddr, (int) offset, true);
+            assertTrue(data == magic, "Failed. MMap operation returned true but wrong magic = " + data);
+        }
+
+        // negative: wrong offset
+        boolean success = wb.imageRead(id, -100, buf, size);
+        assertFalse(success, "Failed. Read operation (wrong offset): returned true");
+
+        // negative: too big offset
+        long filesize = new File(imageFile).length();
+        success = wb.imageRead(id, filesize + 1, buf, size);
+        assertFalse(success, "Failed. Read operation (offset > file size) returned true");
+
+        // negative: negative size
+        success = wb.imageRead(id, offset, buf, -100);
+        assertFalse(success, "Failed. Read operation (negative size) returned true");
+
+        wb.imageCloseImage(id);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/runtime/modules/ImageFile/LocationConstants.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,36 @@
+/*
+ * 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.
+ */
+
+public interface LocationConstants {
+    // keep this in sync with enum in ImageLocation C++ class in the
+    // hotspot's C++ header file imageFile.hpp
+    public static final int LOCATION_ATTRIBUTE_END = 0;          // End of attribute stream marker
+    public static final int LOCATION_ATTRIBUTE_MODULE = 1;       // String table offset of module name
+    public static final int LOCATION_ATTRIBUTE_PARENT = 2;       // String table offset of resource path parent
+    public static final int LOCATION_ATTRIBUTE_BASE = 3;         // String table offset of resource path base
+    public static final int LOCATION_ATTRIBUTE_EXTENSION = 4;    // String table offset of resource path extension
+    public static final int LOCATION_ATTRIBUTE_OFFSET = 5;       // Container byte offset of resource
+    public static final int LOCATION_ATTRIBUTE_COMPRESSED = 6;   // In image byte size of the compressed resource
+    public static final int LOCATION_ATTRIBUTE_UNCOMPRESSED = 7; // In memory byte size of the uncompressed resource
+    public static final int LOCATION_ATTRIBUTE_COUNT = 8;        // Number of attribute kinds
+}
--- a/hotspot/test/testlibrary/ctw/Makefile	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/test/testlibrary/ctw/Makefile	Wed Jul 05 20:42:36 2017 +0200
@@ -8,7 +8,7 @@
 #
 # 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
+# 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).
 #
--- a/hotspot/test/testlibrary/ctw/README	Thu Jul 16 19:31:01 2015 -0700
+++ b/hotspot/test/testlibrary/ctw/README	Wed Jul 05 20:42:36 2017 +0200
@@ -1,26 +1,26 @@
-#
-# Copyright (c) 2013, 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.
-#
-#
+
+Copyright (c) 2013, 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.
+
+
 
 DESCRIPTION
 
--- a/jaxp/.hgtags	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxp/.hgtags	Wed Jul 05 20:42:36 2017 +0200
@@ -315,3 +315,4 @@
 42180703e0a362c1de7cdbf61d2cbc6609e678c4 jdk9-b70
 a3200b88f259f904876b9ab13fd4c4ec2726f8ba jdk9-b71
 81e85f3b6174314155991048767452a9931e12e2 jdk9-b72
+be5efc34a43bdd982d1cbe11cb2f6d6a060dde60 jdk9-b73
--- a/jaxws/.hgtags	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/.hgtags	Wed Jul 05 20:42:36 2017 +0200
@@ -318,3 +318,4 @@
 94084caa27a3c8a09a7510aef596ebd64e97c569 jdk9-b70
 61caeb7061bbf8cc74a767997e5d17cc00712629 jdk9-b71
 1d87054e2d2f405c114f0061b97cbf8214bddf0a jdk9-b72
+285939df908721cdb2b18a119638114306b8dca7 jdk9-b73
--- a/jaxws/src/java.annotations.common/share/classes/javax/annotation/PostConstruct.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.annotations.common/share/classes/javax/annotation/PostConstruct.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -39,6 +39,7 @@
  * method can be annotated with this annotation. The method on which the
  * PostConstruct annotation is applied MUST fulfill all of the following
  * criteria:
+ * <p>
  * <ul>
  * <li>The method MUST NOT have any parameters except in the case of
  * interceptors in which case it takes an InvocationContext object as
--- a/jaxws/src/java.annotations.common/share/classes/javax/annotation/PreDestroy.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.annotations.common/share/classes/javax/annotation/PreDestroy.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -38,6 +38,7 @@
  * except the application client container in Java EE 5. The method on which
  * the PreDestroy annotation is applied MUST fulfill all of the following
  * criteria:
+ * <p>
  * <ul>
  * <li>The method MUST NOT have any parameters except in the case of
  * interceptors in which case it takes an InvocationContext object as
--- a/jaxws/src/java.xml.bind/share/classes/javax/xml/bind/DatatypeConverterImpl.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.bind/share/classes/javax/xml/bind/DatatypeConverterImpl.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2007, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2007, 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
@@ -124,7 +124,7 @@
     }
 
     public static long _parseLong(CharSequence s) {
-        return Long.valueOf(removeOptionalPlus(WhiteSpaceProcessor.trim(s)).toString());
+        return Long.parseLong(removeOptionalPlus(WhiteSpaceProcessor.trim(s)).toString());
     }
 
     public short parseShort(String lexicalXSDShort) {
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/AttachmentPart.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/AttachmentPart.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/Detail.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/Detail.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -30,43 +30,43 @@
 import javax.xml.namespace.QName;
 
 /**
- * A container for <code>DetailEntry</code> objects. <code>DetailEntry</code>
+ * A container for {@code DetailEntry} objects. {@code DetailEntry}
  * objects give detailed error information that is application-specific and
- * related to the <code>SOAPBody</code> object that contains it.
+ * related to the {@code SOAPBody} object that contains it.
  *<P>
- * A <code>Detail</code> object, which is part of a <code>SOAPFault</code>
- * object, can be retrieved using the method <code>SOAPFault.getDetail</code>.
- * The <code>Detail</code> interface provides two methods. One creates a new
- * <code>DetailEntry</code> object and also automatically adds it to
- * the <code>Detail</code> object. The second method gets a list of the
- * <code>DetailEntry</code> objects contained in a <code>Detail</code>
+ * A {@code Detail} object, which is part of a {@code SOAPFault}
+ * object, can be retrieved using the method {@code SOAPFault.getDetail}.
+ * The {@code Detail} interface provides two methods. One creates a new
+ * {@code DetailEntry} object and also automatically adds it to
+ * the {@code Detail} object. The second method gets a list of the
+ * {@code DetailEntry} objects contained in a {@code Detail}
  * object.
  * <P>
- * The following code fragment, in which <i>sf</i> is a <code>SOAPFault</code>
- * object, gets its <code>Detail</code> object (<i>d</i>), adds a new
- * <code>DetailEntry</code> object to <i>d</i>, and then gets a list of all the
- * <code>DetailEntry</code> objects in <i>d</i>. The code also creates a
- * <code>Name</code> object to pass to the method <code>addDetailEntry</code>.
- * The variable <i>se</i>, used to create the <code>Name</code> object,
- * is a <code>SOAPEnvelope</code> object.
- * <PRE>
+ * The following code fragment, in which <i>sf</i> is a {@code SOAPFault}
+ * object, gets its {@code Detail} object (<i>d</i>), adds a new
+ * {@code DetailEntry} object to <i>d</i>, and then gets a list of all the
+ * {@code DetailEntry} objects in <i>d</i>. The code also creates a
+ * {@code Name} object to pass to the method {@code addDetailEntry}.
+ * The variable <i>se</i>, used to create the {@code Name} object,
+ * is a {@code SOAPEnvelope} object.
+ * <pre>{@code
  *    Detail d = sf.getDetail();
  *    Name name = se.createName("GetLastTradePrice", "WOMBAT",
  *                                "http://www.wombat.org/trader");
  *    d.addDetailEntry(name);
  *    Iterator it = d.getDetailEntries();
- * </PRE>
+ * }</pre>
  *
  * @since 1.6
  */
 public interface Detail extends SOAPFaultElement {
 
     /**
-     * Creates a new <code>DetailEntry</code> object with the given
-     * name and adds it to this <code>Detail</code> object.
+     * Creates a new {@code DetailEntry} object with the given
+     * name and adds it to this {@code Detail} object.
      *
-     * @param name a <code>Name</code> object identifying the
-     *         new <code>DetailEntry</code> object
+     * @param name a {@code Name} object identifying the
+     *         new {@code DetailEntry} object
      *
      * @exception SOAPException thrown when there is a problem in adding a
      * DetailEntry object to this Detail object.
@@ -76,12 +76,12 @@
     public DetailEntry addDetailEntry(Name name) throws SOAPException;
 
     /**
-     * Creates a new <code>DetailEntry</code> object with the given
-     * QName and adds it to this <code>Detail</code> object. This method
+     * Creates a new {@code DetailEntry} object with the given
+     * QName and adds it to this {@code Detail} object. This method
      * is the preferred over the one using Name.
      *
-     * @param qname a <code>QName</code> object identifying the
-     *         new <code>DetailEntry</code> object
+     * @param qname a {@code QName} object identifying the
+     *         new {@code DetailEntry} object
      *
      * @exception SOAPException thrown when there is a problem in adding a
      * DetailEntry object to this Detail object.
@@ -92,10 +92,10 @@
     public DetailEntry addDetailEntry(QName qname) throws SOAPException;
 
     /**
-     * Gets an Iterator over all of the <code>DetailEntry</code>s in this <code>Detail</code> object.
+     * Gets an Iterator over all of the {@code DetailEntry}s in this {@code Detail} object.
      *
-     * @return an <code>Iterator</code> object over the <code>DetailEntry</code>
-     *             objects in this <code>Detail</code> object
+     * @return an {@code Iterator} object over the {@code DetailEntry}
+     *             objects in this {@code Detail} object
      */
     public Iterator getDetailEntries();
 }
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/DetailEntry.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/DetailEntry.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -26,9 +26,9 @@
 package javax.xml.soap;
 
 /**
- * The content for a <code>Detail</code> object, giving details for
- * a <code>SOAPFault</code> object.  A <code>DetailEntry</code> object,
- * which carries information about errors related to the <code>SOAPBody</code>
+ * The content for a {@code Detail} object, giving details for
+ * a {@code SOAPFault} object.  A {@code DetailEntry} object,
+ * which carries information about errors related to the {@code SOAPBody}
  * object that contains it, is application-specific.
  *
  * @since 1.6
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/FactoryFinder.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/FactoryFinder.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -33,7 +33,7 @@
 
     /**
      * Creates an instance of the specified class using the specified
-     * <code>ClassLoader</code> object.
+     * {@code ClassLoader} object.
      *
      * @exception SOAPException if the given class could not be found
      *            or could not be instantiated
@@ -54,13 +54,13 @@
     }
 
     /**
-     * Finds the implementation <code>Class</code> object for the given
+     * Finds the implementation {@code Class} object for the given
      * factory name, or null if that fails.
      * <P>
      * This method is package private so that this code can be shared.
      *
-     * @return the <code>Class</code> object of the specified message factory;
-     *         or <code>null</code>
+     * @return the {@code Class} object of the specified message factory;
+     *         or {@code null}
      *
      * @param factoryId             the name of the factory to find, which is
      *                              a system property
@@ -73,22 +73,22 @@
     }
 
     /**
-     * Finds the implementation <code>Class</code> object for the given
-     * factory name, or if that fails, finds the <code>Class</code> object
+     * Finds the implementation {@code Class} object for the given
+     * factory name, or if that fails, finds the {@code Class} object
      * for the given fallback class name. The arguments supplied must be
      * used in order. If using the first argument is successful, the second
      * one will not be used.
      * <P>
      * This method is package private so that this code can be shared.
      *
-     * @return the <code>Class</code> object of the specified message factory;
-     *         may be <code>null</code>
+     * @return the {@code Class} object of the specified message factory;
+     *         may be {@code null}
      *
      * @param factoryId             the name of the factory to find, which is
      *                              a system property
      * @param fallbackClassName     the implementation class name, which is
      *                              to be used only if nothing else
-     *                              is found; <code>null</code> to indicate that
+     *                              is found; {@code null} to indicate that
      *                              there is no fallback class name
      * @exception SOAPException if there is a SOAP error
      */
@@ -99,24 +99,24 @@
     }
 
     /**
-     * Finds the implementation <code>Class</code> object for the given
-     * factory name, or if that fails, finds the <code>Class</code> object
-     * for the given default class name, but only if <code>tryFallback</code>
-     * is <code>true</code>.  The arguments supplied must be used in order
+     * Finds the implementation {@code Class} object for the given
+     * factory name, or if that fails, finds the {@code Class} object
+     * for the given default class name, but only if {@code tryFallback}
+     * is {@code true}.  The arguments supplied must be used in order
      * If using the first argument is successful, the second one will not
      * be used.  Note the default class name may be needed even if fallback
      * is not to be attempted, so certain error conditions can be handled.
      * <P>
      * This method is package private so that this code can be shared.
      *
-     * @return the <code>Class</code> object of the specified message factory;
-     *         may not be <code>null</code>
+     * @return the {@code Class} object of the specified message factory;
+     *         may not be {@code null}
      *
      * @param factoryId             the name of the factory to find, which is
      *                              a system property
      * @param defaultClassName      the implementation class name, which is
      *                              to be used only if nothing else
-     *                              is found; <code>null</code> to indicate
+     *                              is found; {@code null} to indicate
      *                              that there is no default class name
      * @param tryFallback           whether to try the default class as a
      *                              fallback
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/MessageFactory.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/MessageFactory.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -30,36 +30,36 @@
 import java.io.InputStream;
 
 /**
- * A factory for creating <code>SOAPMessage</code> objects.
+ * A factory for creating {@code SOAPMessage} objects.
  * <P>
- * A SAAJ client can create a <code>MessageFactory</code> object
- * using the method <code>newInstance</code>, as shown in the following
+ * A SAAJ client can create a {@code MessageFactory} object
+ * using the method {@code newInstance}, as shown in the following
  * lines of code.
- * <PRE>
+ * <pre>{@code
  *       MessageFactory mf = MessageFactory.newInstance();
  *       MessageFactory mf12 = MessageFactory.newInstance(SOAPConstants.SOAP_1_2_PROTOCOL);
- * </PRE>
+ * }</pre>
  * <P>
- * All <code>MessageFactory</code> objects, regardless of how they are
- * created, will produce <code>SOAPMessage</code> objects that
+ * All {@code MessageFactory} objects, regardless of how they are
+ * created, will produce {@code SOAPMessage} objects that
  * have the following elements by default:
  * <UL>
- *  <LI>A <code>SOAPPart</code> object
- *  <LI>A <code>SOAPEnvelope</code> object
- *  <LI>A <code>SOAPBody</code> object
- *  <LI>A <code>SOAPHeader</code> object
+ *  <LI>A {@code SOAPPart} object
+ *  <LI>A {@code SOAPEnvelope} object
+ *  <LI>A {@code SOAPBody} object
+ *  <LI>A {@code SOAPHeader} object
  * </UL>
  * In some cases, specialized MessageFactory objects may be obtained that produce messages
- * prepopulated with additional entries in the <code>SOAPHeader</code> object and the
- * <code>SOAPBody</code> object.
- * The content of a new <code>SOAPMessage</code> object depends on which of the two
- * <code>MessageFactory</code> methods is used to create it.
+ * prepopulated with additional entries in the {@code SOAPHeader} object and the
+ * {@code SOAPBody} object.
+ * The content of a new {@code SOAPMessage} object depends on which of the two
+ * {@code MessageFactory} methods is used to create it.
  * <UL>
- *  <LI><code>createMessage()</code> <BR>
+ *  <LI>{@code createMessage()} <BR>
  *      This is the method clients would normally use to create a request message.
- *  <LI><code>createMessage(MimeHeaders, java.io.InputStream)</code> -- message has
- *       content from the <code>InputStream</code> object and headers from the
- *       <code>MimeHeaders</code> object <BR>
+ *  <LI>{@code createMessage(MimeHeaders, java.io.InputStream)} -- message has
+ *       content from the {@code InputStream} object and headers from the
+ *       {@code MimeHeaders} object <BR>
  *        This method can be used internally by a service implementation to
  *        create a message that is a response to a request.
  * </UL>
@@ -75,7 +75,7 @@
         = "javax.xml.soap.MessageFactory";
 
     /**
-     * Creates a new <code>MessageFactory</code> object that is an instance
+     * Creates a new {@code MessageFactory} object that is an instance
      * of the default implementation (SOAP 1.1),
      *
      * This method uses the following ordered lookup procedure to determine the MessageFactory implementation class to load:
@@ -90,11 +90,11 @@
      * </UL>
 
      *
-     * @return a new instance of a <code>MessageFactory</code>
+     * @return a new instance of a {@code MessageFactory}
      *
      * @exception SOAPException if there was an error in creating the
      *            default implementation of the
-     *            <code>MessageFactory</code>.
+     *            {@code MessageFactory}.
      * @see SAAJMetaFactory
      */
 
@@ -121,26 +121,26 @@
     }
 
     /**
-     * Creates a new <code>MessageFactory</code> object that is an instance
+     * Creates a new {@code MessageFactory} object that is an instance
      * of the specified implementation.  May be a dynamic message factory,
      * a SOAP 1.1 message factory, or a SOAP 1.2 message factory. A dynamic
      * message factory creates messages based on the MIME headers specified
-     * as arguments to the <code>createMessage</code> method.
+     * as arguments to the {@code createMessage} method.
      *
      * This method uses the SAAJMetaFactory to locate the implementation class
      * and create the MessageFactory instance.
      *
-     * @return a new instance of a <code>MessageFactory</code>
+     * @return a new instance of a {@code MessageFactory}
      *
      * @param protocol  a string constant representing the class of the
      *                   specified message factory implementation. May be
-     *                   either <code>DYNAMIC_SOAP_PROTOCOL</code>,
-     *                   <code>DEFAULT_SOAP_PROTOCOL</code> (which is the same
-     *                   as) <code>SOAP_1_1_PROTOCOL</code>, or
-     *                   <code>SOAP_1_2_PROTOCOL</code>.
+     *                   either {@code DYNAMIC_SOAP_PROTOCOL},
+     *                   {@code DEFAULT_SOAP_PROTOCOL} (which is the same
+     *                   as) {@code SOAP_1_1_PROTOCOL}, or
+     *                   {@code SOAP_1_2_PROTOCOL}.
      *
      * @exception SOAPException if there was an error in creating the
-     *            specified implementation of  <code>MessageFactory</code>.
+     *            specified implementation of  {@code MessageFactory}.
      * @see SAAJMetaFactory
      * @since 1.6, SAAJ 1.3
      */
@@ -149,52 +149,52 @@
     }
 
     /**
-     * Creates a new <code>SOAPMessage</code> object with the default
-     * <code>SOAPPart</code>, <code>SOAPEnvelope</code>, <code>SOAPBody</code>,
-     * and <code>SOAPHeader</code> objects. Profile-specific message factories
-     * can choose to prepopulate the <code>SOAPMessage</code> object with
+     * Creates a new {@code SOAPMessage} object with the default
+     * {@code SOAPPart}, {@code SOAPEnvelope}, {@code SOAPBody},
+     * and {@code SOAPHeader} objects. Profile-specific message factories
+     * can choose to prepopulate the {@code SOAPMessage} object with
      * profile-specific headers.
      * <P>
-     * Content can be added to this message's <code>SOAPPart</code> object, and
+     * Content can be added to this message's {@code SOAPPart} object, and
      * the message can be sent "as is" when a message containing only a SOAP part
-     * is sufficient. Otherwise, the <code>SOAPMessage</code> object needs
-     * to create one or more <code>AttachmentPart</code> objects and
+     * is sufficient. Otherwise, the {@code SOAPMessage} object needs
+     * to create one or more {@code AttachmentPart} objects and
      * add them to itself. Any content that is not in XML format must be
-     * in an <code>AttachmentPart</code> object.
+     * in an {@code AttachmentPart} object.
      *
-     * @return a new <code>SOAPMessage</code> object
+     * @return a new {@code SOAPMessage} object
      * @exception SOAPException if a SOAP error occurs
      * @exception UnsupportedOperationException if the protocol of this
-     *      <code>MessageFactory</code> instance is <code>DYNAMIC_SOAP_PROTOCOL</code>
+     *      {@code MessageFactory} instance is {@code DYNAMIC_SOAP_PROTOCOL}
      */
     public abstract SOAPMessage createMessage()
         throws SOAPException;
 
     /**
-     * Internalizes the contents of the given <code>InputStream</code> object into a
-     * new <code>SOAPMessage</code> object and returns the <code>SOAPMessage</code>
+     * Internalizes the contents of the given {@code InputStream} object into a
+     * new {@code SOAPMessage} object and returns the {@code SOAPMessage}
      * object.
      *
-     * @param in the <code>InputStream</code> object that contains the data
+     * @param in the {@code InputStream} object that contains the data
      *           for a message
      * @param headers the transport-specific headers passed to the
      *        message in a transport-independent fashion for creation of the
      *        message
-     * @return a new <code>SOAPMessage</code> object containing the data from
-     *         the given <code>InputStream</code> object
+     * @return a new {@code SOAPMessage} object containing the data from
+     *         the given {@code InputStream} object
      *
      * @exception IOException if there is a problem in reading data from
      *            the input stream
      *
      * @exception SOAPException may be thrown if the message is invalid
      *
-     * @exception IllegalArgumentException if the <code>MessageFactory</code>
+     * @exception IllegalArgumentException if the {@code MessageFactory}
      *      requires one or more MIME headers to be present in the
-     *      <code>headers</code> parameter and they are missing.
-     *      <code>MessageFactory</code> implementations for
-     *      <code>SOAP_1_1_PROTOCOL</code> or
-     *      <code>SOAP_1_2_PROTOCOL</code> must not throw
-     *      <code>IllegalArgumentException</code> for this reason.
+     *      {@code headers} parameter and they are missing.
+     *      {@code MessageFactory} implementations for
+     *      {@code SOAP_1_1_PROTOCOL} or
+     *      {@code SOAP_1_2_PROTOCOL} must not throw
+     *      {@code IllegalArgumentException} for this reason.
      */
     public abstract SOAPMessage createMessage(MimeHeaders headers,
                                               InputStream in)
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/MimeHeader.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/MimeHeader.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -28,7 +28,7 @@
 
 /**
  * An object that stores a MIME header name and its value. One or more
- * <code>MimeHeader</code> objects may be contained in a <code>MimeHeaders</code>
+ * {@code MimeHeader} objects may be contained in a {@code MimeHeaders}
  * object.
  *
  * @see MimeHeaders
@@ -40,11 +40,11 @@
    private String value;
 
    /**
-    * Constructs a <code>MimeHeader</code> object initialized with the given
+    * Constructs a {@code MimeHeader} object initialized with the given
     * name and value.
     *
-    * @param name a <code>String</code> giving the name of the header
-    * @param value a <code>String</code> giving the value of the header
+    * @param name a {@code String} giving the name of the header
+    * @param value a {@code String} giving the value of the header
     */
     public MimeHeader(String name, String value) {
         this.name = name;
@@ -52,18 +52,18 @@
     }
 
     /**
-     * Returns the name of this <code>MimeHeader</code> object.
+     * Returns the name of this {@code MimeHeader} object.
      *
-     * @return the name of the header as a <code>String</code>
+     * @return the name of the header as a {@code String}
      */
     public String getName() {
         return name;
     }
 
     /**
-     * Returns the value of this <code>MimeHeader</code> object.
+     * Returns the value of this {@code MimeHeader} object.
      *
-     * @return  the value of the header as a <code>String</code>
+     * @return  the value of the header as a {@code String}
      */
     public String getValue() {
         return value;
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/MimeHeaders.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/MimeHeaders.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -29,13 +29,13 @@
 import java.util.Vector;
 
 /**
- * A container for <code>MimeHeader</code> objects, which represent
+ * A container for {@code MimeHeader} objects, which represent
  * the MIME headers present in a MIME part of a message.
  *
  * <p>This class is used primarily when an application wants to
  * retrieve specific attachments based on certain MIME headers and
  * values. This class will most likely be used by implementations of
- * <code>AttachmentPart</code> and other MIME dependent parts of the SAAJ
+ * {@code AttachmentPart} and other MIME dependent parts of the SAAJ
  * API.
  * @see SOAPMessage#getAttachments
  * @see AttachmentPart
@@ -45,8 +45,8 @@
     private Vector headers;
 
    /**
-    * Constructs a default <code>MimeHeaders</code> object initialized with
-    * an empty <code>Vector</code> object.
+    * Constructs a default {@code MimeHeaders} object initialized with
+    * an empty {@code Vector} object.
     */
     public MimeHeaders() {
         headers = new Vector();
@@ -54,10 +54,10 @@
 
     /**
      * Returns all of the values for the specified header as an array of
-     * <code>String</code> objects.
+     * {@code String} objects.
      *
      * @param   name the name of the header for which values will be returned
-     * @return a <code>String</code> array with all of the values for the
+     * @return a {@code String} array with all of the values for the
      *         specified header
      * @see #setHeader
      */
@@ -86,9 +86,9 @@
      * <P>
      * Note that RFC822 headers can contain only US-ASCII characters.
      *
-     * @param   name a <code>String</code> with the name of the header for
+     * @param   name a {@code String} with the name of the header for
      *          which to search
-     * @param   value a <code>String</code> with the value that will replace the
+     * @param   value a {@code String} with the value that will replace the
      *          current value of the specified header
      *
      * @exception IllegalArgumentException if there was a problem in the
@@ -120,14 +120,14 @@
     }
 
     /**
-     * Adds a <code>MimeHeader</code> object with the specified name and value
-     * to this <code>MimeHeaders</code> object's list of headers.
+     * Adds a {@code MimeHeader} object with the specified name and value
+     * to this {@code MimeHeaders} object's list of headers.
      * <P>
      * Note that RFC822 headers can contain only US-ASCII characters.
      *
-     * @param   name a <code>String</code> with the name of the header to
+     * @param   name a {@code String} with the name of the header to
      *          be added
-     * @param   value a <code>String</code> with the value of the header to
+     * @param   value a {@code String} with the value of the header to
      *          be added
      *
      * @exception IllegalArgumentException if there was a problem in the
@@ -152,10 +152,10 @@
     }
 
     /**
-     * Remove all <code>MimeHeader</code> objects whose name matches the
+     * Remove all {@code MimeHeader} objects whose name matches the
      * given name.
      *
-     * @param   name a <code>String</code> with the name of the header for
+     * @param   name a {@code String} with the name of the header for
      *          which to search
      */
     public void removeHeader(String name) {
@@ -167,7 +167,7 @@
     }
 
     /**
-     * Removes all the header entries from this <code>MimeHeaders</code> object.
+     * Removes all the header entries from this {@code MimeHeaders} object.
      */
     public void removeAllHeaders() {
         headers.removeAllElements();
@@ -175,10 +175,10 @@
 
 
     /**
-     * Returns all the <code>MimeHeader</code>s in this <code>MimeHeaders</code> object.
+     * Returns all the {@code MimeHeader}s in this {@code MimeHeaders} object.
      *
-     * @return  an <code>Iterator</code> object over this <code>MimeHeaders</code>
-     *          object's list of <code>MimeHeader</code> objects
+     * @return  an {@code Iterator} object over this {@code MimeHeaders}
+     *          object's list of {@code MimeHeader} objects
      */
     public Iterator getAllHeaders() {
         return headers.iterator();
@@ -243,12 +243,12 @@
 
 
     /**
-     * Returns all the <code>MimeHeader</code> objects whose name matches
+     * Returns all the {@code MimeHeader} objects whose name matches
      * a name in the given array of names.
      *
-     * @param names an array of <code>String</code> objects with the names
+     * @param names an array of {@code String} objects with the names
      *         for which to search
-     * @return  an <code>Iterator</code> object over the <code>MimeHeader</code>
+     * @return  an {@code Iterator} object over the {@code MimeHeader}
      *          objects whose name matches one of the names in the given list
      */
     public Iterator getMatchingHeaders(String[] names) {
@@ -256,12 +256,12 @@
     }
 
     /**
-     * Returns all of the <code>MimeHeader</code> objects whose name does not
+     * Returns all of the {@code MimeHeader} objects whose name does not
      * match a name in the given array of names.
      *
-     * @param names an array of <code>String</code> objects with the names
+     * @param names an array of {@code String} objects with the names
      *         for which to search
-     * @return  an <code>Iterator</code> object over the <code>MimeHeader</code>
+     * @return  an {@code Iterator} object over the {@code MimeHeader}
      *          objects whose name does not match one of the names in the given list
      */
     public Iterator getNonMatchingHeaders(String[] names) {
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/Name.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/Name.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -55,17 +55,17 @@
  * The following line of
  * code, in which <i>se</i> is a {@code SOAPEnvelope} object, creates a new
  * {@code Name} object with all three.
- * <PRE>
+ * <pre>{@code
  *     Name name = se.createName("GetLastTradePrice", "WOMBAT",
  *                                "http://www.wombat.org/trader");
- * </PRE>
+ * }</pre>
  * The following line of code gives an example of how a {@code Name} object
  * can be used. The variable <i>element</i> is a {@code SOAPElement} object.
  * This code creates a new {@code SOAPElement} object with the given name and
  * adds it to <i>element</i>.
- * <PRE>
+ * <pre>{@code
  *     element.addChildElement(name);
- * </PRE>
+ * }</pre>
  * <P>
  * The {@code Name} interface may be deprecated in a future release of SAAJ
  * in favor of {@code javax.xml.namespace.QName}
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/Node.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/Node.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -35,19 +35,19 @@
  */
 public interface Node extends org.w3c.dom.Node {
     /**
-     * Returns the value of this node if this is a <code>Text</code> node or the
+     * Returns the value of this node if this is a {@code Text} node or the
      * value of the immediate child of this node otherwise.
-     * If there is an immediate child of this <code>Node</code> that it is a
-     * <code>Text</code> node then it's value will be returned. If there is
-     * more than one <code>Text</code> node then the value of the first
-     * <code>Text</code> Node will be returned.
-     * Otherwise <code>null</code> is returned.
+     * If there is an immediate child of this {@code Node} that it is a
+     * {@code Text} node then it's value will be returned. If there is
+     * more than one {@code Text} node then the value of the first
+     * {@code Text} Node will be returned.
+     * Otherwise {@code null} is returned.
      *
-     * @return a <code>String</code> with the text of this node if this is a
-     *          <code>Text</code> node or the text contained by the first
-     *          immediate child of this <code>Node</code> object that is a
-     *          <code>Text</code> object if such a child exists;
-     *          <code>null</code> otherwise.
+     * @return a {@code String} with the text of this node if this is a
+     *          {@code Text} node or the text contained by the first
+     *          immediate child of this {@code Node} object that is a
+     *          {@code Text} object if such a child exists;
+     *          {@code null} otherwise.
      */
     public String getValue();
 
@@ -55,24 +55,24 @@
      * If this is a Text node then this method will set its value,
      * otherwise it sets the value of  the immediate (Text) child of this node.
      * The value of the immediate child of this node can be set only if, there is
-     * one child node and that node is a <code>Text</code> node, or if
-     * there are no children in which case a child <code>Text</code> node will be
+     * one child node and that node is a {@code Text} node, or if
+     * there are no children in which case a child {@code Text} node will be
      * created.
      *
-     * @exception IllegalStateException if the node is not a <code>Text</code>
+     * @exception IllegalStateException if the node is not a {@code Text}
      *              node and either has more than one child node or has a child
-     *              node that is not a <code>Text</code> node.
+     *              node that is not a {@code Text} node.
      *
      * @since 1.6, SAAJ 1.2
      */
     public void setValue(String value);
 
     /**
-     * Sets the parent of this <code>Node</code> object to the given
-     * <code>SOAPElement</code> object.
+     * Sets the parent of this {@code Node} object to the given
+     * {@code SOAPElement} object.
      *
-     * @param parent the <code>SOAPElement</code> object to be set as
-     *       the parent of this <code>Node</code> object
+     * @param parent the {@code SOAPElement} object to be set as
+     *       the parent of this {@code Node} object
      *
      * @exception SOAPException if there is a problem in setting the
      *                          parent to the given element
@@ -81,13 +81,13 @@
     public void setParentElement(SOAPElement parent) throws SOAPException;
 
     /**
-     * Returns the parent element of this <code>Node</code> object.
-     * This method can throw an <code>UnsupportedOperationException</code>
+     * Returns the parent element of this {@code Node} object.
+     * This method can throw an {@code UnsupportedOperationException}
      * if the tree is not kept in memory.
      *
-     * @return the <code>SOAPElement</code> object that is the parent of
-     *         this <code>Node</code> object or <code>null</code> if this
-     *         <code>Node</code> object is root
+     * @return the {@code SOAPElement} object that is the parent of
+     *         this {@code Node} object or {@code null} if this
+     *         {@code Node} object is root
      *
      * @exception UnsupportedOperationException if the whole tree is not
      *            kept in memory
@@ -96,18 +96,18 @@
     public SOAPElement getParentElement();
 
     /**
-     * Removes this <code>Node</code> object from the tree.
+     * Removes this {@code Node} object from the tree.
      */
     public void detachNode();
 
     /**
-     * Notifies the implementation that this <code>Node</code>
+     * Notifies the implementation that this {@code Node}
      * object is no longer being used by the application and that the
      * implementation is free to reuse this object for nodes that may
      * be created later.
      * <P>
-     * Calling the method <code>recycleNode</code> implies that the method
-     * <code>detachNode</code> has been called previously.
+     * Calling the method {@code recycleNode} implies that the method
+     * {@code detachNode} has been called previously.
      */
     public void recycleNode();
 
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SAAJMetaFactory.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SAAJMetaFactory.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -27,9 +27,9 @@
 
 /**
 * The access point for the implementation classes of the factories defined in the
-* SAAJ API. All of the <code>newInstance</code> methods defined on factories in
+* SAAJ API. All of the {@code newInstance} methods defined on factories in
 * SAAJ 1.3 defer to instances of this class to do the actual object creation.
-* The implementations of <code>newInstance()</code> methods (in SOAPFactory and MessageFactory)
+* The implementations of {@code newInstance()} methods (in SOAPFactory and MessageFactory)
 * that existed in SAAJ 1.2 have been updated to also delegate to the SAAJMetaFactory when the SAAJ 1.2
 * defined lookup fails to locate the Factory implementation class name.
 *
@@ -48,10 +48,10 @@
         "com.sun.xml.internal.messaging.saaj.soap.SAAJMetaFactoryImpl";
 
     /**
-     * Creates a new instance of a concrete <code>SAAJMetaFactory</code> object.
+     * Creates a new instance of a concrete {@code SAAJMetaFactory} object.
      * The SAAJMetaFactory is an SPI, it pulls the creation of the other factories together into a
      * single place. Changing out the SAAJMetaFactory has the effect of changing out the entire SAAJ
-     * implementation. Service providers provide the name of their <code>SAAJMetaFactory</code>
+     * implementation. Service providers provide the name of their {@code SAAJMetaFactory}
      * implementation.
      *
      * This method uses the following ordered lookup procedure to determine the SAAJMetaFactory implementation class to load:
@@ -65,8 +65,8 @@
      *  <LI> Default to com.sun.xml.internal.messaging.saaj.soap.SAAJMetaFactoryImpl.
      * </UL>
      *
-     * @return a concrete <code>SAAJMetaFactory</code> object
-     * @exception SOAPException if there is an error in creating the <code>SAAJMetaFactory</code>
+     * @return a concrete {@code SAAJMetaFactory} object
+     * @exception SOAPException if there is an error in creating the {@code SAAJMetaFactory}
      */
     static SAAJMetaFactory getInstance() throws SOAPException {
             try {
@@ -84,10 +84,10 @@
     protected SAAJMetaFactory() { }
 
      /**
-      * Creates a <code>MessageFactory</code> object for
-      * the given <code>String</code> protocol.
+      * Creates a {@code MessageFactory} object for
+      * the given {@code String} protocol.
       *
-      * @param protocol a <code>String</code> indicating the protocol
+      * @param protocol a {@code String} indicating the protocol
       * @exception SOAPException if there is an error in creating the
       *            MessageFactory
       * @see SOAPConstants#SOAP_1_1_PROTOCOL
@@ -98,10 +98,10 @@
         throws SOAPException;
 
      /**
-      * Creates a <code>SOAPFactory</code> object for
-      * the given <code>String</code> protocol.
+      * Creates a {@code SOAPFactory} object for
+      * the given {@code String} protocol.
       *
-      * @param protocol a <code>String</code> indicating the protocol
+      * @param protocol a {@code String} indicating the protocol
       * @exception SOAPException if there is an error in creating the
       *            SOAPFactory
       * @see SOAPConstants#SOAP_1_1_PROTOCOL
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SAAJResult.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SAAJResult.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -40,18 +40,18 @@
 public class SAAJResult extends DOMResult {
 
     /**
-     * Creates a <code>SAAJResult</code> that will present results in the form
+     * Creates a {@code SAAJResult} that will present results in the form
      * of a SAAJ tree that supports the default (SOAP 1.1) protocol.
      * <p>
-     * This kind of <code>SAAJResult</code> is meant for use in situations where the
+     * This kind of {@code SAAJResult} is meant for use in situations where the
      * results will be used as a parameter to a method that takes a parameter
-     * whose type, such as <code>SOAPElement</code>, is drawn from the SAAJ
+     * whose type, such as {@code SOAPElement}, is drawn from the SAAJ
      * API. When used in a transformation, the results are populated into the
-     * <code>SOAPPart</code> of a <code>SOAPMessage</code> that is created internally.
-     * The <code>SOAPPart</code> returned by {@link DOMResult#getNode()}
+     * {@code SOAPPart} of a {@code SOAPMessage} that is created internally.
+     * The {@code SOAPPart} returned by {@link DOMResult#getNode()}
      * is not guaranteed to be well-formed.
      *
-     * @throws SOAPException if there is a problem creating a <code>SOAPMessage</code>
+     * @throws SOAPException if there is a problem creating a {@code SOAPMessage}
      *
      * @since 1.6, SAAJ 1.3
      */
@@ -60,23 +60,23 @@
     }
 
     /**
-     * Creates a <code>SAAJResult</code> that will present results in the form
+     * Creates a {@code SAAJResult} that will present results in the form
      * of a SAAJ tree that supports the specified protocol. The
-     * <code>DYNAMIC_SOAP_PROTOCOL</code> is ambiguous in this context and will
-     * cause this constructor to throw an <code>UnsupportedOperationException</code>.
+     * {@code DYNAMIC_SOAP_PROTOCOL} is ambiguous in this context and will
+     * cause this constructor to throw an {@code UnsupportedOperationException}.
      * <p>
-     * This kind of <code>SAAJResult</code> is meant for use in situations where the
+     * This kind of {@code SAAJResult} is meant for use in situations where the
      * results will be used as a parameter to a method that takes a parameter
-     * whose type, such as <code>SOAPElement</code>, is drawn from the SAAJ
+     * whose type, such as {@code SOAPElement}, is drawn from the SAAJ
      * API. When used in a transformation the results are populated into the
-     * <code>SOAPPart</code> of a <code>SOAPMessage</code> that is created
-     * internally. The <code>SOAPPart</code> returned by {@link DOMResult#getNode()}
+     * {@code SOAPPart} of a {@code SOAPMessage} that is created
+     * internally. The {@code SOAPPart} returned by {@link DOMResult#getNode()}
      * is not guaranteed to be well-formed.
      *
      * @param protocol - the name of the SOAP protocol that the resulting SAAJ
      *                      tree should support
      *
-     * @throws SOAPException if a <code>SOAPMessage</code> supporting the
+     * @throws SOAPException if a {@code SOAPMessage} supporting the
      *             specified protocol cannot be created
      *
      * @since 1.6, SAAJ 1.3
@@ -86,16 +86,16 @@
     }
 
     /**
-     * Creates a <code>SAAJResult</code> that will write the results into the
-     * <code>SOAPPart</code> of the supplied <code>SOAPMessage</code>.
+     * Creates a {@code SAAJResult} that will write the results into the
+     * {@code SOAPPart} of the supplied {@code SOAPMessage}.
      * In the normal case these results will be written using DOM APIs and,
-     * as a result, the finished <code>SOAPPart</code> will not be guaranteed
+     * as a result, the finished {@code SOAPPart} will not be guaranteed
      * to be well-formed unless the data used to create it is also well formed.
-     * When used in a transformation the validity of the <code>SOAPMessage</code>
+     * When used in a transformation the validity of the {@code SOAPMessage}
      * after the transformation can be guaranteed only by means outside SAAJ
      * specification.
      *
-     * @param message - the message whose <code>SOAPPart</code> will be
+     * @param message - the message whose {@code SOAPPart} will be
      *                  populated as a result of some transformation or
      *                  marshalling operation
      *
@@ -106,11 +106,11 @@
     }
 
     /**
-     * Creates a <code>SAAJResult</code> that will write the results as a
-     * child node of the <code>SOAPElement</code> specified. In the normal
+     * Creates a {@code SAAJResult} that will write the results as a
+     * child node of the {@code SOAPElement} specified. In the normal
      * case these results will be written using DOM APIs and as a result may
      * invalidate the structure of the SAAJ tree. This kind of
-     * <code>SAAJResult</code> should only be used when the validity of the
+     * {@code SAAJResult} should only be used when the validity of the
      * incoming data can be guaranteed by means outside of the SAAJ
      * specification.
      *
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPBody.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPBody.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -258,7 +258,7 @@
     public SOAPBodyElement addBodyElement(QName qname) throws SOAPException;
 
     /**
-     * Adds the root node of the DOM <code>{@link org.w3c.dom.Document}</code>
+     * Adds the root node of the DOM {@link org.w3c.dom.Document}
      * to this {@code SOAPBody} object.
      * <p>
      * Calling this method invalidates the {@code document} parameter.
@@ -279,12 +279,12 @@
         throws SOAPException;
 
     /**
-     * Creates a new DOM <code>{@link org.w3c.dom.Document}</code> and sets
+     * Creates a new DOM {@link org.w3c.dom.Document} and sets
      * the first child of this {@code SOAPBody} as it's document
      * element. The child {@code SOAPElement} is removed as part of the
      * process.
      *
-     * @return the <code>{@link org.w3c.dom.Document}</code> representation
+     * @return the {@link org.w3c.dom.Document} representation
      *         of the {@code SOAPBody} content.
      *
      * @exception SOAPException
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPBodyElement.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPBodyElement.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -26,18 +26,18 @@
 package javax.xml.soap;
 
 /**
- * A <code>SOAPBodyElement</code> object represents the contents in
- * a <code>SOAPBody</code> object.  The <code>SOAPFault</code> interface
- * is a <code>SOAPBodyElement</code> object that has been defined.
+ * A {@code SOAPBodyElement} object represents the contents in
+ * a {@code SOAPBody} object.  The {@code SOAPFault} interface
+ * is a {@code SOAPBodyElement} object that has been defined.
  * <P>
- * A new <code>SOAPBodyElement</code> object can be created and added
- * to a <code>SOAPBody</code> object with the <code>SOAPBody</code>
- * method <code>addBodyElement</code>. In the following line of code,
- * <code>sb</code> is a <code>SOAPBody</code> object, and
- * <code>myName</code> is a <code>Name</code> object.
- * <PRE>
+ * A new {@code SOAPBodyElement} object can be created and added
+ * to a {@code SOAPBody} object with the {@code SOAPBody}
+ * method {@code addBodyElement}. In the following line of code,
+ * {@code sb} is a {@code SOAPBody} object, and
+ * {@code myName} is a {@code Name} object.
+ * <pre>{@code
  *    SOAPBodyElement sbe = sb.addBodyElement(myName);
- * </PRE>
+ * }</pre>
  *
  * @since 1.6
  */
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPConnection.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPConnection.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -32,18 +32,18 @@
  * <p>
  * The SOAPConnection class is optional. Some implementations may
  * not implement this interface in which case the call to
- * <code>SOAPConnectionFactory.newInstance()</code> (see below) will
- * throw an <code>UnsupportedOperationException</code>.
+ * {@code SOAPConnectionFactory.newInstance()} (see below) will
+ * throw an {@code UnsupportedOperationException}.
  * <p>
- * A client can obtain a <code>SOAPConnection</code> object using a
+ * A client can obtain a {@code SOAPConnection} object using a
  * {@link SOAPConnectionFactory} object as in the following example:
- * <PRE>
+ * <pre>{@code
  *      SOAPConnectionFactory factory = SOAPConnectionFactory.newInstance();
  *      SOAPConnection con = factory.createConnection();
- * </PRE>
- * A <code>SOAPConnection</code> object can be used to send messages
+ * }</pre>
+ * A {@code SOAPConnection} object can be used to send messages
  * directly to a URL following the request/response paradigm.  That is,
- * messages are sent using the method <code>call</code>, which sends the
+ * messages are sent using the method {@code call}, which sends the
  * message and then waits until it gets a reply.
  *
  * @since 1.6
@@ -54,15 +54,15 @@
      * Sends the given message to the specified endpoint and blocks until
      * it has returned the response.
      *
-     * @param request the <code>SOAPMessage</code> object to be sent
-     * @param to an <code>Object</code> that identifies
+     * @param request the {@code SOAPMessage} object to be sent
+     * @param to an {@code Object} that identifies
      *         where the message should be sent. It is required to
      *         support Objects of type
-     *         <code>java.lang.String</code>,
-     *         <code>java.net.URL</code>, and when JAXM is present
-     *         <code>javax.xml.messaging.URLEndpoint</code>
+     *         {@code java.lang.String},
+     *         {@code java.net.URL}, and when JAXM is present
+     *         {@code javax.xml.messaging.URLEndpoint}
      *
-     * @return the <code>SOAPMessage</code> object that is the response to the
+     * @return the {@code SOAPMessage} object that is the response to the
      *         message that was sent
      * @throws SOAPException if there is a SOAP error
      */
@@ -72,12 +72,12 @@
     /**
      * Gets a message from a specific endpoint and blocks until it receives,
      *
-     * @param to an <code>Object</code> that identifies where
+     * @param to an {@code Object} that identifies where
      *                  the request should be sent. Objects of type
-     *                 <code>java.lang.String</code> and
-     *                 <code>java.net.URL</code> must be supported.
+     *                 {@code java.lang.String} and
+     *                 {@code java.net.URL} must be supported.
      *
-     * @return the <code>SOAPMessage</code> object that is the response to the
+     * @return the {@code SOAPMessage} object that is the response to the
      *                  get message request
      * @throws SOAPException if there is a SOAP error
      * @since 1.6, SAAJ 1.3
@@ -88,7 +88,7 @@
     }
 
     /**
-     * Closes this <code>SOAPConnection</code> object.
+     * Closes this {@code SOAPConnection} object.
      *
      * @throws SOAPException if there is a SOAP error
      */
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPConnectionFactory.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPConnectionFactory.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -26,38 +26,38 @@
 package javax.xml.soap;
 
 /**
- * A factory for creating <code>SOAPConnection</code> objects. Implementation of this class
- * is optional. If <code>SOAPConnectionFactory.newInstance()</code> throws an
+ * A factory for creating {@code SOAPConnection} objects. Implementation of this class
+ * is optional. If {@code SOAPConnectionFactory.newInstance()} throws an
  * UnsupportedOperationException then the implementation does not support the
  * SAAJ communication infrastructure. Otherwise {@link SOAPConnection} objects
- * can be created by calling <code>createConnection()</code> on the newly
- * created <code>SOAPConnectionFactory</code> object.
+ * can be created by calling {@code createConnection()} on the newly
+ * created {@code SOAPConnectionFactory} object.
  *
  * @since 1.6
  */
 public abstract class SOAPConnectionFactory {
     /**
-     * A constant representing the default value for a <code>SOAPConnection</code>
+     * A constant representing the default value for a {@code SOAPConnection}
      * object. The default is the point-to-point SOAP connection.
      */
     static final String DEFAULT_SOAP_CONNECTION_FACTORY
         = "com.sun.xml.internal.messaging.saaj.client.p2p.HttpSOAPConnectionFactory";
 
     /**
-     * A constant representing the <code>SOAPConnection</code> class.
+     * A constant representing the {@code SOAPConnection} class.
      */
     static private final String SF_PROPERTY
         = "javax.xml.soap.SOAPConnectionFactory";
 
     /**
      * Creates an instance of the default
-     * <code>SOAPConnectionFactory</code> object.
+     * {@code SOAPConnectionFactory} object.
      *
      * @return a new instance of a default
-     *         <code>SOAPConnectionFactory</code> object
+     *         {@code SOAPConnectionFactory} object
      *
      * @exception SOAPException if there was an error creating the
-     *            <code>SOAPConnectionFactory</code>
+     *            {@code SOAPConnectionFactory}
      *
      * @exception UnsupportedOperationException if newInstance is not
      * supported.
@@ -76,12 +76,12 @@
     }
 
     /**
-     * Create a new <code>SOAPConnection</code>.
+     * Create a new {@code SOAPConnection}.
      *
-     * @return the new <code>SOAPConnection</code> object.
+     * @return the new {@code SOAPConnection} object.
      *
      * @exception SOAPException if there was an exception creating the
-     * <code>SOAPConnection</code> object.
+     * {@code SOAPConnection} object.
      */
     public abstract SOAPConnection createConnection()
         throws SOAPException;
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPConstants.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPConstants.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -34,30 +34,30 @@
  */
 public interface SOAPConstants {
     /**
-     * Used to create <code>MessageFactory</code> instances that create
-     * <code>SOAPMessages</code> whose concrete type is based on the
-     * <code>Content-Type</code> MIME header passed to the
-     * <code>createMessage</code> method. If no <code>Content-Type</code>
-     * header is passed then the <code>createMessage</code> may throw an
-     * <code>IllegalArgumentException</code> or, in the case of the no
-     * argument version of <code>createMessage</code>, an
-     * <code>UnsupportedOperationException</code>.
+     * Used to create {@code MessageFactory} instances that create
+     * {@code SOAPMessages} whose concrete type is based on the
+     * {@code Content-Type} MIME header passed to the
+     * {@code createMessage} method. If no {@code Content-Type}
+     * header is passed then the {@code createMessage} may throw an
+     * {@code IllegalArgumentException} or, in the case of the no
+     * argument version of {@code createMessage}, an
+     * {@code UnsupportedOperationException}.
      *
      * @since  1.6, SAAJ 1.3
      */
     public static final String DYNAMIC_SOAP_PROTOCOL = "Dynamic Protocol";
 
     /**
-     * Used to create <code>MessageFactory</code> instances that create
-     * <code>SOAPMessages</code> whose behavior supports the SOAP 1.1  specification.
+     * Used to create {@code MessageFactory} instances that create
+     * {@code SOAPMessages} whose behavior supports the SOAP 1.1  specification.
      *
      * @since  1.6, SAAJ 1.3
      */
     public static final String SOAP_1_1_PROTOCOL = "SOAP 1.1 Protocol";
 
     /**
-     * Used to create <code>MessageFactory</code> instances that create
-     * <code>SOAPMessages</code> whose behavior supports the SOAP 1.2
+     * Used to create {@code MessageFactory} instances that create
+     * {@code SOAPMessages} whose behavior supports the SOAP 1.2
      * specification
      *
      * @since  1.6, SAAJ 1.3
@@ -93,9 +93,9 @@
 
     /**
      * The namespace identifier for the SOAP 1.1 encoding.
-     * An attribute named <code>encodingStyle</code> in the
-     * <code>URI_NS_SOAP_ENVELOPE</code> namespace and set to the value
-     * <code>URI_NS_SOAP_ENCODING</code> can be added to an element to indicate
+     * An attribute named {@code encodingStyle} in the
+     * {@code URI_NS_SOAP_ENVELOPE} namespace and set to the value
+     * {@code URI_NS_SOAP_ENCODING} can be added to an element to indicate
      * that it is encoded using the rules in section 5 of the SOAP 1.1
      * specification.
      */
@@ -110,14 +110,14 @@
         URI_NS_SOAP_1_2_ENCODING = "http://www.w3.org/2003/05/soap-encoding";
 
     /**
-     * The media type  of the <code>Content-Type</code> MIME header in SOAP 1.1.
+     * The media type  of the {@code Content-Type} MIME header in SOAP 1.1.
      * @since 1.6, SAAJ 1.3
      */
     public static final String
         SOAP_1_1_CONTENT_TYPE = "text/xml";
 
     /**
-     * The media type  of the <code>Content-Type</code> MIME header in SOAP 1.2.
+     * The media type  of the {@code Content-Type} MIME header in SOAP 1.2.
      * @since 1.6, SAAJ 1.3
      */
     public static final String
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPElement.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPElement.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -38,8 +38,7 @@
  * Methods in this interface that are required to return SAAJ specific objects
  * may "silently" replace nodes in the tree as required to successfully return
  * objects of the correct type. See {@link #getChildElements()} and
- * {@link <a HREF="package-summary.html#package_description">javax.xml.soap</a>}
- * for details.
+ * {@link javax.xml.soap} for details.
  *
  * @since 1.6
  */
@@ -345,7 +344,7 @@
      *          with the {@code prefix} in the context of this
      *          {@code SOAPElement}. This namespace will be the same as
      *          the one that would be returned by
-     *          <code>{@link #getNamespaceURI(String)}</code> if it were given
+     *          {@link #getNamespaceURI(String)} if it were given
      *          {@code prefix} as it's parameter.
      *
      * @exception SOAPException if the {@code QName} cannot be created.
@@ -439,7 +438,7 @@
      * have been obtained through DOM APIs as invalid and either discard them or
      * refresh them with the values returned by this {@code Iterator}. This
      * behavior can be avoided by calling the equivalent DOM APIs. See
-     * {@link <a HREF="package-summary.html#package_description">javax.xml.soap</a>}
+     * {@link javax.xml.soap}
      * for more details.
      *
      * @return an iterator with the content of this {@code SOAPElement}
@@ -461,7 +460,7 @@
      * have been obtained through DOM APIs as invalid and either discard them or
      * refresh them with the values returned by this {@code Iterator}. This
      * behavior can be avoided by calling the equivalent DOM APIs. See
-     * {@link <a HREF="package-summary.html#package_description">javax.xml.soap</a>}
+     * {@link javax.xml.soap}
      * for more details.
      *
      * @param name a {@code Name} object with the name of the child
@@ -488,7 +487,7 @@
      * have been obtained through DOM APIs as invalid and either discard them or
      * refresh them with the values returned by this {@code Iterator}. This
      * behavior can be avoided by calling the equivalent DOM APIs. See
-     * {@link <a HREF="package-summary.html#package_description">javax.xml.soap</a>}
+     * {@link javax.xml.soap}
      * for more details.
      *
      * @param qname a {@code QName} object with the qname of the child
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPElementFactory.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPElementFactory.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -26,16 +26,16 @@
 package javax.xml.soap;
 
 /**
- * <code>SOAPElementFactory</code> is a factory for XML fragments that
+ * {@code SOAPElementFactory} is a factory for XML fragments that
  * will eventually end up in the SOAP part. These fragments
- * can be inserted as children of the <code>SOAPHeader</code> or
- * <code>SOAPBody</code> or <code>SOAPEnvelope</code>.
+ * can be inserted as children of the {@code SOAPHeader} or
+ * {@code SOAPBody} or {@code SOAPEnvelope}.
  *
  * <p>Elements created using this factory do not have the properties
  * of an element that lives inside a SOAP header document. These
  * elements are copied into the XML document tree when they are
  * inserted.
- * @deprecated - Use <code>javax.xml.soap.SOAPFactory</code> for creating SOAPElements.
+ * @deprecated - Use {@code javax.xml.soap.SOAPFactory} for creating SOAPElements.
  * @see javax.xml.soap.SOAPFactory
  * @since 1.6
  */
@@ -48,17 +48,17 @@
     }
 
     /**
-     * Create a <code>SOAPElement</code> object initialized with the
-     * given <code>Name</code> object.
+     * Create a {@code SOAPElement} object initialized with the
+     * given {@code Name} object.
      *
-     * @param name a <code>Name</code> object with the XML name for
+     * @param name a {@code Name} object with the XML name for
      *             the new element
      *
-     * @return the new <code>SOAPElement</code> object that was
+     * @return the new {@code SOAPElement} object that was
      *         created
      *
      * @exception SOAPException if there is an error in creating the
-     *            <code>SOAPElement</code> object
+     *            {@code SOAPElement} object
      *
      * @deprecated Use
      * javax.xml.soap.SOAPFactory.createElement(javax.xml.soap.Name)
@@ -72,17 +72,17 @@
     }
 
     /**
-     * Create a <code>SOAPElement</code> object initialized with the
+     * Create a {@code SOAPElement} object initialized with the
      * given local name.
      *
-     * @param localName a <code>String</code> giving the local name for
+     * @param localName a {@code String} giving the local name for
      *             the new element
      *
-     * @return the new <code>SOAPElement</code> object that was
+     * @return the new {@code SOAPElement} object that was
      *         created
      *
      * @exception SOAPException if there is an error in creating the
-     *            <code>SOAPElement</code> object
+     *            {@code SOAPElement} object
      *
      * @deprecated Use
      * javax.xml.soap.SOAPFactory.createElement(String localName) instead
@@ -94,17 +94,17 @@
     }
 
     /**
-     * Create a new <code>SOAPElement</code> object with the given
+     * Create a new {@code SOAPElement} object with the given
      * local name, prefix and uri.
      *
-     * @param localName a <code>String</code> giving the local name
+     * @param localName a {@code String} giving the local name
      *                  for the new element
-     * @param prefix the prefix for this <code>SOAPElement</code>
-     * @param uri a <code>String</code> giving the URI of the
+     * @param prefix the prefix for this {@code SOAPElement}
+     * @param uri a {@code String} giving the URI of the
      *            namespace to which the new element belongs
      *
      * @exception SOAPException if there is an error in creating the
-     *            <code>SOAPElement</code> object
+     *            {@code SOAPElement} object
      *
      * @deprecated Use
      * javax.xml.soap.SOAPFactory.createElement(String localName,
@@ -120,12 +120,12 @@
     }
 
     /**
-     * Creates a new instance of <code>SOAPElementFactory</code>.
+     * Creates a new instance of {@code SOAPElementFactory}.
      *
-     * @return a new instance of a <code>SOAPElementFactory</code>
+     * @return a new instance of a {@code SOAPElementFactory}
      *
      * @exception SOAPException if there was an error creating the
-     *            default <code>SOAPElementFactory</code>
+     *            default {@code SOAPElementFactory}
      */
     public static SOAPElementFactory newInstance() throws SOAPException {
         try {
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPEnvelope.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPEnvelope.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -28,87 +28,87 @@
 
 /**
  * The container for the SOAPHeader and SOAPBody portions of a
- * <code>SOAPPart</code> object. By default, a <code>SOAPMessage</code>
- * object is created with a <code>SOAPPart</code> object that has a
- * <code>SOAPEnvelope</code> object. The <code>SOAPEnvelope</code> object
- * by default has an empty <code>SOAPBody</code> object and an empty
- * <code>SOAPHeader</code> object.  The <code>SOAPBody</code> object is
- * required, and the <code>SOAPHeader</code> object, though
+ * {@code SOAPPart} object. By default, a {@code SOAPMessage}
+ * object is created with a {@code SOAPPart} object that has a
+ * {@code SOAPEnvelope} object. The {@code SOAPEnvelope} object
+ * by default has an empty {@code SOAPBody} object and an empty
+ * {@code SOAPHeader} object.  The {@code SOAPBody} object is
+ * required, and the {@code SOAPHeader} object, though
  * optional, is used in the majority of cases. If the
- * <code>SOAPHeader</code> object is not needed, it can be deleted,
+ * {@code SOAPHeader} object is not needed, it can be deleted,
  * which is shown later.
  * <P>
- * A client can access the <code>SOAPHeader</code> and <code>SOAPBody</code>
- * objects by calling the methods <code>SOAPEnvelope.getHeader</code> and
- * <code>SOAPEnvelope.getBody</code>. The
+ * A client can access the {@code SOAPHeader} and {@code SOAPBody}
+ * objects by calling the methods {@code SOAPEnvelope.getHeader} and
+ * {@code SOAPEnvelope.getBody}. The
  * following  lines of code use these two methods after starting with
- * the <code>SOAPMessage</code>
- * object <i>message</i> to get the <code>SOAPPart</code> object <i>sp</i>,
- * which is then used to get the <code>SOAPEnvelope</code> object <i>se</i>.
+ * the {@code SOAPMessage}
+ * object <i>message</i> to get the {@code SOAPPart} object <i>sp</i>,
+ * which is then used to get the {@code SOAPEnvelope} object <i>se</i>.
  *
- * <PRE>
+ * <pre>{@code
  *     SOAPPart sp = message.getSOAPPart();
  *     SOAPEnvelope se = sp.getEnvelope();
  *     SOAPHeader sh = se.getHeader();
  *     SOAPBody sb = se.getBody();
- * </PRE>
+ * }</pre>
  * <P>
- * It is possible to change the body or header of a <code>SOAPEnvelope</code>
+ * It is possible to change the body or header of a {@code SOAPEnvelope}
  * object by retrieving the current one, deleting it, and then adding
- * a new body or header. The <code>javax.xml.soap.Node</code> method
- * <code>deleteNode</code> deletes the XML element (node) on which it is
+ * a new body or header. The {@code javax.xml.soap.Node} method
+ * {@code deleteNode} deletes the XML element (node) on which it is
  * called.  For example, the following line of code deletes the
- * <code>SOAPBody</code> object that is retrieved by the method <code>getBody</code>.
- * <PRE>
+ * {@code SOAPBody} object that is retrieved by the method {@code getBody}.
+ * <pre>{@code
  *      se.getBody().detachNode();
- * </PRE>
- * To create a <code>SOAPHeader</code> object to replace the one that was removed,
+ * }</pre>
+ * To create a {@code SOAPHeader} object to replace the one that was removed,
  * a client uses
- * the method <code>SOAPEnvelope.addHeader</code>, which creates a new header and
- * adds it to the <code>SOAPEnvelope</code> object. Similarly, the method
- * <code>addBody</code> creates a new <code>SOAPBody</code> object and adds
- * it to the <code>SOAPEnvelope</code> object. The following code fragment
+ * the method {@code SOAPEnvelope.addHeader}, which creates a new header and
+ * adds it to the {@code SOAPEnvelope} object. Similarly, the method
+ * {@code addBody} creates a new {@code SOAPBody} object and adds
+ * it to the {@code SOAPEnvelope} object. The following code fragment
  * retrieves the current header, removes it, and adds a new one. Then
  * it retrieves the current body, removes it, and adds a new one.
  *
- * <PRE>
+ * <pre>{@code
  *     SOAPPart sp = message.getSOAPPart();
  *     SOAPEnvelope se = sp.getEnvelope();
  *     se.getHeader().detachNode();
  *     SOAPHeader sh = se.addHeader();
  *     se.getBody().detachNode();
  *     SOAPBody sb = se.addBody();
- * </PRE>
- * It is an error to add a <code>SOAPBody</code> or <code>SOAPHeader</code>
+ * }</pre>
+ * It is an error to add a {@code SOAPBody} or {@code SOAPHeader}
  * object if one already exists.
  * <P>
- * The <code>SOAPEnvelope</code> interface provides three methods for creating
- * <code>Name</code> objects. One method creates <code>Name</code> objects with
+ * The {@code SOAPEnvelope} interface provides three methods for creating
+ * {@code Name} objects. One method creates {@code Name} objects with
  * a local name, a namespace prefix, and a namesapce URI. The second method creates
- * <code>Name</code> objects with a local name and a namespace prefix, and the third
- * creates <code>Name</code> objects with just a local name.  The following line of
- * code, in which <i>se</i> is a <code>SOAPEnvelope</code> object, creates a new
- * <code>Name</code> object with all three.
- * <PRE>
+ * {@code Name} objects with a local name and a namespace prefix, and the third
+ * creates {@code Name} objects with just a local name.  The following line of
+ * code, in which <i>se</i> is a {@code SOAPEnvelope} object, creates a new
+ * {@code Name} object with all three.
+ * <pre>{@code
  *     Name name = se.createName("GetLastTradePrice", "WOMBAT",
  *                                "http://www.wombat.org/trader");
- * </PRE>
+ * }</pre>
  *
  * @since 1.6
  */
 public interface SOAPEnvelope extends SOAPElement {
 
     /**
-     * Creates a new <code>Name</code> object initialized with the
+     * Creates a new {@code Name} object initialized with the
      * given local name, namespace prefix, and namespace URI.
      * <P>
-     * This factory method creates <code>Name</code> objects for use in
+     * This factory method creates {@code Name} objects for use in
      * the SOAP/XML document.
      *
-     * @param localName a <code>String</code> giving the local name
-     * @param prefix a <code>String</code> giving the prefix of the namespace
-     * @param uri a <code>String</code> giving the URI of the namespace
-     * @return a <code>Name</code> object initialized with the given
+     * @param localName a {@code String} giving the local name
+     * @param prefix a {@code String} giving the prefix of the namespace
+     * @param uri a {@code String} giving the URI of the namespace
+     * @return a {@code Name} object initialized with the given
      *         local name, namespace prefix, and namespace URI
      * @throws SOAPException if there is a SOAP error
      */
@@ -117,14 +117,14 @@
         throws SOAPException;
 
     /**
-     * Creates a new <code>Name</code> object initialized with the
+     * Creates a new {@code Name} object initialized with the
      * given local name.
      * <P>
-     * This factory method creates <code>Name</code> objects for use in
+     * This factory method creates {@code Name} objects for use in
      * the SOAP/XML document.
      *
-     * @param localName a <code>String</code> giving the local name
-     * @return a <code>Name</code> object initialized with the given
+     * @param localName a {@code String} giving the local name
+     * @return a {@code Name} object initialized with the given
      *         local name
      * @throws SOAPException if there is a SOAP error
      */
@@ -132,71 +132,71 @@
         throws SOAPException;
 
     /**
-     * Returns the <code>SOAPHeader</code> object for
-     * this <code>SOAPEnvelope</code> object.
+     * Returns the {@code SOAPHeader} object for
+     * this {@code SOAPEnvelope} object.
      * <P>
-     * A new <code>SOAPMessage</code> object is by default created with a
-     * <code>SOAPEnvelope</code> object that contains an empty
-     * <code>SOAPHeader</code> object.  As a result, the method
-     * <code>getHeader</code> will always return a <code>SOAPHeader</code>
+     * A new {@code SOAPMessage} object is by default created with a
+     * {@code SOAPEnvelope} object that contains an empty
+     * {@code SOAPHeader} object.  As a result, the method
+     * {@code getHeader} will always return a {@code SOAPHeader}
      * object unless the header has been removed and a new one has not
      * been added.
      *
-     * @return the <code>SOAPHeader</code> object or <code>null</code> if
+     * @return the {@code SOAPHeader} object or {@code null} if
      *         there is none
      * @exception SOAPException if there is a problem obtaining the
-     *            <code>SOAPHeader</code> object
+     *            {@code SOAPHeader} object
      */
     public SOAPHeader getHeader() throws SOAPException;
 
     /**
-     * Returns the <code>SOAPBody</code> object associated with this
-     * <code>SOAPEnvelope</code> object.
+     * Returns the {@code SOAPBody} object associated with this
+     * {@code SOAPEnvelope} object.
      * <P>
-     * A new <code>SOAPMessage</code> object is by default created with a
-     * <code>SOAPEnvelope</code> object that contains an empty
-     * <code>SOAPBody</code> object.  As a result, the method
-     * <code>getBody</code> will always return a <code>SOAPBody</code>
+     * A new {@code SOAPMessage} object is by default created with a
+     * {@code SOAPEnvelope} object that contains an empty
+     * {@code SOAPBody} object.  As a result, the method
+     * {@code getBody} will always return a {@code SOAPBody}
      * object unless the body has been removed and a new one has not
      * been added.
      *
-     * @return the <code>SOAPBody</code> object for this
-     *         <code>SOAPEnvelope</code> object or <code>null</code>
+     * @return the {@code SOAPBody} object for this
+     *         {@code SOAPEnvelope} object or {@code null}
      *         if there is none
      * @exception SOAPException if there is a problem obtaining the
-     *            <code>SOAPBody</code> object
+     *            {@code SOAPBody} object
      */
     public SOAPBody getBody() throws SOAPException;
     /**
-     * Creates a <code>SOAPHeader</code> object and sets it as the
-     * <code>SOAPHeader</code> object for this <code>SOAPEnvelope</code>
+     * Creates a {@code SOAPHeader} object and sets it as the
+     * {@code SOAPHeader} object for this {@code SOAPEnvelope}
      * object.
      * <P>
      * It is illegal to add a header when the envelope already
      * contains a header.  Therefore, this method should be called
      * only after the existing header has been removed.
      *
-     * @return the new <code>SOAPHeader</code> object
+     * @return the new {@code SOAPHeader} object
      *
      * @exception SOAPException if this
-     *            <code>SOAPEnvelope</code> object already contains a
-     *            valid <code>SOAPHeader</code> object
+     *            {@code SOAPEnvelope} object already contains a
+     *            valid {@code SOAPHeader} object
      */
     public SOAPHeader addHeader() throws SOAPException;
     /**
-     * Creates a <code>SOAPBody</code> object and sets it as the
-     * <code>SOAPBody</code> object for this <code>SOAPEnvelope</code>
+     * Creates a {@code SOAPBody} object and sets it as the
+     * {@code SOAPBody} object for this {@code SOAPEnvelope}
      * object.
      * <P>
      * It is illegal to add a body when the envelope already
      * contains a body. Therefore, this method should be called
      * only after the existing body has been removed.
      *
-     * @return the new <code>SOAPBody</code> object
+     * @return the new {@code SOAPBody} object
      *
      * @exception SOAPException if this
-     *            <code>SOAPEnvelope</code> object already contains a
-     *            valid <code>SOAPBody</code> object
+     *            {@code SOAPEnvelope} object already contains a
+     *            valid {@code SOAPBody} object
      */
     public SOAPBody addBody() throws SOAPException;
 }
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPException.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPException.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -27,16 +27,16 @@
 
 /**
  * An exception that signals that a SOAP exception has occurred. A
- * <code>SOAPException</code> object may contain a <code>String</code>
+ * {@code SOAPException} object may contain a {@code String}
  * that gives the reason for the exception, an embedded
- * <code>Throwable</code> object, or both. This class provides methods
+ * {@code Throwable} object, or both. This class provides methods
  * for retrieving reason messages and for retrieving the embedded
- * <code>Throwable</code> object.
+ * {@code Throwable} object.
  *
- * <P> Typical reasons for throwing a <code>SOAPException</code>
+ * <P> Typical reasons for throwing a {@code SOAPException}
  * object are problems such as difficulty setting a header, not being
  * able to send a message, and not being able to get a connection with
- * the provider.  Reasons for embedding a <code>Throwable</code>
+ * the provider.  Reasons for embedding a {@code Throwable}
  * object include problems such as input/output errors or a parsing
  * problem, such as an error in parsing a header.
  *
@@ -46,8 +46,8 @@
     private Throwable cause;
 
     /**
-     * Constructs a <code>SOAPException</code> object with no
-     * reason or embedded <code>Throwable</code> object.
+     * Constructs a {@code SOAPException} object with no
+     * reason or embedded {@code Throwable} object.
      */
     public SOAPException() {
         super();
@@ -55,8 +55,8 @@
     }
 
     /**
-     * Constructs a <code>SOAPException</code> object with the given
-     * <code>String</code> as the reason for the exception being thrown.
+     * Constructs a {@code SOAPException} object with the given
+     * {@code String} as the reason for the exception being thrown.
      *
      * @param reason a description of what caused the exception
      */
@@ -66,14 +66,14 @@
     }
 
     /**
-     * Constructs a <code>SOAPException</code> object with the given
-     * <code>String</code> as the reason for the exception being thrown
-     * and the given <code>Throwable</code> object as an embedded
+     * Constructs a {@code SOAPException} object with the given
+     * {@code String} as the reason for the exception being thrown
+     * and the given {@code Throwable} object as an embedded
      * exception.
      *
      * @param reason a description of what caused the exception
-     * @param cause a <code>Throwable</code> object that is to
-     *        be embedded in this <code>SOAPException</code> object
+     * @param cause a {@code Throwable} object that is to
+     *        be embedded in this {@code SOAPException} object
      */
     public SOAPException(String reason, Throwable cause) {
         super(reason);
@@ -81,8 +81,8 @@
     }
 
     /**
-     * Constructs a <code>SOAPException</code> object initialized
-     * with the given <code>Throwable</code> object.
+     * Constructs a {@code SOAPException} object initialized
+     * with the given {@code Throwable} object.
      */
     public SOAPException(Throwable cause) {
         super(cause.toString());
@@ -90,17 +90,17 @@
     }
 
     /**
-     * Returns the detail message for this <code>SOAPException</code>
+     * Returns the detail message for this {@code SOAPException}
      * object.
      * <P>
-     * If there is an embedded <code>Throwable</code> object, and if the
-     * <code>SOAPException</code> object has no detail message of its
+     * If there is an embedded {@code Throwable} object, and if the
+     * {@code SOAPException} object has no detail message of its
      * own, this method will return the detail message from the embedded
-     * <code>Throwable</code> object.
+     * {@code Throwable} object.
      *
      * @return the error or warning message for this
-     *         <code>SOAPException</code> or, if it has none, the
-     *         message of the embedded <code>Throwable</code> object,
+     *         {@code SOAPException} or, if it has none, the
+     *         message of the embedded {@code Throwable} object,
      *         if there is one
      */
     public String getMessage() {
@@ -113,11 +113,11 @@
     }
 
     /**
-     * Returns the <code>Throwable</code> object embedded in this
-     * <code>SOAPException</code> if there is one. Otherwise, this method
-     * returns <code>null</code>.
+     * Returns the {@code Throwable} object embedded in this
+     * {@code SOAPException} if there is one. Otherwise, this method
+     * returns {@code null}.
      *
-     * @return the embedded <code>Throwable</code> object or <code>null</code>
+     * @return the embedded {@code Throwable} object or {@code null}
      *         if there is none
      */
 
@@ -126,29 +126,29 @@
     }
 
     /**
-     * Initializes the <code>cause</code> field of this <code>SOAPException</code>
-     * object with the given <code>Throwable</code> object.
+     * Initializes the {@code cause} field of this {@code SOAPException}
+     * object with the given {@code Throwable} object.
      * <P>
      * This method can be called at most once.  It is generally called from
      * within the constructor or immediately after the constructor has
-     * returned a new <code>SOAPException</code> object.
-     * If this <code>SOAPException</code> object was created with the
+     * returned a new {@code SOAPException} object.
+     * If this {@code SOAPException} object was created with the
      * constructor {@link #SOAPException(Throwable)} or
      * {@link #SOAPException(String,Throwable)}, meaning that its
-     * <code>cause</code> field already has a value, this method cannot be
+     * {@code cause} field already has a value, this method cannot be
      * called even once.
      *
-     * @param  cause the <code>Throwable</code> object that caused this
-     *         <code>SOAPException</code> object to be thrown.  The value of this
+     * @param  cause the {@code Throwable} object that caused this
+     *         {@code SOAPException} object to be thrown.  The value of this
      *         parameter is saved for later retrieval by the
      *         {@link #getCause()} method.  A <tt>null</tt> value is
      *         permitted and indicates that the cause is nonexistent or
      *         unknown.
-     * @return  a reference to this <code>SOAPException</code> instance
-     * @throws IllegalArgumentException if <code>cause</code> is this
-     *         <code>Throwable</code> object.  (A <code>Throwable</code> object
+     * @return  a reference to this {@code SOAPException} instance
+     * @throws IllegalArgumentException if {@code cause} is this
+     *         {@code Throwable} object.  (A {@code Throwable} object
      *         cannot be its own cause.)
-     * @throws IllegalStateException if the cause for this <code>SOAPException</code> object
+     * @throws IllegalStateException if the cause for this {@code SOAPException} object
      *         has already been initialized
      */
     public synchronized Throwable initCause(Throwable cause) {
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPFactory.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPFactory.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -30,18 +30,18 @@
 import org.w3c.dom.Element;
 
 /**
- * <code>SOAPFactory</code> is a factory for creating various objects
+ * {@code SOAPFactory} is a factory for creating various objects
  * that exist in the SOAP XML tree.
 
- * <code>SOAPFactory</code> can be
+ * {@code SOAPFactory} can be
  * used to create XML fragments that will eventually end up in the
  * SOAP part. These fragments can be inserted as children of the
  * {@link SOAPHeaderElement} or {@link SOAPBodyElement} or
  * {@link SOAPEnvelope} or other {@link SOAPElement} objects.
  *
- * <code>SOAPFactory</code> also has methods to create
- * <code>javax.xml.soap.Detail</code> objects as well as
- * <code>java.xml.soap.Name</code> objects.
+ * {@code SOAPFactory} also has methods to create
+ * {@code javax.xml.soap.Detail} objects as well as
+ * {@code java.xml.soap.Name} objects.
  *
  * @since 1.6
  */
@@ -49,34 +49,34 @@
 
     /**
      * A constant representing the property used to lookup the name of
-     * a <code>SOAPFactory</code> implementation class.
+     * a {@code SOAPFactory} implementation class.
      */
     static private final String SOAP_FACTORY_PROPERTY =
         "javax.xml.soap.SOAPFactory";
 
     /**
-     * Class name of default <code>SOAPFactory</code> implementation.
+     * Class name of default {@code SOAPFactory} implementation.
      */
     static final String DEFAULT_SOAP_FACTORY
         = "com.sun.xml.internal.messaging.saaj.soap.ver1_1.SOAPFactory1_1Impl";
 
     /**
-     * Creates a <code>SOAPElement</code> object from an existing DOM
-     * <code>Element</code>. If the DOM <code>Element</code> that is passed in
-     * as an argument is already a <code>SOAPElement</code> then this method
+     * Creates a {@code SOAPElement} object from an existing DOM
+     * {@code Element}. If the DOM {@code Element} that is passed in
+     * as an argument is already a {@code SOAPElement} then this method
      * must return it unmodified without any further work. Otherwise, a new
-     * <code>SOAPElement</code> is created and a deep copy is made of the
-     * <code>domElement</code> argument. The concrete type of the return value
-     * will depend on the name of the <code>domElement</code> argument. If any
-     * part of the tree rooted in <code>domElement</code> violates SOAP rules, a
-     * <code>SOAPException</code> will be thrown.
+     * {@code SOAPElement} is created and a deep copy is made of the
+     * {@code domElement} argument. The concrete type of the return value
+     * will depend on the name of the {@code domElement} argument. If any
+     * part of the tree rooted in {@code domElement} violates SOAP rules, a
+     * {@code SOAPException} will be thrown.
      *
-     * @param domElement - the <code>Element</code> to be copied.
+     * @param domElement - the {@code Element} to be copied.
      *
-     * @return a new <code>SOAPElement</code> that is a copy of <code>domElement</code>.
+     * @return a new {@code SOAPElement} that is a copy of {@code domElement}.
      *
      * @exception SOAPException if there is an error in creating the
-     *            <code>SOAPElement</code> object
+     *            {@code SOAPElement} object
      *
      * @since 1.6, SAAJ 1.3
      */
@@ -85,41 +85,41 @@
     }
 
     /**
-     * Creates a <code>SOAPElement</code> object initialized with the
-     * given <code>Name</code> object. The concrete type of the return value
-     * will depend on the name given to the new <code>SOAPElement</code>. For
-     * instance, a new <code>SOAPElement</code> with the name
+     * Creates a {@code SOAPElement} object initialized with the
+     * given {@code Name} object. The concrete type of the return value
+     * will depend on the name given to the new {@code SOAPElement}. For
+     * instance, a new {@code SOAPElement} with the name
      * "{http://www.w3.org/2003/05/soap-envelope}Envelope" would cause a
-     * <code>SOAPEnvelope</code> that supports SOAP 1.2 behavior to be created.
+     * {@code SOAPEnvelope} that supports SOAP 1.2 behavior to be created.
      *
-     * @param name a <code>Name</code> object with the XML name for
+     * @param name a {@code Name} object with the XML name for
      *             the new element
      *
-     * @return the new <code>SOAPElement</code> object that was
+     * @return the new {@code SOAPElement} object that was
      *         created
      *
      * @exception SOAPException if there is an error in creating the
-     *            <code>SOAPElement</code> object
+     *            {@code SOAPElement} object
      * @see SOAPFactory#createElement(javax.xml.namespace.QName)
      */
     public abstract SOAPElement createElement(Name name) throws SOAPException;
 
     /**
-     * Creates a <code>SOAPElement</code> object initialized with the
-     * given <code>QName</code> object. The concrete type of the return value
-     * will depend on the name given to the new <code>SOAPElement</code>. For
-     * instance, a new <code>SOAPElement</code> with the name
+     * Creates a {@code SOAPElement} object initialized with the
+     * given {@code QName} object. The concrete type of the return value
+     * will depend on the name given to the new {@code SOAPElement}. For
+     * instance, a new {@code SOAPElement} with the name
      * "{http://www.w3.org/2003/05/soap-envelope}Envelope" would cause a
-     * <code>SOAPEnvelope</code> that supports SOAP 1.2 behavior to be created.
+     * {@code SOAPEnvelope} that supports SOAP 1.2 behavior to be created.
      *
-     * @param qname a <code>QName</code> object with the XML name for
+     * @param qname a {@code QName} object with the XML name for
      *             the new element
      *
-     * @return the new <code>SOAPElement</code> object that was
+     * @return the new {@code SOAPElement} object that was
      *         created
      *
      * @exception SOAPException if there is an error in creating the
-     *            <code>SOAPElement</code> object
+     *            {@code SOAPElement} object
      * @see SOAPFactory#createElement(Name)
      * @since 1.6, SAAJ 1.3
      */
@@ -128,38 +128,38 @@
     }
 
     /**
-     * Creates a <code>SOAPElement</code> object initialized with the
+     * Creates a {@code SOAPElement} object initialized with the
      * given local name.
      *
-     * @param localName a <code>String</code> giving the local name for
+     * @param localName a {@code String} giving the local name for
      *             the new element
      *
-     * @return the new <code>SOAPElement</code> object that was
+     * @return the new {@code SOAPElement} object that was
      *         created
      *
      * @exception SOAPException if there is an error in creating the
-     *            <code>SOAPElement</code> object
+     *            {@code SOAPElement} object
      */
     public abstract SOAPElement createElement(String localName)
         throws SOAPException;
 
 
     /**
-     * Creates a new <code>SOAPElement</code> object with the given
+     * Creates a new {@code SOAPElement} object with the given
      * local name, prefix and uri. The concrete type of the return value
-     * will depend on the name given to the new <code>SOAPElement</code>. For
-     * instance, a new <code>SOAPElement</code> with the name
+     * will depend on the name given to the new {@code SOAPElement}. For
+     * instance, a new {@code SOAPElement} with the name
      * "{http://www.w3.org/2003/05/soap-envelope}Envelope" would cause a
-     * <code>SOAPEnvelope</code> that supports SOAP 1.2 behavior to be created.
+     * {@code SOAPEnvelope} that supports SOAP 1.2 behavior to be created.
      *
-     * @param localName a <code>String</code> giving the local name
+     * @param localName a {@code String} giving the local name
      *                  for the new element
-     * @param prefix the prefix for this <code>SOAPElement</code>
-     * @param uri a <code>String</code> giving the URI of the
+     * @param prefix the prefix for this {@code SOAPElement}
+     * @param uri a {@code String} giving the URI of the
      *            namespace to which the new element belongs
      *
      * @exception SOAPException if there is an error in creating the
-     *            <code>SOAPElement</code> object
+     *            {@code SOAPElement} object
      */
     public abstract SOAPElement createElement(
         String localName,
@@ -168,51 +168,51 @@
         throws SOAPException;
 
     /**
-     * Creates a new <code>Detail</code> object which serves as a container
-     * for <code>DetailEntry</code> objects.
+     * Creates a new {@code Detail} object which serves as a container
+     * for {@code DetailEntry} objects.
      * <P>
-     * This factory method creates <code>Detail</code> objects for use in
-     * situations where it is not practical to use the <code>SOAPFault</code>
+     * This factory method creates {@code Detail} objects for use in
+     * situations where it is not practical to use the {@code SOAPFault}
      * abstraction.
      *
-     * @return a <code>Detail</code> object
+     * @return a {@code Detail} object
      * @throws SOAPException if there is a SOAP error
      * @throws UnsupportedOperationException if the protocol specified
-     *         for the SOAPFactory was <code>DYNAMIC_SOAP_PROTOCOL</code>
+     *         for the SOAPFactory was {@code DYNAMIC_SOAP_PROTOCOL}
      */
     public abstract Detail createDetail() throws SOAPException;
 
     /**
-     *Creates a new <code>SOAPFault</code> object initialized with the given <code>reasonText</code>
-     *  and <code>faultCode</code>
+     *Creates a new {@code SOAPFault} object initialized with the given {@code reasonText}
+     *  and {@code faultCode}
      *@param reasonText the ReasonText/FaultString for the fault
      *@param faultCode the FaultCode for the fault
-     *@return a <code>SOAPFault</code> object
+     *@return a {@code SOAPFault} object
      *@throws SOAPException if there is a SOAP error
      *@since 1.6, SAAJ 1.3
      */
     public abstract SOAPFault createFault(String reasonText, QName faultCode) throws SOAPException;
 
     /**
-     *Creates a new default <code>SOAPFault</code> object
-     *@return a <code>SOAPFault</code> object
+     *Creates a new default {@code SOAPFault} object
+     *@return a {@code SOAPFault} object
      *@throws SOAPException if there is a SOAP error
      *@since 1.6, SAAJ 1.3
      */
     public abstract SOAPFault createFault() throws SOAPException;
 
     /**
-     * Creates a new <code>Name</code> object initialized with the
+     * Creates a new {@code Name} object initialized with the
      * given local name, namespace prefix, and namespace URI.
      * <P>
-     * This factory method creates <code>Name</code> objects for use in
-     * situations where it is not practical to use the <code>SOAPEnvelope</code>
+     * This factory method creates {@code Name} objects for use in
+     * situations where it is not practical to use the {@code SOAPEnvelope}
      * abstraction.
      *
-     * @param localName a <code>String</code> giving the local name
-     * @param prefix a <code>String</code> giving the prefix of the namespace
-     * @param uri a <code>String</code> giving the URI of the namespace
-     * @return a <code>Name</code> object initialized with the given
+     * @param localName a {@code String} giving the local name
+     * @param prefix a {@code String} giving the prefix of the namespace
+     * @param uri a {@code String} giving the URI of the namespace
+     * @return a {@code Name} object initialized with the given
      *         local name, namespace prefix, and namespace URI
      * @throws SOAPException if there is a SOAP error
      */
@@ -223,22 +223,22 @@
         throws SOAPException;
 
     /**
-     * Creates a new <code>Name</code> object initialized with the
+     * Creates a new {@code Name} object initialized with the
      * given local name.
      * <P>
-     * This factory method creates <code>Name</code> objects for use in
-     * situations where it is not practical to use the <code>SOAPEnvelope</code>
+     * This factory method creates {@code Name} objects for use in
+     * situations where it is not practical to use the {@code SOAPEnvelope}
      * abstraction.
      *
-     * @param localName a <code>String</code> giving the local name
-     * @return a <code>Name</code> object initialized with the given
+     * @param localName a {@code String} giving the local name
+     * @return a {@code Name} object initialized with the given
      *         local name
      * @throws SOAPException if there is a SOAP error
      */
     public abstract Name createName(String localName) throws SOAPException;
 
     /**
-     * Creates a new <code>SOAPFactory</code> object that is an instance of
+     * Creates a new {@code SOAPFactory} object that is an instance of
      * the default implementation (SOAP 1.1),
      *
      * This method uses the following ordered lookup procedure to determine the SOAPFactory implementation class to load:
@@ -252,10 +252,10 @@
      *  <LI> Use the SAAJMetaFactory instance to locate the SOAPFactory implementation class.
      * </UL>
      *
-     * @return a new instance of a <code>SOAPFactory</code>
+     * @return a new instance of a {@code SOAPFactory}
      *
      * @exception SOAPException if there was an error creating the
-     *            default <code>SOAPFactory</code>
+     *            default {@code SOAPFactory}
      * @see SAAJMetaFactory
      */
     public static SOAPFactory newInstance()
@@ -275,21 +275,21 @@
     }
 
     /**
-     * Creates a new <code>SOAPFactory</code> object that is an instance of
+     * Creates a new {@code SOAPFactory} object that is an instance of
      * the specified implementation, this method uses the SAAJMetaFactory to
      * locate the implementation class and create the SOAPFactory instance.
      *
-     * @return a new instance of a <code>SOAPFactory</code>
+     * @return a new instance of a {@code SOAPFactory}
      *
      * @param protocol  a string constant representing the protocol of the
      *                   specified SOAP factory implementation. May be
-     *                   either <code>DYNAMIC_SOAP_PROTOCOL</code>,
-     *                   <code>DEFAULT_SOAP_PROTOCOL</code> (which is the same
-     *                   as) <code>SOAP_1_1_PROTOCOL</code>, or
-     *                   <code>SOAP_1_2_PROTOCOL</code>.
+     *                   either {@code DYNAMIC_SOAP_PROTOCOL},
+     *                   {@code DEFAULT_SOAP_PROTOCOL} (which is the same
+     *                   as) {@code SOAP_1_1_PROTOCOL}, or
+     *                   {@code SOAP_1_2_PROTOCOL}.
      *
      * @exception SOAPException if there was an error creating the
-     *            specified <code>SOAPFactory</code>
+     *            specified {@code SOAPFactory}
      * @see SAAJMetaFactory
      * @since 1.6, SAAJ 1.3
      */
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPFault.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPFault.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -31,16 +31,16 @@
 import javax.xml.namespace.QName;
 
 /**
- * An element in the <code>SOAPBody</code> object that contains
+ * An element in the {@code SOAPBody} object that contains
  * error and/or status information. This information may relate to
- * errors in the <code>SOAPMessage</code> object or to problems
+ * errors in the {@code SOAPMessage} object or to problems
  * that are not related to the content in the message itself. Problems
  * not related to the message itself are generally errors in
  * processing, such as the inability to communicate with an upstream
  * server.
  * <P>
- * Depending on the <code>protocol</code> specified while creating the
- * <code>MessageFactory</code> instance,  a <code>SOAPFault</code> has
+ * Depending on the {@code protocol} specified while creating the
+ * {@code MessageFactory} instance,  a {@code SOAPFault} has
  * sub-elements as defined in the SOAP 1.1/SOAP 1.2 specification.
  *
  * @since 1.6
@@ -48,14 +48,14 @@
 public interface SOAPFault extends SOAPBodyElement {
 
     /**
-     * Sets this <code>SOAPFault</code> object with the given fault code.
+     * Sets this {@code SOAPFault} object with the given fault code.
      *
      * <P> Fault codes, which give information about the fault, are defined
      * in the SOAP 1.1 specification. A fault code is mandatory and must
-     * be of type <code>Name</code>. This method provides a convenient
+     * be of type {@code Name}. This method provides a convenient
      * way to set a fault code. For example,
      *
-     * <PRE>
+     * <pre>{@code
      * SOAPEnvelope se = ...;
      * // Create a qualified name in the SOAP namespace with a localName
      * // of "Client". Note that prefix parameter is optional and is null
@@ -64,10 +64,10 @@
      *                            SOAPConstants.URI_NS_SOAP_ENVELOPE);
      * SOAPFault fault = ...;
      * fault.setFaultCode(qname);
-     * </PRE>
+     * }</pre>
      * It is preferable to use this method over {@link #setFaultCode(String)}.
      *
-     * @param faultCodeQName a <code>Name</code> object giving the fault
+     * @param faultCodeQName a {@code Name} object giving the fault
      * code to be set. It must be namespace qualified.
      * @see #getFaultCodeAsName
      *
@@ -79,16 +79,16 @@
     public void setFaultCode(Name faultCodeQName) throws SOAPException;
 
     /**
-     * Sets this <code>SOAPFault</code> object with the given fault code.
+     * Sets this {@code SOAPFault} object with the given fault code.
      *
      * It is preferable to use this method over {@link #setFaultCode(Name)}.
      *
-     * @param faultCodeQName a <code>QName</code> object giving the fault
+     * @param faultCodeQName a {@code QName} object giving the fault
      * code to be set. It must be namespace qualified.
      * @see #getFaultCodeAsQName
      *
      * @exception SOAPException if there was an error in adding the
-     *            <code>faultcode</code> element to the underlying XML tree.
+     *            {@code faultcode} element to the underlying XML tree.
      *
      * @see #setFaultCode(Name)
      * @see #getFaultCodeAsQName()
@@ -98,14 +98,14 @@
     public void setFaultCode(QName faultCodeQName) throws SOAPException;
 
     /**
-     * Sets this <code>SOAPFault</code> object with the give fault code.
+     * Sets this {@code SOAPFault} object with the give fault code.
      * <P>
      * Fault codes, which given information about the fault, are defined in
      * the SOAP 1.1 specification. This element is mandatory in SOAP 1.1.
      * Because the fault code is required to be a QName it is preferable to
      * use the {@link #setFaultCode(Name)} form of this method.
      *
-     * @param faultCode a <code>String</code> giving the fault code to be set.
+     * @param faultCode a {@code String} giving the fault code to be set.
      *         It must be of the form "prefix:localName" where the prefix has
      *         been defined in a namespace declaration.
      * @see #setFaultCode(Name)
@@ -113,21 +113,21 @@
      * @see SOAPElement#addNamespaceDeclaration
      *
      * @exception SOAPException if there was an error in adding the
-     *            <code>faultCode</code> to the underlying XML tree.
+     *            {@code faultCode} to the underlying XML tree.
      */
     public void setFaultCode(String faultCode) throws SOAPException;
 
     /**
      * Gets the mandatory SOAP 1.1 fault code for this
-     * <code>SOAPFault</code> object as a SAAJ <code>Name</code> object.
+     * {@code SOAPFault} object as a SAAJ {@code Name} object.
      * The SOAP 1.1 specification requires the value of the "faultcode"
      * element to be of type QName. This method returns the content of the
      * element as a QName in the form of a SAAJ Name object. This method
-     * should be used instead of the <code>getFaultCode</code> method since
+     * should be used instead of the {@code getFaultCode} method since
      * it allows applications to easily access the namespace name without
      * additional parsing.
      *
-     * @return a <code>Name</code> representing the faultcode
+     * @return a {@code Name} representing the faultcode
      * @see #setFaultCode(Name)
      *
      * @since 1.6, SAAJ 1.2
@@ -137,9 +137,9 @@
 
     /**
      * Gets the fault code for this
-     * <code>SOAPFault</code> object as a <code>QName</code> object.
+     * {@code SOAPFault} object as a {@code QName} object.
      *
-     * @return a <code>QName</code> representing the faultcode
+     * @return a {@code QName} representing the faultcode
      *
      * @see #setFaultCode(QName)
      *
@@ -148,12 +148,12 @@
     public QName getFaultCodeAsQName();
 
     /**
-     * Gets the Subcodes for this <code>SOAPFault</code> as an iterator over
-     * <code>QNames</code>.
+     * Gets the Subcodes for this {@code SOAPFault} as an iterator over
+     * {@code QNames}.
      *
-     * @return an <code>Iterator</code> that accesses a sequence of
-     *      <code>QNames</code>. This <code>Iterator</code> should not support
-     *      the optional <code>remove</code> method. The order in which the
+     * @return an {@code Iterator} that accesses a sequence of
+     *      {@code QNames}. This {@code Iterator} should not support
+     *      the optional {@code remove} method. The order in which the
      *      Subcodes are returned reflects the hierarchy of Subcodes present
      *      in the fault from top to bottom.
      *
@@ -166,9 +166,9 @@
 
     /**
      * Removes any Subcodes that may be contained by this
-     * <code>SOAPFault</code>. Subsequent calls to
-     * <code>getFaultSubcodes</code> will return an empty iterator until a call
-     * to <code>appendFaultSubcode</code> is made.
+     * {@code SOAPFault}. Subsequent calls to
+     * {@code getFaultSubcodes} will return an empty iterator until a call
+     * to {@code appendFaultSubcode} is made.
      *
      * @exception UnsupportedOperationException if this message does not
      *      support the SOAP 1.2 concept of Subcode.
@@ -179,7 +179,7 @@
 
     /**
      * Adds a Subcode to the end of the sequence of Subcodes contained by this
-     * <code>SOAPFault</code>. Subcodes, which were introduced in SOAP 1.2, are
+     * {@code SOAPFault}. Subcodes, which were introduced in SOAP 1.2, are
      * represented by a recursive sequence of subelements rooted in the
      * mandatory Code subelement of a SOAP Fault.
      *
@@ -194,83 +194,83 @@
     public void appendFaultSubcode(QName subcode) throws SOAPException;
 
     /**
-     * Gets the fault code for this <code>SOAPFault</code> object.
+     * Gets the fault code for this {@code SOAPFault} object.
      *
-     * @return a <code>String</code> with the fault code
+     * @return a {@code String} with the fault code
      * @see #getFaultCodeAsName
      * @see #setFaultCode
      */
     public String getFaultCode();
 
     /**
-     * Sets this <code>SOAPFault</code> object with the given fault actor.
+     * Sets this {@code SOAPFault} object with the given fault actor.
      * <P>
      * The fault actor is the recipient in the message path who caused the
      * fault to happen.
      * <P>
-     * If this <code>SOAPFault</code> supports SOAP 1.2 then this call is
+     * If this {@code SOAPFault} supports SOAP 1.2 then this call is
      * equivalent to {@link #setFaultRole(String)}
      *
-     * @param faultActor a <code>String</code> identifying the actor that
-     *        caused this <code>SOAPFault</code> object
+     * @param faultActor a {@code String} identifying the actor that
+     *        caused this {@code SOAPFault} object
      * @see #getFaultActor
      *
      * @exception SOAPException if there was an error in adding the
-     *            <code>faultActor</code> to the underlying XML tree.
+     *            {@code faultActor} to the underlying XML tree.
      */
     public void setFaultActor(String faultActor) throws SOAPException;
 
     /**
-     * Gets the fault actor for this <code>SOAPFault</code> object.
+     * Gets the fault actor for this {@code SOAPFault} object.
      * <P>
-     * If this <code>SOAPFault</code> supports SOAP 1.2 then this call is
+     * If this {@code SOAPFault} supports SOAP 1.2 then this call is
      * equivalent to {@link #getFaultRole()}
      *
-     * @return a <code>String</code> giving the actor in the message path
-     *         that caused this <code>SOAPFault</code> object
+     * @return a {@code String} giving the actor in the message path
+     *         that caused this {@code SOAPFault} object
      * @see #setFaultActor
      */
     public String getFaultActor();
 
     /**
-     * Sets the fault string for this <code>SOAPFault</code> object
+     * Sets the fault string for this {@code SOAPFault} object
      * to the given string.
      * <P>
      * If this
-     * <code>SOAPFault</code> is part of a message that supports SOAP 1.2 then
+     * {@code SOAPFault} is part of a message that supports SOAP 1.2 then
      * this call is equivalent to:
-     * <pre>
+     * <pre>{@code
      *      addFaultReasonText(faultString, Locale.getDefault());
-     * </pre>
+     * }</pre>
      *
-     * @param faultString a <code>String</code> giving an explanation of
+     * @param faultString a {@code String} giving an explanation of
      *        the fault
      * @see #getFaultString
      *
      * @exception SOAPException if there was an error in adding the
-     *            <code>faultString</code> to the underlying XML tree.
+     *            {@code faultString} to the underlying XML tree.
      */
     public void setFaultString(String faultString) throws SOAPException;
 
     /**
-     * Sets the fault string for this <code>SOAPFault</code> object
+     * Sets the fault string for this {@code SOAPFault} object
      * to the given string and localized to the given locale.
      * <P>
      * If this
-     * <code>SOAPFault</code> is part of a message that supports SOAP 1.2 then
+     * {@code SOAPFault} is part of a message that supports SOAP 1.2 then
      * this call is equivalent to:
-     * <pre>
+     * <pre>{@code
      *      addFaultReasonText(faultString, locale);
-     * </pre>
+     * }</pre>
      *
-     * @param faultString a <code>String</code> giving an explanation of
+     * @param faultString a {@code String} giving an explanation of
      *         the fault
      * @param locale a {@link java.util.Locale Locale} object indicating
-     *         the native language of the <code>faultString</code>
+     *         the native language of the {@code faultString}
      * @see #getFaultString
      *
      * @exception SOAPException if there was an error in adding the
-     *            <code>faultString</code> to the underlying XML tree.
+     *            {@code faultString} to the underlying XML tree.
      *
      * @since 1.6, SAAJ 1.2
      */
@@ -278,20 +278,20 @@
         throws SOAPException;
 
     /**
-     * Gets the fault string for this <code>SOAPFault</code> object.
+     * Gets the fault string for this {@code SOAPFault} object.
      * <P>
      * If this
-     * <code>SOAPFault</code> is part of a message that supports SOAP 1.2 then
+     * {@code SOAPFault} is part of a message that supports SOAP 1.2 then
      * this call is equivalent to:
-     * <pre>
+     * <pre>{@code
      *    String reason = null;
      *    try {
      *        reason = (String) getFaultReasonTexts().next();
      *    } catch (SOAPException e) {}
      *    return reason;
-     * </pre>
+     * }</pre>
      *
-     * @return a <code>String</code> giving an explanation of
+     * @return a {@code String} giving an explanation of
      *        the fault
      * @see #setFaultString(String)
      * @see #setFaultString(String, Locale)
@@ -299,22 +299,22 @@
     public String getFaultString();
 
     /**
-     * Gets the locale of the fault string for this <code>SOAPFault</code>
+     * Gets the locale of the fault string for this {@code SOAPFault}
      * object.
      * <P>
      * If this
-     * <code>SOAPFault</code> is part of a message that supports SOAP 1.2 then
+     * {@code SOAPFault} is part of a message that supports SOAP 1.2 then
      * this call is equivalent to:
-     * <pre>
+     * <pre>{@code
      *    Locale locale = null;
      *    try {
      *        locale = (Locale) getFaultReasonLocales().next();
      *    } catch (SOAPException e) {}
      *    return locale;
-     * </pre>
+     * }</pre>
      *
-     * @return a <code>Locale</code> object indicating the native language of
-     *          the fault string or <code>null</code> if no locale was specified
+     * @return a {@code Locale} object indicating the native language of
+     *          the fault string or {@code null} if no locale was specified
      * @see #setFaultString(String, Locale)
      *
      * @since 1.6, SAAJ 1.2
@@ -322,11 +322,11 @@
     public Locale getFaultStringLocale();
 
     /**
-     * Returns true if this <code>SOAPFault</code> has a <code>Detail</code>
+     * Returns true if this {@code SOAPFault} has a {@code Detail}
      * subelement and false otherwise. Equivalent to
-     * <code>(getDetail()!=null)</code>.
+     * {@code (getDetail()!=null)}.
      *
-     * @return true if this <code>SOAPFault</code> has a <code>Detail</code>
+     * @return true if this {@code SOAPFault} has a {@code Detail}
      * subelement and false otherwise.
      *
      * @since 1.6, SAAJ 1.3
@@ -334,44 +334,44 @@
     public boolean hasDetail();
 
     /**
-     * Returns the optional detail element for this <code>SOAPFault</code>
+     * Returns the optional detail element for this {@code SOAPFault}
      * object.
      * <P>
-     * A <code>Detail</code> object carries application-specific error
+     * A {@code Detail} object carries application-specific error
      * information, the scope of the error information is restricted to
-     * faults in the <code>SOAPBodyElement</code> objects if this is a
+     * faults in the {@code SOAPBodyElement} objects if this is a
      * SOAP 1.1 Fault.
      *
-     * @return a <code>Detail</code> object with application-specific
+     * @return a {@code Detail} object with application-specific
      *         error information if present, null otherwise
      */
     public Detail getDetail();
 
     /**
-     * Creates an optional <code>Detail</code> object and sets it as the
-     * <code>Detail</code> object for this <code>SOAPFault</code>
+     * Creates an optional {@code Detail} object and sets it as the
+     * {@code Detail} object for this {@code SOAPFault}
      * object.
      * <P>
      * It is illegal to add a detail when the fault already
      * contains a detail. Therefore, this method should be called
      * only after the existing detail has been removed.
      *
-     * @return the new <code>Detail</code> object
+     * @return the new {@code Detail} object
      *
      * @exception SOAPException if this
-     *            <code>SOAPFault</code> object already contains a
-     *            valid <code>Detail</code> object
+     *            {@code SOAPFault} object already contains a
+     *            valid {@code Detail} object
      */
     public Detail addDetail() throws SOAPException;
 
     /**
-     * Returns an <code>Iterator</code> over a distinct sequence of
-     * <code>Locale</code>s for which there are associated Reason Text items.
-     * Any of these <code>Locale</code>s can be used in a call to
-     * <code>getFaultReasonText</code> in order to obtain a localized version
+     * Returns an {@code Iterator} over a distinct sequence of
+     * {@code Locale}s for which there are associated Reason Text items.
+     * Any of these {@code Locale}s can be used in a call to
+     * {@code getFaultReasonText} in order to obtain a localized version
      * of the Reason Text string.
      *
-     * @return an <code>Iterator</code> over a sequence of <code>Locale</code>
+     * @return an {@code Iterator} over a sequence of {@code Locale}
      *      objects for which there are associated Reason Text items.
      *
      * @exception SOAPException if there was an error in retrieving
@@ -384,11 +384,11 @@
     public Iterator getFaultReasonLocales() throws SOAPException;
 
     /**
-     * Returns an <code>Iterator</code> over a sequence of
-     * <code>String</code> objects containing all of the Reason Text items for
-     * this <code>SOAPFault</code>.
+     * Returns an {@code Iterator} over a sequence of
+     * {@code String} objects containing all of the Reason Text items for
+     * this {@code SOAPFault}.
      *
-     * @return an <code>Iterator</code> over env:Fault/env:Reason/env:Text items.
+     * @return an {@code Iterator} over env:Fault/env:Reason/env:Text items.
      *
      * @exception SOAPException if there was an error in retrieving
      * the  fault Reason texts.
@@ -400,14 +400,14 @@
     public Iterator getFaultReasonTexts() throws SOAPException;
 
     /**
-     * Returns the Reason Text associated with the given <code>Locale</code>.
+     * Returns the Reason Text associated with the given {@code Locale}.
      * If more than one such Reason Text exists the first matching Text is
      * returned
      *
-     * @param locale -- the <code>Locale</code> for which a localized
+     * @param locale -- the {@code Locale} for which a localized
      *      Reason Text is desired
      *
-     * @return the Reason Text associated with <code>locale</code>
+     * @return the Reason Text associated with {@code locale}
      *
      * @see #getFaultString
      *
@@ -423,23 +423,23 @@
     /**
      * Appends or replaces a Reason Text item containing the specified
      * text message and an <i>xml:lang</i> derived from
-     * <code>locale</code>. If a Reason Text item with this
+     * {@code locale}. If a Reason Text item with this
      * <i>xml:lang</i> already exists its text value will be replaced
-     * with <code>text</code>.
-     * The <code>locale</code> parameter should not be <code>null</code>
+     * with {@code text}.
+     * The {@code locale} parameter should not be {@code null}
      * <P>
      * Code sample:
      *
-     * <PRE>
+     * <pre>{@code
      * SOAPFault fault = ...;
      * fault.addFaultReasonText("Version Mismatch", Locale.ENGLISH);
-     * </PRE>
+     * }</pre>
      *
      * @param text -- reason message string
      * @param locale -- Locale object representing the locale of the message
      *
      * @exception SOAPException if there was an error in adding the Reason text
-     * or the <code>locale</code> passed was <code>null</code>.
+     * or the {@code locale} passed was {@code null}.
      * @exception UnsupportedOperationException if this message does not
      *      support the SOAP 1.2 concept of Fault Reason.
      *
@@ -450,11 +450,11 @@
 
     /**
      * Returns the optional Node element value for this
-     * <code>SOAPFault</code> object. The Node element is
+     * {@code SOAPFault} object. The Node element is
      * optional in SOAP 1.2.
      *
      * @return Content of the env:Fault/env:Node element as a String
-     * or <code>null</code> if none
+     * or {@code null} if none
      *
      * @exception UnsupportedOperationException if this message does not
      *      support the SOAP 1.2 concept of Fault Node.
@@ -465,11 +465,11 @@
 
     /**
      * Creates or replaces any existing Node element value for
-     * this <code>SOAPFault</code> object. The Node element
+     * this {@code SOAPFault} object. The Node element
      * is optional in SOAP 1.2.
      *
      * @exception SOAPException  if there was an error in setting the
-     *            Node for this  <code>SOAPFault</code> object.
+     *            Node for this  {@code SOAPFault} object.
      * @exception UnsupportedOperationException if this message does not
      *      support the SOAP 1.2 concept of Fault Node.
      *
@@ -480,11 +480,11 @@
 
     /**
      * Returns the optional Role element value for this
-     * <code>SOAPFault</code> object. The Role element is
+     * {@code SOAPFault} object. The Role element is
      * optional in SOAP 1.2.
      *
      * @return Content of the env:Fault/env:Role element as a String
-     * or <code>null</code> if none
+     * or {@code null} if none
      *
      * @exception UnsupportedOperationException if this message does not
      *      support the SOAP 1.2 concept of Fault Role.
@@ -495,13 +495,13 @@
 
     /**
      * Creates or replaces any existing Role element value for
-     * this <code>SOAPFault</code> object. The Role element
+     * this {@code SOAPFault} object. The Role element
      * is optional in SOAP 1.2.
      *
      * @param uri - the URI of the Role
      *
      * @exception SOAPException  if there was an error in setting the
-     *            Role for this  <code>SOAPFault</code> object.
+     *            Role for this  {@code SOAPFault} object.
      *
      * @exception UnsupportedOperationException if this message does not
      *      support the SOAP 1.2 concept of Fault Role.
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPFaultElement.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPFaultElement.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -27,11 +27,11 @@
 
 /**
  * A representation of the contents in
- * a <code>SOAPFault</code> object.  The <code>Detail</code> interface
- * is a <code>SOAPFaultElement</code>.
+ * a {@code SOAPFault} object.  The {@code Detail} interface
+ * is a {@code SOAPFaultElement}.
  * <P>
- * Content is added to a <code>SOAPFaultElement</code> using the
- * <code>SOAPElement</code> method <code>addTextNode</code>.
+ * Content is added to a {@code SOAPFaultElement} using the
+ * {@code SOAPElement} method {@code addTextNode}.
  *
  * @since 1.6
  */
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPHeader.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPHeader.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -34,49 +34,49 @@
  * element. A SOAP header element consists of XML data that affects
  * the way the application-specific content is processed by the message
  * provider. For example, transaction semantics, authentication information,
- * and so on, can be specified as the content of a <code>SOAPHeader</code>
+ * and so on, can be specified as the content of a {@code SOAPHeader}
  * object.
  * <P>
- * A <code>SOAPEnvelope</code> object contains an empty
- * <code>SOAPHeader</code> object by default. If the <code>SOAPHeader</code>
+ * A {@code SOAPEnvelope} object contains an empty
+ * {@code SOAPHeader} object by default. If the {@code SOAPHeader}
  * object, which is optional, is not needed, it can be retrieved and deleted
  * with the following line of code. The variable <i>se</i> is a
- * <code>SOAPEnvelope</code> object.
- * <PRE>
+ * {@code SOAPEnvelope} object.
+ * <pre>{@code
  *      se.getHeader().detachNode();
- * </PRE>
+ * }</pre>
  *
- * A <code>SOAPHeader</code> object is created with the <code>SOAPEnvelope</code>
- * method <code>addHeader</code>. This method, which creates a new header and adds it
+ * A {@code SOAPHeader} object is created with the {@code SOAPEnvelope}
+ * method {@code addHeader}. This method, which creates a new header and adds it
  * to the envelope, may be called only after the existing header has been removed.
  *
- * <PRE>
+ * <pre>{@code
  *      se.getHeader().detachNode();
  *      SOAPHeader sh = se.addHeader();
- * </PRE>
+ * }</pre>
  * <P>
- * A <code>SOAPHeader</code> object can have only <code>SOAPHeaderElement</code>
- * objects as its immediate children. The method <code>addHeaderElement</code>
- * creates a new <code>HeaderElement</code> object and adds it to the
- * <code>SOAPHeader</code> object. In the following line of code, the
- * argument to the method <code>addHeaderElement</code> is a <code>Name</code>
- * object that is the name for the new <code>HeaderElement</code> object.
- * <PRE>
+ * A {@code SOAPHeader} object can have only {@code SOAPHeaderElement}
+ * objects as its immediate children. The method {@code addHeaderElement}
+ * creates a new {@code HeaderElement} object and adds it to the
+ * {@code SOAPHeader} object. In the following line of code, the
+ * argument to the method {@code addHeaderElement} is a {@code Name}
+ * object that is the name for the new {@code HeaderElement} object.
+ * <pre>{@code
  *      SOAPHeaderElement shElement = sh.addHeaderElement(name);
- * </PRE>
+ * }</pre>
  *
  * @see SOAPHeaderElement
  * @since 1.6
  */
 public interface SOAPHeader extends SOAPElement {
     /**
-     * Creates a new <code>SOAPHeaderElement</code> object initialized with the
-     * specified name and adds it to this <code>SOAPHeader</code> object.
+     * Creates a new {@code SOAPHeaderElement} object initialized with the
+     * specified name and adds it to this {@code SOAPHeader} object.
      *
-     * @param name a <code>Name</code> object with the name of the new
-     *        <code>SOAPHeaderElement</code> object
-     * @return the new <code>SOAPHeaderElement</code> object that was
-     *          inserted into this <code>SOAPHeader</code> object
+     * @param name a {@code Name} object with the name of the new
+     *        {@code SOAPHeaderElement} object
+     * @return the new {@code SOAPHeaderElement} object that was
+     *          inserted into this {@code SOAPHeader} object
      * @exception SOAPException if a SOAP error occurs
      * @see SOAPHeader#addHeaderElement(javax.xml.namespace.QName)
      */
@@ -84,13 +84,13 @@
         throws SOAPException;
 
     /**
-     * Creates a new <code>SOAPHeaderElement</code> object initialized with the
-     * specified qname and adds it to this <code>SOAPHeader</code> object.
+     * Creates a new {@code SOAPHeaderElement} object initialized with the
+     * specified qname and adds it to this {@code SOAPHeader} object.
      *
-     * @param qname a <code>QName</code> object with the qname of the new
-     *        <code>SOAPHeaderElement</code> object
-     * @return the new <code>SOAPHeaderElement</code> object that was
-     *          inserted into this <code>SOAPHeader</code> object
+     * @param qname a {@code QName} object with the qname of the new
+     *        {@code SOAPHeaderElement} object
+     * @return the new {@code SOAPHeaderElement} object that was
+     *          inserted into this {@code SOAPHeader} object
      * @exception SOAPException if a SOAP error occurs
      * @see SOAPHeader#addHeaderElement(Name)
      * @since 1.6, SAAJ 1.3
@@ -99,19 +99,19 @@
         throws SOAPException;
 
     /**
-     * Returns an <code>Iterator</code> over all the <code>SOAPHeaderElement</code> objects
-     * in this <code>SOAPHeader</code> object
+     * Returns an {@code Iterator} over all the {@code SOAPHeaderElement} objects
+     * in this {@code SOAPHeader} object
      * that have the specified <i>actor</i> and that have a MustUnderstand attribute
-     * whose value is equivalent to <code>true</code>.
+     * whose value is equivalent to {@code true}.
      * <p>
      * In SOAP 1.2 the <i>env:actor</i> attribute is replaced by the <i>env:role</i>
      * attribute, but with essentially the same semantics.
      *
-     * @param actor a <code>String</code> giving the URI of the <code>actor</code> / <code>role</code>
+     * @param actor a {@code String} giving the URI of the {@code actor} / {@code role}
      *        for which to search
-     * @return an <code>Iterator</code> object over all the
-     *         <code>SOAPHeaderElement</code> objects that contain the specified
-     *          <code>actor</code> / <code>role</code> and are marked as MustUnderstand
+     * @return an {@code Iterator} object over all the
+     *         {@code SOAPHeaderElement} objects that contain the specified
+     *          {@code actor} / {@code role} and are marked as MustUnderstand
      * @see #examineHeaderElements
      * @see #extractHeaderElements
      * @see SOAPConstants#URI_SOAP_ACTOR_NEXT
@@ -121,8 +121,8 @@
     public Iterator examineMustUnderstandHeaderElements(String actor);
 
     /**
-     * Returns an <code>Iterator</code> over all the <code>SOAPHeaderElement</code> objects
-     * in this <code>SOAPHeader</code> object
+     * Returns an {@code Iterator} over all the {@code SOAPHeaderElement} objects
+     * in this {@code SOAPHeader} object
      * that have the specified <i>actor</i>.
      *
      * An <i>actor</i> is a global attribute that indicates the intermediate
@@ -130,40 +130,40 @@
      * receiver. An actor receives the message and processes it before sending
      * it on to the next actor. The default actor is the ultimate intended
      * recipient for the message, so if no actor attribute is included in a
-     * <code>SOAPHeader</code> object, it is sent to the ultimate receiver
+     * {@code SOAPHeader} object, it is sent to the ultimate receiver
      * along with the message body.
      * <p>
      * In SOAP 1.2 the <i>env:actor</i> attribute is replaced by the <i>env:role</i>
      * attribute, but with essentially the same semantics.
      *
-     * @param actor a <code>String</code> giving the URI of the <code>actor</code> / <code>role</code>
+     * @param actor a {@code String} giving the URI of the {@code actor} / {@code role}
      *        for which to search
-     * @return an <code>Iterator</code> object over all the
-     *         <code>SOAPHeaderElement</code> objects that contain the specified
-     *          <code>actor</code> / <code>role</code>
+     * @return an {@code Iterator} object over all the
+     *         {@code SOAPHeaderElement} objects that contain the specified
+     *          {@code actor} / {@code role}
      * @see #extractHeaderElements
      * @see SOAPConstants#URI_SOAP_ACTOR_NEXT
      */
     public Iterator examineHeaderElements(String actor);
 
     /**
-     * Returns an <code>Iterator</code> over all the <code>SOAPHeaderElement</code> objects
-     * in this <code>SOAPHeader</code> object
+     * Returns an {@code Iterator} over all the {@code SOAPHeaderElement} objects
+     * in this {@code SOAPHeader} object
      * that have the specified <i>actor</i> and detaches them
-     * from this <code>SOAPHeader</code> object.
+     * from this {@code SOAPHeader} object.
      * <P>
      * This method allows an actor to process the parts of the
-     * <code>SOAPHeader</code> object that apply to it and to remove
+     * {@code SOAPHeader} object that apply to it and to remove
      * them before passing the message on to the next actor.
      * <p>
      * In SOAP 1.2 the <i>env:actor</i> attribute is replaced by the <i>env:role</i>
      * attribute, but with essentially the same semantics.
      *
-     * @param actor a <code>String</code> giving the URI of the <code>actor</code> / <code>role</code>
+     * @param actor a {@code String} giving the URI of the {@code actor} / {@code role}
      *        for which to search
-     * @return an <code>Iterator</code> object over all the
-     *         <code>SOAPHeaderElement</code> objects that contain the specified
-     *          <code>actor</code> / <code>role</code>
+     * @return an {@code Iterator} object over all the
+     *         {@code SOAPHeaderElement} objects that contain the specified
+     *          {@code actor} / {@code role}
      *
      * @see #examineHeaderElements
      * @see SOAPConstants#URI_SOAP_ACTOR_NEXT
@@ -171,14 +171,14 @@
     public Iterator extractHeaderElements(String actor);
 
     /**
-     * Creates a new NotUnderstood <code>SOAPHeaderElement</code> object initialized
-     * with the specified name and adds it to this <code>SOAPHeader</code> object.
+     * Creates a new NotUnderstood {@code SOAPHeaderElement} object initialized
+     * with the specified name and adds it to this {@code SOAPHeader} object.
      * This operation is supported only by SOAP 1.2.
      *
-     * @param name a <code>QName</code> object with the name of the
-     *        <code>SOAPHeaderElement</code> object that was not understood.
-     * @return the new <code>SOAPHeaderElement</code> object that was
-     *          inserted into this <code>SOAPHeader</code> object
+     * @param name a {@code QName} object with the name of the
+     *        {@code SOAPHeaderElement} object that was not understood.
+     * @return the new {@code SOAPHeaderElement} object that was
+     *          inserted into this {@code SOAPHeader} object
      * @exception SOAPException if a SOAP error occurs.
      * @exception UnsupportedOperationException if this is a SOAP 1.1 Header.
      * @since 1.6, SAAJ 1.3
@@ -187,15 +187,15 @@
         throws SOAPException;
 
     /**
-     * Creates a new Upgrade <code>SOAPHeaderElement</code> object initialized
+     * Creates a new Upgrade {@code SOAPHeaderElement} object initialized
      * with the specified List of supported SOAP URIs and adds it to this
-     * <code>SOAPHeader</code> object.
+     * {@code SOAPHeader} object.
      * This operation is supported on both SOAP 1.1 and SOAP 1.2 header.
      *
-     * @param supportedSOAPURIs an <code>Iterator</code> object with the URIs of SOAP
+     * @param supportedSOAPURIs an {@code Iterator} object with the URIs of SOAP
      *          versions supported.
-     * @return the new <code>SOAPHeaderElement</code> object that was
-     *          inserted into this <code>SOAPHeader</code> object
+     * @return the new {@code SOAPHeaderElement} object that was
+     *          inserted into this {@code SOAPHeader} object
      * @exception SOAPException if a SOAP error occurs.
      * @since 1.6, SAAJ 1.3
      */
@@ -203,14 +203,14 @@
         throws SOAPException;
 
     /**
-     * Creates a new Upgrade <code>SOAPHeaderElement</code> object initialized
+     * Creates a new Upgrade {@code SOAPHeaderElement} object initialized
      * with the specified array of supported SOAP URIs and adds it to this
-     * <code>SOAPHeader</code> object.
+     * {@code SOAPHeader} object.
      * This operation is supported on both SOAP 1.1 and SOAP 1.2 header.
      *
      * @param  supportedSoapUris an array of the URIs of SOAP versions supported.
-     * @return the new <code>SOAPHeaderElement</code> object that was
-     *          inserted into this <code>SOAPHeader</code> object
+     * @return the new {@code SOAPHeaderElement} object that was
+     *          inserted into this {@code SOAPHeader} object
      * @exception SOAPException if a SOAP error occurs.
      * @since 1.6, SAAJ 1.3
      */
@@ -218,14 +218,14 @@
         throws SOAPException;
 
     /**
-     * Creates a new Upgrade <code>SOAPHeaderElement</code> object initialized
+     * Creates a new Upgrade {@code SOAPHeaderElement} object initialized
      * with the specified supported SOAP URI and adds it to this
-     * <code>SOAPHeader</code> object.
+     * {@code SOAPHeader} object.
      * This operation is supported on both SOAP 1.1 and SOAP 1.2 header.
      *
      * @param supportedSoapUri the URI of SOAP the version that is supported.
-     * @return the new <code>SOAPHeaderElement</code> object that was
-     *          inserted into this <code>SOAPHeader</code> object
+     * @return the new {@code SOAPHeaderElement} object that was
+     *          inserted into this {@code SOAPHeader} object
      * @exception SOAPException if a SOAP error occurs.
      * @since 1.6, SAAJ 1.3
      */
@@ -233,12 +233,12 @@
         throws SOAPException;
 
     /**
-     * Returns an <code>Iterator</code> over all the <code>SOAPHeaderElement</code> objects
-     * in this <code>SOAPHeader</code> object.
+     * Returns an {@code Iterator} over all the {@code SOAPHeaderElement} objects
+     * in this {@code SOAPHeader} object.
      *
-     * @return an <code>Iterator</code> object over all the
-     *          <code>SOAPHeaderElement</code> objects contained by this
-     *          <code>SOAPHeader</code>
+     * @return an {@code Iterator} object over all the
+     *          {@code SOAPHeaderElement} objects contained by this
+     *          {@code SOAPHeader}
      * @see #extractAllHeaderElements
      *
      * @since 1.6, SAAJ 1.2
@@ -246,13 +246,13 @@
     public Iterator examineAllHeaderElements();
 
     /**
-     * Returns an <code>Iterator</code> over all the <code>SOAPHeaderElement</code> objects
-     * in this <code>SOAPHeader</code> object and detaches them
-     * from this <code>SOAPHeader</code> object.
+     * Returns an {@code Iterator} over all the {@code SOAPHeaderElement} objects
+     * in this {@code SOAPHeader} object and detaches them
+     * from this {@code SOAPHeader} object.
      *
-     * @return an <code>Iterator</code> object over all the
-     *          <code>SOAPHeaderElement</code> objects contained by this
-     *          <code>SOAPHeader</code>
+     * @return an {@code Iterator} object over all the
+     *          {@code SOAPHeaderElement} objects contained by this
+     *          {@code SOAPHeader}
      *
      * @see #examineAllHeaderElements
      *
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPHeaderElement.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPHeaderElement.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -28,25 +28,25 @@
 /**
  * An object representing the contents in the SOAP header part of the
  * SOAP envelope.
- * The immediate children of a <code>SOAPHeader</code> object can
- * be represented only as <code>SOAPHeaderElement</code> objects.
+ * The immediate children of a {@code SOAPHeader} object can
+ * be represented only as {@code SOAPHeaderElement} objects.
  * <P>
- * A <code>SOAPHeaderElement</code> object can have other
- * <code>SOAPElement</code> objects as its children.
+ * A {@code SOAPHeaderElement} object can have other
+ * {@code SOAPElement} objects as its children.
  *
  * @since 1.6
  */
 public interface SOAPHeaderElement extends SOAPElement {
 
     /**
-     * Sets the actor associated with this <code>SOAPHeaderElement</code>
+     * Sets the actor associated with this {@code SOAPHeaderElement}
      * object to the specified actor. The default value of an actor is:
-     *          <code>SOAPConstants.URI_SOAP_ACTOR_NEXT</code>
+     *          {@code SOAPConstants.URI_SOAP_ACTOR_NEXT}
      * <P>
-     * If this <code>SOAPHeaderElement</code> supports SOAP 1.2 then this call is
+     * If this {@code SOAPHeaderElement} supports SOAP 1.2 then this call is
      * equivalent to {@link #setRole(String)}
      *
-     * @param  actorURI a <code>String</code> giving the URI of the actor
+     * @param  actorURI a {@code String} giving the URI of the actor
      *           to set
      *
      * @exception IllegalArgumentException if there is a problem in
@@ -57,10 +57,10 @@
     public void setActor(String actorURI);
 
     /**
-     * Sets the <code>Role</code> associated with this <code>SOAPHeaderElement</code>
-     * object to the specified <code>Role</code>.
+     * Sets the {@code Role} associated with this {@code SOAPHeaderElement}
+     * object to the specified {@code Role}.
      *
-     * @param uri - the URI of the <code>Role</code>
+     * @param uri - the URI of the {@code Role}
      *
      * @throws SOAPException if there is an error in setting the role
      *
@@ -73,20 +73,20 @@
 
     /**
      * Returns the uri of the <i>actor</i> attribute of this
-     * <code>SOAPHeaderElement</code>.
+     * {@code SOAPHeaderElement}.
      *<P>
-     * If this <code>SOAPHeaderElement</code> supports SOAP 1.2 then this call is
+     * If this {@code SOAPHeaderElement} supports SOAP 1.2 then this call is
      * equivalent to {@link #getRole()}
-     * @return  a <code>String</code> giving the URI of the actor
+     * @return  a {@code String} giving the URI of the actor
      * @see #setActor
      */
     public String getActor();
 
     /**
      * Returns the value of the <i>Role</i> attribute of this
-     * <code>SOAPHeaderElement</code>.
+     * {@code SOAPHeaderElement}.
      *
-     * @return a <code>String</code> giving the URI of the <code>Role</code>
+     * @return a {@code String} giving the URI of the {@code Role}
      *
      * @exception UnsupportedOperationException if this message does not
      *      support the SOAP 1.2 concept of Fault Role.
@@ -96,16 +96,16 @@
     public String getRole();
 
     /**
-     * Sets the mustUnderstand attribute for this <code>SOAPHeaderElement</code>
+     * Sets the mustUnderstand attribute for this {@code SOAPHeaderElement}
      * object to be either true or false.
      * <P>
      * If the mustUnderstand attribute is on, the actor who receives the
-     * <code>SOAPHeaderElement</code> must process it correctly. This
-     * ensures, for example, that if the <code>SOAPHeaderElement</code>
+     * {@code SOAPHeaderElement} must process it correctly. This
+     * ensures, for example, that if the {@code SOAPHeaderElement}
      * object modifies the message, that the message is being modified correctly.
      *
-     * @param mustUnderstand <code>true</code> to set the mustUnderstand
-     *        attribute to true; <code>false</code> to set it to false
+     * @param mustUnderstand {@code true} to set the mustUnderstand
+     *        attribute to true; {@code false} to set it to false
      *
      * @exception IllegalArgumentException if there is a problem in
      * setting the mustUnderstand attribute
@@ -116,16 +116,16 @@
 
     /**
      * Returns the boolean value of the mustUnderstand attribute for this
-     * <code>SOAPHeaderElement</code>.
+     * {@code SOAPHeaderElement}.
      *
-     * @return <code>true</code> if the mustUnderstand attribute of this
-     *        <code>SOAPHeaderElement</code> object is turned on; <code>false</code>
+     * @return {@code true} if the mustUnderstand attribute of this
+     *        {@code SOAPHeaderElement} object is turned on; {@code false}
      *         otherwise
      */
     public boolean getMustUnderstand();
 
     /**
-     * Sets the <i>relay</i> attribute for this <code>SOAPHeaderElement</code> to be
+     * Sets the <i>relay</i> attribute for this {@code SOAPHeaderElement} to be
      * either true or false.
      * <P>
      * The SOAP relay attribute is set to true to indicate that the SOAP header
@@ -133,7 +133,7 @@
      * but not actually process it. This attribute is ignored on header blocks
      * whose mustUnderstand attribute is set to true or that are targeted at
      * the ultimate reciever (which is the default). The default value of this
-     * attribute is <code>false</code>.
+     * attribute is {@code false}.
      *
      * @param relay the new value of the <i>relay</i> attribute
      *
@@ -151,10 +151,10 @@
 
     /**
      * Returns the boolean value of the <i>relay</i> attribute for this
-     * <code>SOAPHeaderElement</code>
+     * {@code SOAPHeaderElement}
      *
-     * @return <code>true</code> if the relay attribute is turned on;
-     * <code>false</code> otherwise
+     * @return {@code true} if the relay attribute is turned on;
+     * {@code false} otherwise
      *
      * @exception UnsupportedOperationException if this message does not
      *      support the SOAP 1.2 concept of Relay attribute.
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPMessage.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPMessage.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -55,12 +55,12 @@
  * object, and the {@code SOAPEnvelope} object is used to retrieve the
  * {@code SOAPBody} and {@code SOAPHeader} objects.
  *
- * <PRE>
+ * <pre>{@code
  *     SOAPPart sp = message.getSOAPPart();
  *     SOAPEnvelope se = sp.getEnvelope();
  *     SOAPBody sb = se.getBody();
  *     SOAPHeader sh = se.getHeader();
- * </PRE>
+ * }</pre>
  *
  * <P>
  * In addition to the mandatory {@code SOAPPart} object, a {@code SOAPMessage}
@@ -103,14 +103,15 @@
  * @since 1.6
  */
 public abstract class SOAPMessage {
+
     /**
-         * Specifies the character type encoding for the SOAP Message. Valid values
-         * include "utf-8" and "utf-16". See vendor documentation for additional
-         * supported values. The default is "utf-8".
-         *
-         * @see SOAPMessage#setProperty(String, Object) SOAPMessage.setProperty
-         * @since 1.6, SAAJ 1.2
-         */
+     * Specifies the character type encoding for the SOAP Message. Valid values
+     * include "utf-8" and "utf-16". See vendor documentation for additional
+     * supported values. The default is "utf-8".
+     *
+     * @see SOAPMessage#setProperty(String, Object) SOAPMessage.setProperty
+     * @since 1.6, SAAJ 1.2
+     */
     public static final String CHARACTER_SET_ENCODING =
         "javax.xml.soap.character-set-encoding";
 
@@ -146,25 +147,24 @@
     public abstract String getContentDescription();
 
     /**
-         * Gets the SOAP part of this {@code SOAPMessage} object.
-         * <P>
-         * {@code SOAPMessage} object contains one or more attachments, the
-         * SOAP Part must be the first MIME body part in the message.
-         *
-         * @return the {@code SOAPPart} object for this {@code SOAPMessage}
-         *         object
-         */
+     * Gets the SOAP part of this {@code SOAPMessage} object.
+     * <p>
+     * {@code SOAPMessage} object contains one or more attachments, the
+     * SOAP Part must be the first MIME body part in the message.
+     *
+     * @return the {@code SOAPPart} object for this {@code SOAPMessage}
+     * object
+     */
     public abstract SOAPPart getSOAPPart();
 
     /**
-         * Gets the SOAP Body contained in this {@code SOAPMessage} object.
-         *
-         * @return the {@code SOAPBody} object contained by this {@code SOAPMessage}
-         *         object
-         * @exception SOAPException
-         *               if the SOAP Body does not exist or cannot be retrieved
-         * @since 1.6, SAAJ 1.2
-         */
+     * Gets the SOAP Body contained in this {@code SOAPMessage} object.
+     *
+     * @return the {@code SOAPBody} object contained by this {@code SOAPMessage}
+     * object
+     * @throws SOAPException if the SOAP Body does not exist or cannot be retrieved
+     * @since 1.6, SAAJ 1.2
+     */
     public SOAPBody getSOAPBody() throws SOAPException {
         throw new UnsupportedOperationException("getSOAPBody must be overridden by all subclasses of SOAPMessage");
     }
@@ -183,41 +183,40 @@
     }
 
     /**
-         * Removes all {@code AttachmentPart} objects that have been added
-         * to this {@code SOAPMessage} object.
-         * <P>
-         * This method does not touch the SOAP part.
-         */
+     * Removes all {@code AttachmentPart} objects that have been added
+     * to this {@code SOAPMessage} object.
+     * <p>
+     * This method does not touch the SOAP part.
+     */
     public abstract void removeAllAttachments();
 
     /**
-         * Gets a count of the number of attachments in this message. This count
-         * does not include the SOAP part.
-         *
-         * @return the number of {@code AttachmentPart} objects that are
-         *         part of this {@code SOAPMessage} object
-         */
+     * Gets a count of the number of attachments in this message. This count
+     * does not include the SOAP part.
+     *
+     * @return the number of {@code AttachmentPart} objects that are
+     * part of this {@code SOAPMessage} object
+     */
     public abstract int countAttachments();
 
     /**
-         * Retrieves all the {@code AttachmentPart} objects that are part of
-         * this {@code SOAPMessage} object.
-         *
-         * @return an iterator over all the attachments in this message
-         */
+     * Retrieves all the {@code AttachmentPart} objects that are part of
+     * this {@code SOAPMessage} object.
+     *
+     * @return an iterator over all the attachments in this message
+     */
     public abstract Iterator getAttachments();
 
     /**
-         * Retrieves all the {@code AttachmentPart} objects that have header
-         * entries that match the specified headers. Note that a returned
-         * attachment could have headers in addition to those specified.
-         *
-         * @param headers
-         *           a {@code MimeHeaders} object containing the MIME
-         *           headers for which to search
-         * @return an iterator over all attachments that have a header that matches
-         *         one of the given headers
-         */
+     * Retrieves all the {@code AttachmentPart} objects that have header
+     * entries that match the specified headers. Note that a returned
+     * attachment could have headers in addition to those specified.
+     *
+     * @param headers a {@code MimeHeaders} object containing the MIME
+     *                headers for which to search
+     * @return an iterator over all attachments that have a header that matches
+     * one of the given headers
+     */
     public abstract Iterator getAttachments(MimeHeaders headers);
 
     /**
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPPart.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/SOAPPart.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -54,9 +54,9 @@
  * calling the method {@code SOAPMessage.getSOAPPart}. The
  * following  line of code, in which {@code message} is a
  * {@code SOAPMessage} object, retrieves the SOAP part of a message.
- * <PRE>
+ * <pre>{@code
  *   SOAPPart soapPart = message.getSOAPPart();
- * </PRE>
+ * }</pre>
  * <P>
  * A {@code SOAPPart} object contains a {@code SOAPEnvelope} object,
  * which in turn contains a {@code SOAPBody} object and a
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/Text.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/soap/Text.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -26,7 +26,7 @@
 package javax.xml.soap;
 
 /**
- * A representation of a node whose value is text.  A <code>Text</code> object
+ * A representation of a node whose value is text.  A {@code Text} object
  * may represent text that is content or text that is a comment.
  *
  * @since 1.6
@@ -34,10 +34,10 @@
 public interface Text extends Node, org.w3c.dom.Text {
 
     /**
-     * Retrieves whether this <code>Text</code> object represents a comment.
+     * Retrieves whether this {@code Text} object represents a comment.
      *
-     * @return <code>true</code> if this <code>Text</code> object is a
-     *         comment; <code>false</code> otherwise
+     * @return {@code true} if this {@code Text} object is a
+     *         comment; {@code false} otherwise
      */
     public boolean isComment();
 }
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/AsyncHandler.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/AsyncHandler.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -25,7 +25,7 @@
 
 package javax.xml.ws;
 
-/** The <code>AsyncHandler</code> interface is implemented by
+/** The {@code AsyncHandler} interface is implemented by
  * clients that wish to receive callback notification of the completion of
  * service endpoint operations invoked asynchronously.
  *
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/BindingProvider.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/BindingProvider.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -29,7 +29,7 @@
 import javax.xml.ws.wsaddressing.W3CEndpointReference;
 
 /**
- * The <code>BindingProvider</code> interface provides access to the
+ * The {@code BindingProvider} interface provides access to the
  * protocol binding and associated context objects for request and
  * response message processing.
  *
@@ -40,14 +40,14 @@
 public interface BindingProvider {
     /**
      * Standard property: User name for authentication.
-     * <p>Type: <code>java.lang.String</code>
+     * <p>Type: {@code java.lang.String}
      **/
     public static final String USERNAME_PROPERTY =
             "javax.xml.ws.security.auth.username";
 
     /**
      * Standard property: Password for authentication.
-     * <p>Type: <code>java.lang.String</code>
+     * <p>Type: {@code java.lang.String}
      **/
     public static final String PASSWORD_PROPERTY =
             "javax.xml.ws.security.auth.password";
@@ -57,7 +57,7 @@
      * URI scheme for the endpoint address specification MUST
      * correspond to the protocol/transport binding for the
      * binding in use.
-     * <p>Type: <code>java.lang.String</code>
+     * <p>Type: {@code java.lang.String}
      **/
     public static final String ENDPOINT_ADDRESS_PROPERTY =
             "javax.xml.ws.service.endpoint.address";
@@ -66,10 +66,10 @@
      * Standard property: This boolean property is used by a service
      * client to indicate whether or not it wants to participate in
      * a session with a service endpoint. If this property is set to
-     * <code>true</code>, the service client indicates that it wants the session
-     * to be maintained. If set to <code>false</code>, the session is not maintained.
-     * The default value for this property is <code>false</code>.
-     * <p>Type: <code>java.lang.Boolean</code>
+     * {@code true}, the service client indicates that it wants the session
+     * to be maintained. If set to {@code false}, the session is not maintained.
+     * The default value for this property is {@code false}.
+     * <p>Type: {@code java.lang.Boolean}
      **/
     public static final String SESSION_MAINTAIN_PROPERTY =
             "javax.xml.ws.session.maintain";
@@ -77,29 +77,29 @@
     /**
      * Standard property for SOAPAction. This boolean property
      * indicates whether or not the value of the
-     * <code>javax.xml.ws.soap.http.soapaction.uri</code> property
+     * {@code javax.xml.ws.soap.http.soapaction.uri} property
      * is used for the value of the SOAPAction. The
-     * default value of this property is <code>false</code> indicating
+     * default value of this property is {@code false} indicating
      * that the
-     * <code>javax.xml.ws.soap.http.soapaction.uri</code> property
+     * {@code javax.xml.ws.soap.http.soapaction.uri} property
      * is not used for the value of the SOAPAction, however,
      * if WS-Addressing is enabled, the default value is
-     * <code>true</code>.
+     * {@code true}.
      *
-     * <p>Type: <code>java.lang.Boolean</code>
+     * <p>Type: {@code java.lang.Boolean}
      **/
     public static final String SOAPACTION_USE_PROPERTY =
             "javax.xml.ws.soap.http.soapaction.use";
 
     /**
      * Standard property for SOAPAction. Indicates the SOAPAction
-     * URI if the <code>javax.xml.ws.soap.http.soapaction.use</code>
-     * property is set to <code>true</code>. If WS-Addressing
+     * URI if the {@code javax.xml.ws.soap.http.soapaction.use}
+     * property is set to {@code true}. If WS-Addressing
      * is enabled, this value will also be used for the value of the
      * WS-Addressing Action header.  If this property is not set,
      * the default SOAPAction and WS-Addressing Action will be sent.
      *
-     * <p>Type: <code>java.lang.String</code>
+     * <p>Type: {@code java.lang.String}
      **/
     public static final String SOAPACTION_URI_PROPERTY =
             "javax.xml.ws.soap.http.soapaction.uri";
@@ -139,18 +139,18 @@
 
 
     /**
-     * Returns the <code>EndpointReference</code> associated with
-     * this <code>BindingProvider</code> instance.
+     * Returns the {@code EndpointReference} associated with
+     * this {@code BindingProvider} instance.
      * <p>
-     * If the Binding for this <code>bindingProvider</code> is
+     * If the Binding for this {@code bindingProvider} is
      * either SOAP1.1/HTTP or SOAP1.2/HTTP, then a
-     * <code>W3CEndpointReference</code> MUST be returned.
+     * {@code W3CEndpointReference} MUST be returned.
      *
      * @return EndpointReference of the target endpoint associated with this
-     * <code>BindingProvider</code> instance.
+     * {@code BindingProvider} instance.
      *
      * @throws java.lang.UnsupportedOperationException If this
-     * <code>BindingProvider</code> uses the XML/HTTP binding.
+     * {@code BindingProvider} uses the XML/HTTP binding.
      *
      * @see W3CEndpointReference
      *
@@ -160,21 +160,21 @@
 
 
     /**
-     * Returns the <code>EndpointReference</code> associated with
-     * this <code>BindingProvider</code> instance.  The instance
-     * returned will be of type <code>clazz</code>.
+     * Returns the {@code EndpointReference} associated with
+     * this {@code BindingProvider} instance.  The instance
+     * returned will be of type {@code clazz}.
      *
-     * @param clazz Specifies the type of <code>EndpointReference</code>
+     * @param clazz Specifies the type of {@code EndpointReference}
      * that MUST be returned.
 
      * @return EndpointReference of the target endpoint associated with this
-     * <code>BindingProvider</code> instance. MUST be of type
-     * <code>clazz</code>.
+     * {@code BindingProvider} instance. MUST be of type
+     * {@code clazz}.
 
-     * @throws WebServiceException If the Class <code>clazz</code>
+     * @throws WebServiceException If the Class {@code clazz}
      * is not supported by this implementation.
      * @throws java.lang.UnsupportedOperationException If this
-     * <code>BindingProvider</code> uses the XML/HTTP binding.
+     * {@code BindingProvider} uses the XML/HTTP binding.
      *
      * @since 1.6, JAX-WS 2.1
      */
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/BindingType.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/BindingType.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -32,7 +32,7 @@
 import java.lang.annotation.RetentionPolicy;
 
 /**
- *  The <code>BindingType</code> annotation is used to
+ *  The {@code BindingType} annotation is used to
  *  specify the binding to use for a web service
  *  endpoint implementation class.
  *  <p>
@@ -50,7 +50,7 @@
       * A binding identifier (a URI).
       * If not specified, the default is the SOAP 1.1 / HTTP binding.
       * <p>
-      * See the <code>SOAPBinding</code> and <code>HTTPBinding</code>
+      * See the {@code SOAPBinding} and {@code HTTPBinding}
       * for the definition of the standard binding identifiers.
       *
       * @see javax.xml.ws.Binding
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/Endpoint.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/Endpoint.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -37,23 +37,23 @@
  * A Web service endpoint.
  *
  * <p>Endpoints are created using the static methods defined in this
- * class. An endpoint is always tied to one <code>Binding</code>
+ * class. An endpoint is always tied to one {@code Binding}
  * and one implementor, both set at endpoint creation time.
  *
  * <p>An endpoint is either in a published or an unpublished state.
- * The <code>publish</code> methods can be used to start publishing
+ * The {@code publish} methods can be used to start publishing
  * an endpoint, at which point it starts accepting incoming requests.
- * Conversely, the <code>stop</code> method can be used to stop
+ * Conversely, the {@code stop} method can be used to stop
  * accepting incoming requests and take the endpoint down.
  * Once stopped, an endpoint cannot be published again.
  *
- * <p>An <code>Executor</code> may be set on the endpoint in order
+ * <p>An {@code Executor} may be set on the endpoint in order
  * to gain better control over the threads used to dispatch incoming
  * requests. For instance, thread pooling with certain parameters
- * can be enabled by creating a <code>ThreadPoolExecutor</code> and
+ * can be enabled by creating a {@code ThreadPoolExecutor} and
  * registering it with the endpoint.
  *
- * <p>Handler chains can be set using the contained <code>Binding</code>.
+ * <p>Handler chains can be set using the contained {@code Binding}.
  *
  * <p>An endpoint may have a list of metadata documents, such as WSDL
  * and XMLSchema documents, bound to it. At publishing time, the
@@ -114,8 +114,8 @@
      *
      * @param implementor The endpoint implementor.
      * @param features A list of WebServiceFeature to configure on the
-     *        endpoint. Supported features not in the <code>features
-     *        </code> parameter will have their default values.
+     *        endpoint. Supported features not in the {@code features
+     *        } parameter will have their default values.
      *
      *
      * @return The newly created endpoint.
@@ -135,7 +135,7 @@
      * {@link javax.xml.ws.Endpoint#publish(Object)} methods.
      *
      * @param bindingId A URI specifying the binding to use. If the bindingID is
-     * <code>null</code> and no binding is specified via a BindingType
+     * {@code null} and no binding is specified via a BindingType
      * annotation then a default SOAP 1.1 / HTTP binding MUST be used.
      *
      * @param implementor The endpoint implementor.
@@ -156,14 +156,14 @@
      * {@link javax.xml.ws.Endpoint#publish(Object)} methods.
      *
      * @param bindingId A URI specifying the binding to use. If the bindingID is
-     * <code>null</code> and no binding is specified via a BindingType
+     * {@code null} and no binding is specified via a BindingType
      * annotation then a default SOAP 1.1 / HTTP binding MUST be used.
      *
      * @param implementor The endpoint implementor.
      *
      * @param features A list of WebServiceFeature to configure on the
-     *        endpoint. Supported features not in the <code>features
-     *        </code> parameter will have their default values.
+     *        endpoint. Supported features not in the {@code features
+     *        } parameter will have their default values.
      *
      * @return The newly created endpoint.
      * @since 1.7, JAX-WS 2.2
@@ -205,9 +205,9 @@
      *          If the endpoint has been published already or it has been stopped.
      *
      * @throws java.lang.SecurityException
-     *          If a <code>java.lang.SecurityManger</code>
+     *          If a {@code java.lang.SecurityManger}
      *          is being used and the application doesn't have the
-     *          <code>WebServicePermission("publishEndpoint")</code> permission.
+     *          {@code WebServicePermission("publishEndpoint")} permission.
      **/
     public abstract void publish(String address);
 
@@ -231,9 +231,9 @@
      * @return The newly created endpoint.
      *
      * @throws java.lang.SecurityException
-     *          If a <code>java.lang.SecurityManger</code>
+     *          If a {@code java.lang.SecurityManger}
      *          is being used and the application doesn't have the
-     *          <code>WebServicePermission("publishEndpoint")</code> permission.
+     *          {@code WebServicePermission("publishEndpoint")} permission.
      *
      **/
     public static Endpoint publish(String address, Object implementor) {
@@ -258,14 +258,14 @@
      *        URI schemes.
      * @param implementor The endpoint implementor.
      * @param features A list of WebServiceFeature to configure on the
-     *        endpoint. Supported features not in the <code>features
-     *        </code> parameter will have their default values.
+     *        endpoint. Supported features not in the {@code features
+     *        } parameter will have their default values.
      * @return The newly created endpoint.
      *
      * @throws java.lang.SecurityException
-     *          If a <code>java.lang.SecurityManger</code>
+     *          If a {@code java.lang.SecurityManger}
      *          is being used and the application doesn't have the
-     *          <code>WebServicePermission("publishEndpoint")</code> permission.
+     *          {@code WebServicePermission("publishEndpoint")} permission.
      * @since 1.7, JAX-WS 2.2
      */
     public static Endpoint publish(String address, Object implementor, WebServiceFeature ... features) {
@@ -294,9 +294,9 @@
      *         If the endpoint has been published already or it has been stopped.
      *
      * @throws java.lang.SecurityException
-     *          If a <code>java.lang.SecurityManger</code>
+     *          If a {@code java.lang.SecurityManger}
      *          is being used and the application doesn't have the
-     *          <code>WebServicePermission("publishEndpoint")</code> permission.
+     *          {@code WebServicePermission("publishEndpoint")} permission.
      **/
     public abstract void publish(Object serverContext);
 
@@ -327,9 +327,9 @@
      *         If the endpoint has been published already or it has been stopped.
      *
      * @throws java.lang.SecurityException
-     *          If a <code>java.lang.SecurityManger</code>
+     *          If a {@code java.lang.SecurityManger}
      *          is being used and the application doesn't have the
-     *          <code>WebServicePermission("publishEndpoint")</code> permission.
+     *          {@code WebServicePermission("publishEndpoint")} permission.
      * @since 1.7, JAX-WS 2.2
      */
     public void publish(HttpContext serverContext) {
@@ -348,14 +348,14 @@
     /**
      * Returns true if the endpoint is in the published state.
      *
-     * @return <code>true</code> if the endpoint is in the published state.
+     * @return {@code true} if the endpoint is in the published state.
      **/
     public abstract boolean isPublished();
 
     /**
      * Returns a list of metadata documents for the service.
      *
-     * @return <code>List&lt;javax.xml.transform.Source&gt;</code> A list of metadata documents for the service
+     * @return {@code List<javax.xml.transform.Source>} A list of metadata documents for the service
      **/
     public abstract List<javax.xml.transform.Source> getMetadata();
 
@@ -372,12 +372,12 @@
     public abstract void setMetadata(List<javax.xml.transform.Source> metadata);
 
     /**
-     * Returns the executor for this <code>Endpoint</code>instance.
+     * Returns the executor for this {@code Endpoint}instance.
      *
      * The executor is used to dispatch an incoming request to
      * the implementor object.
      *
-     * @return The <code>java.util.concurrent.Executor</code> to be
+     * @return The {@code java.util.concurrent.Executor} to be
      *         used to dispatch a request.
      *
      * @see java.util.concurrent.Executor
@@ -385,17 +385,17 @@
     public abstract java.util.concurrent.Executor getExecutor();
 
     /**
-     * Sets the executor for this <code>Endpoint</code> instance.
+     * Sets the executor for this {@code Endpoint} instance.
      *
      * The executor is used to dispatch an incoming request to
      * the implementor object.
      *
-     * If this <code>Endpoint</code> is published using the
-     * <code>publish(Object)</code> method and the specified server
+     * If this {@code Endpoint} is published using the
+     * {@code publish(Object)} method and the specified server
      * context defines its own threading behavior, the executor
      * may be ignored.
      *
-     * @param executor The <code>java.util.concurrent.Executor</code>
+     * @param executor The {@code java.util.concurrent.Executor}
      *        to be used to dispatch a request.
      *
      * @throws SecurityException  If the instance does not support
@@ -408,7 +408,7 @@
 
 
     /**
-     * Returns the property bag for this <code>Endpoint</code> instance.
+     * Returns the property bag for this {@code Endpoint} instance.
      *
      * @return Map&lt;String,Object&gt; The property bag
      *         associated with this instance.
@@ -416,7 +416,7 @@
     public abstract Map<String,Object> getProperties();
 
     /**
-     * Sets the property bag for this <code>Endpoint</code> instance.
+     * Sets the property bag for this {@code Endpoint} instance.
      *
      * @param properties The property bag associated with
      *        this instance.
@@ -424,24 +424,24 @@
     public abstract void setProperties(Map<String,Object> properties);
 
     /**
-     * Returns the <code>EndpointReference</code> associated with
-     * this <code>Endpoint</code> instance.
+     * Returns the {@code EndpointReference} associated with
+     * this {@code Endpoint} instance.
      * <p>
-     * If the Binding for this <code>bindingProvider</code> is
+     * If the Binding for this {@code bindingProvider} is
      * either SOAP1.1/HTTP or SOAP1.2/HTTP, then a
-     * <code>W3CEndpointReference</code> MUST be returned.
+     * {@code W3CEndpointReference} MUST be returned.
      *
      * @param referenceParameters Reference parameters to be associated with the
-     * returned <code>EndpointReference</code> instance.
-     * @return EndpointReference of this <code>Endpoint</code> instance.
-     * If the returned <code>EndpointReference</code> is of type
-     * <code>W3CEndpointReference</code> then it MUST contain the
-     * the specified <code>referenceParameters</code>.
+     * returned {@code EndpointReference} instance.
+     * @return EndpointReference of this {@code Endpoint} instance.
+     * If the returned {@code EndpointReference} is of type
+     * {@code W3CEndpointReference} then it MUST contain the
+     * the specified {@code referenceParameters}.
 
      * @throws WebServiceException If any error in the creation of
-     * the <code>EndpointReference</code> or if the <code>Endpoint</code> is
+     * the {@code EndpointReference} or if the {@code Endpoint} is
      * not in the published state.
-     * @throws UnsupportedOperationException If this <code>BindingProvider</code>
+     * @throws UnsupportedOperationException If this {@code BindingProvider}
      * uses the XML/HTTP binding.
      *
      * @see W3CEndpointReference
@@ -452,23 +452,23 @@
 
 
     /**
-     * Returns the <code>EndpointReference</code> associated with
-     * this <code>Endpoint</code> instance.
+     * Returns the {@code EndpointReference} associated with
+     * this {@code Endpoint} instance.
      *
      * @param clazz Specifies the type of EndpointReference  that MUST be returned.
      * @param referenceParameters Reference parameters to be associated with the
-     * returned <code>EndpointReference</code> instance.
-     * @return EndpointReference of type <code>clazz</code> of this
-     * <code>Endpoint</code> instance.
-     * If the returned <code>EndpointReference</code> is of type
-     * <code>W3CEndpointReference</code> then it MUST contain the
-     * the specified <code>referenceParameters</code>.
+     * returned {@code EndpointReference} instance.
+     * @return EndpointReference of type {@code clazz} of this
+     * {@code Endpoint} instance.
+     * If the returned {@code EndpointReference} is of type
+     * {@code W3CEndpointReference} then it MUST contain the
+     * the specified {@code referenceParameters}.
 
      * @throws WebServiceException If any error in the creation of
-     * the <code>EndpointReference</code> or if the <code>Endpoint</code> is
-     * not in the published state or if the <code>clazz</code> is not a supported
-     * <code>EndpointReference</code> type.
-     * @throws UnsupportedOperationException If this <code>BindingProvider</code>
+     * the {@code EndpointReference} or if the {@code Endpoint} is
+     * not in the published state or if the {@code clazz} is not a supported
+     * {@code EndpointReference} type.
+     * @throws UnsupportedOperationException If this {@code BindingProvider}
      * uses the XML/HTTP binding.
      *
      *
@@ -478,7 +478,7 @@
             Element... referenceParameters);
 
     /**
-     * By settng a <code>EndpointContext</code>, JAX-WS runtime knows about
+     * By settng a {@code EndpointContext}, JAX-WS runtime knows about
      * addresses of other endpoints in an application. If multiple endpoints
      * share different ports of a WSDL, then the multiple port addresses
      * are patched when the WSDL is accessed.
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/EndpointContext.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/EndpointContext.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2009, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2009, 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
@@ -25,11 +25,10 @@
 
 package javax.xml.ws;
 
-import javax.xml.ws.Endpoint;
 import java.util.Set;
 
 /**
- * <code>EndpointContext</code> allows multiple endpoints in an application
+ * {@code EndpointContext} allows multiple endpoints in an application
  * to share any information. For example, servlet application's war may
  * contain multiple endpoints and these endpoints can get addresses of each
  * other by sharing this context. If multiple endpoints share different
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/EndpointReference.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/EndpointReference.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -44,35 +44,35 @@
  * need not be concerned with its contents.  The web service
  * developer should use this class strictly as a mechanism to
  * reference a remote web service endpoint. See the {@link Service} APIs
- * that clients can use to that utilize an <code>EndpointReference</code>.
+ * that clients can use to that utilize an {@code EndpointReference}.
  * See the {@link javax.xml.ws.Endpoint}, and
  * {@link javax.xml.ws.BindingProvider} APIs on how
- * <code>EndpointReferences</code> can be created for published
+ * {@code EndpointReferences} can be created for published
  * endpoints.
  * <p>
  * Concrete implementations of this class will represent
- * an <code>EndpointReference</code> for a particular version of Addressing.
+ * an {@code EndpointReference} for a particular version of Addressing.
  * For example the {@link W3CEndpointReference} is for use
  * with W3C Web Services Addressing 1.0 - Core Recommendation.
  * If JAX-WS implementors need to support different versions
  * of addressing, they should write their own
- * <code>EndpointReference</code> subclass for that version.
+ * {@code EndpointReference} subclass for that version.
  * This will allow a JAX-WS implementation to create
- * a vendor specific <code>EndpointReferences</code> that the
+ * a vendor specific {@code EndpointReferences} that the
  * vendor can use to flag a different version of
  * addressing.
  * <p>
  * Web service developers that wish to pass or return
- * <code>EndpointReference</code> in Java methods in an
+ * {@code EndpointReference} in Java methods in an
  * SEI should use
- * concrete instances of an <code>EndpointReference</code> such
- * as the <code>W3CEndpointReference</code>.  This way the
+ * concrete instances of an {@code EndpointReference} such
+ * as the {@code W3CEndpointReference}.  This way the
  * schema mapped from the SEI will be more descriptive of the
  * type of endpoint reference being passed.
  * <p>
  * JAX-WS implementors are expected to extract the XML infoset
- * from an <CODE>EndpointReferece</CODE> using the
- * <code>{@link EndpointReference#writeTo}</code>
+ * from an {@code EndpointReferece} using the
+ * {@link EndpointReference#writeTo}
  * method.
  * <p>
  * JAXB will bind this class to xs:anyType. If a better binding
@@ -92,68 +92,68 @@
 
     /**
      * Factory method to read an EndpointReference from the infoset contained in
-     * <code>eprInfoset</code>. This method delegates to the vendor specific
+     * {@code eprInfoset}. This method delegates to the vendor specific
      * implementation of the {@link javax.xml.ws.spi.Provider#readEndpointReference} method.
      *
-     * @param eprInfoset The <code>EndpointReference</code> infoset to be unmarshalled
+     * @param eprInfoset The {@code EndpointReference} infoset to be unmarshalled
      *
-     * @return the EndpointReference unmarshalled from <code>eprInfoset</code>
-     *    never <code>null</code>
+     * @return the EndpointReference unmarshalled from {@code eprInfoset}
+     *    never {@code null}
      * @throws WebServiceException
      *    if an error occurs while creating the
-     *    <code>EndpointReference</code> from the <CODE>eprInfoset</CODE>
+     *    {@code EndpointReference} from the {@code eprInfoset}
      * @throws java.lang.IllegalArgumentException
-     *     if the <code>null</code> <code>eprInfoset</code> value is given.
+     *     if the {@code null} {@code eprInfoset} value is given.
      */
     public static EndpointReference readFrom(Source eprInfoset) {
         return Provider.provider().readEndpointReference(eprInfoset);
     }
 
     /**
-     * write this <code>EndpointReference</code> to the specified infoset format
+     * write this {@code EndpointReference} to the specified infoset format
      *
      * @param result for writing infoset
      * @throws WebServiceException
      *   if there is an error writing the
-     *   <code>EndpointReference</code> to the specified <code>result</code>.
+     *   {@code EndpointReference} to the specified {@code result}.
      *
      * @throws java.lang.IllegalArgumentException
-     *      If the <code>null</code> <code>result</code> value is given.
+     *      If the {@code null} {@code result} value is given.
      */
     public abstract void writeTo(Result result);
 
 
     /**
-     * The <code>getPort</code> method returns a proxy. If there
+     * The {@code getPort} method returns a proxy. If there
      * are any reference parameters in the
-     * <code>EndpointReference</code> instance, then those reference
+     * {@code EndpointReference} instance, then those reference
      * parameters MUST appear as SOAP headers, indicating them to be
      * reference parameters, on all messages sent to the endpoint.
-     * The parameter  <code>serviceEndpointInterface</code> specifies
+     * The parameter  {@code serviceEndpointInterface} specifies
      * the service endpoint interface that is supported by the
      * returned proxy.
-     * The <code>EndpointReference</code> instance specifies the
+     * The {@code EndpointReference} instance specifies the
      * endpoint that will be invoked by the returned proxy.
      * In the implementation of this method, the JAX-WS
      * runtime system takes the responsibility of selecting a protocol
      * binding (and a port) and configuring the proxy accordingly from
-     * the WSDL Metadata from this <code>EndpointReference</code> or from
-     * annotations on the <code>serviceEndpointInterface</code>.  For this method
+     * the WSDL Metadata from this {@code EndpointReference} or from
+     * annotations on the {@code serviceEndpointInterface}.  For this method
      * to successfully return a proxy, WSDL metadata MUST be available and the
-     * <code>EndpointReference</code> instance MUST contain an implementation understood
-     * <code>serviceName</code> metadata.
+     * {@code EndpointReference} instance MUST contain an implementation understood
+     * {@code serviceName} metadata.
      * <p>
-     * Because this port is not created from a <code>Service</code> object, handlers
-     * will not automatically be configured, and the <code>HandlerResolver</code>
-     * and <code>Executor</code> cannot be get or set for this port. The
-     * <code>BindingProvider().getBinding().setHandlerChain()</code>
+     * Because this port is not created from a {@code Service} object, handlers
+     * will not automatically be configured, and the {@code HandlerResolver}
+     * and {@code Executor} cannot be get or set for this port. The
+     * {@code BindingProvider().getBinding().setHandlerChain()}
      * method can be used to manually configure handlers for this port.
      *
      *
      * @param serviceEndpointInterface Service endpoint interface
-     * @param features  An array of <code>WebServiceFeatures</code> to configure on the
-     *                proxy.  Supported features not in the <code>features
-     *                </code> parameter will have their default values.
+     * @param features  An array of {@code WebServiceFeatures} to configure on the
+     *                proxy.  Supported features not in the {@code features
+     *                } parameter will have their default values.
      * @return Object Proxy instance that supports the
      *                  specified service endpoint interface
      * @throws WebServiceException
@@ -163,10 +163,10 @@
      *                  <LI>If there is any missing WSDL metadata
      *                      as required by this method
      *                  <LI>If this
-     *                      <code>endpointReference</code>
+     *                      {@code endpointReference}
      *                      is invalid
      *                  <LI>If an illegal
-     *                      <code>serviceEndpointInterface</code>
+     *                      {@code serviceEndpointInterface}
      *                      is specified
      *                  <LI>If a feature is enabled that is not compatible with
      *                      this port or is unsupported.
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/Holder.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/Holder.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -28,7 +28,7 @@
 import java.io.Serializable;
 
 /**
- * Holds a value of type <code>T</code>.
+ * Holds a value of type {@code T}.
  *
  * @since 1.6, JAX-WS 2.0
  */
@@ -42,7 +42,7 @@
     public T value;
 
     /**
-     * Creates a new holder with a <code>null</code> value.
+     * Creates a new holder with a {@code null} value.
      */
     public Holder() {
     }
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/LogicalMessage.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/LogicalMessage.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -28,7 +28,7 @@
 import javax.xml.transform.Source;
 import javax.xml.bind.JAXBContext;
 
-/** The <code>LogicalMessage</code> interface represents a
+/** The {@code LogicalMessage} interface represents a
  *  protocol agnostic XML message and contains methods that
  *  provide access to the payload of the message.
  *
@@ -38,17 +38,17 @@
 
   /** Gets the message payload as an XML source, may be called
    *  multiple times on the same LogicalMessage instance, always
-   *  returns a new <code>Source</code> that may be used to retrieve the entire
+   *  returns a new {@code Source} that may be used to retrieve the entire
    *  message payload.
    *
-   *  <p>If the returned <code>Source</code> is an instance of
-   *  <code>DOMSource</code>, then
+   *  <p>If the returned {@code Source} is an instance of
+   *  {@code DOMSource}, then
    *  modifications to the encapsulated DOM tree change the message
    *  payload in-place, there is no need to susequently call
-   *  <code>setPayload</code>. Other types of <code>Source</code> provide only
+   *  {@code setPayload}. Other types of {@code Source} provide only
    *  read access to the message payload.
    *
-   *  @return The contained message payload; returns <code>null</code> if no
+   *  @return The contained message payload; returns {@code null} if no
    *          payload is present in this message.
   **/
   public Source getPayload();
@@ -65,11 +65,11 @@
 
   /** Gets the message payload as a JAXB object. Note that there is no
    *  connection between the returned object and the message payload,
-   *  changes to the payload require calling <code>setPayload</code>.
+   *  changes to the payload require calling {@code setPayload}.
    *
    *  @param  context The JAXBContext that should be used to unmarshall
    *          the message payload
-   *  @return The contained message payload; returns <code>null</code> if no
+   *  @return The contained message payload; returns {@code null} if no
    *          payload is present in this message
    *  @throws WebServiceException If an error occurs when using a supplied
    *     JAXBContext to unmarshall the payload. The cause of
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/ProtocolException.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/ProtocolException.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -25,7 +25,7 @@
 
 package javax.xml.ws;
 
-/** The <code>ProtocolException</code> class is a
+/** The {@code ProtocolException} class is a
  *  base class for exceptions related to a specific protocol binding. Subclasses
  *  are used to communicate protocol level fault information to clients and may
  *  be used on the server to control the protocol specific fault representation.
@@ -34,9 +34,9 @@
 **/
 public class ProtocolException extends WebServiceException {
     /**
-     * Constructs a new protocol exception with <code>null</code> as its detail message. The
+     * Constructs a new protocol exception with {@code null} as its detail message. The
      * cause is not initialized, and may subsequently be initialized by a call
-     * to <code>Throwable.initCause(java.lang.Throwable)</code>.
+     * to {@code Throwable.initCause(java.lang.Throwable)}.
      */
     public ProtocolException() {
         super();
@@ -45,7 +45,7 @@
     /**
      * Constructs a new protocol exception with the specified detail message.
      * The cause is not initialized, and may subsequently be initialized by a
-     * call to <code>Throwable.initCause(java.lang.Throwable)</code>.
+     * call to {@code Throwable.initCause(java.lang.Throwable)}.
      *
      * @param message the detail message. The detail message is saved for later
      *   retrieval by the Throwable.getMessage() method.
@@ -64,7 +64,7 @@
      * @param message the detail message (which is saved for later retrieval  by
      *   the Throwable.getMessage() method).
      * @param cause the cause (which is saved for later retrieval by the
-     * <code>Throwable.getCause()</code> method). (A <code>null</code> value is  permitted, and indicates
+     * {@code Throwable.getCause()} method). (A {@code null} value is  permitted, and indicates
      * that the cause is nonexistent or  unknown.)
      */
     public ProtocolException(String message,  Throwable cause) {
@@ -73,13 +73,13 @@
 
     /**
      * Constructs a new runtime exception with the specified cause and a  detail
-     * message of <code>(cause==null ? null : cause.toString())</code>  (which typically
+     * message of {@code (cause==null ? null : cause.toString())}  (which typically
      * contains the class and detail message of  cause). This constructor is
      * useful for runtime exceptions  that are little more than wrappers for
      * other throwables.
      *
      * @param cause the cause (which is saved for later retrieval by the
-     * <code>Throwable.getCause()</code> method). (A <code>null</code> value is  permitted, and indicates
+     * {@code Throwable.getCause()} method). (A {@code null} value is  permitted, and indicates
      * that the cause is nonexistent or  unknown.)
      */
     public ProtocolException(Throwable cause) {
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/Provider.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/Provider.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -26,16 +26,16 @@
 package javax.xml.ws;
 
 /**
- *  <p>Service endpoints may implement the <code>Provider</code>
+ *  <p>Service endpoints may implement the {@code Provider}
  *  interface as a dynamic alternative to an SEI.
  *
- *  <p>Implementations are required to support <code>Provider&lt;Source&gt;</code>,
- *  <code>Provider&lt;SOAPMessage&gt;</code> and
- *  <code>Provider&lt;DataSource&gt;</code>, depending on the binding
+ *  <p>Implementations are required to support {@code Provider<Source>},
+ *  {@code Provider<SOAPMessage>} and
+ *  {@code Provider<DataSource>}, depending on the binding
  *  in use and the service mode.
  *
- *  <p>The <code>ServiceMode</code> annotation can be used to control whether
- *  the <code>Provider</code> instance will receive entire protocol messages
+ *  <p>The {@code ServiceMode} annotation can be used to control whether
+ *  the {@code Provider} instance will receive entire protocol messages
  *  or just message payloads.
  *
  *  @since 1.6, JAX-WS 2.0
@@ -50,11 +50,11 @@
    *  message.
    *
    *  @param  request The request message or message payload.
-   *  @return The response message or message payload. May be <code>null</code> if
+   *  @return The response message or message payload. May be {@code null} if
               there is no response.
    *  @throws WebServiceException If there is an error processing request.
-   *          The cause of the <code>WebServiceException</code> may be set to a subclass
-   *          of <code>ProtocolException</code> to control the protocol level
+   *          The cause of the {@code WebServiceException} may be set to a subclass
+   *          of {@code ProtocolException} to control the protocol level
    *          representation of the exception.
    *  @see javax.xml.ws.handler.MessageContext
    *  @see javax.xml.ws.ProtocolException
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/RequestWrapper.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/RequestWrapper.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -33,11 +33,11 @@
 
 /**
  * Used to annotate methods in the Service Endpoint Interface with the request
- * wrapper bean to be used at runtime. The default value of the <code>localName</code> is
- * the <code>operationName</code>, as defined in <code>WebMethod</code> annotation and the
- * <code>targetNamespace</code> is the target namespace of the SEI.
+ * wrapper bean to be used at runtime. The default value of the {@code localName} is
+ * the {@code operationName}, as defined in {@code WebMethod} annotation and the
+ * {@code targetNamespace} is the target namespace of the SEI.
  * <p> When starting from Java this annotation is used resolve
- * overloading conflicts in document literal mode. Only the <code>className</code>
+ * overloading conflicts in document literal mode. Only the {@code className}
  * is required in this case.
  *
  *  @since 1.6, JAX-WS 2.0
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/RespectBinding.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/RespectBinding.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -34,18 +34,18 @@
 
 
 /**
- * This feature clarifies the use of the <code>wsdl:binding</code>
+ * This feature clarifies the use of the {@code wsdl:binding}
  * in a JAX-WS runtime.
  * <p>
  * This annotation MUST only be used in conjunction the
- * <code>javax.jws.WebService</code>, {@link WebServiceProvider},
+ * {@code javax.jws.WebService}, {@link WebServiceProvider},
  * {@link WebServiceRef} annotations.
- * When used with the <code>javax.jws.WebService</code> annotation this
+ * When used with the {@code javax.jws.WebService} annotation this
  * annotation MUST only be used on the service endpoint implementation
  * class.
- * When used with a <code>WebServiceRef</code> annotation, this annotation
+ * When used with a {@code WebServiceRef} annotation, this annotation
  * MUST only be used when a proxy instance is created. The injected SEI
- * proxy, and endpoint MUST honor the values of the <code>RespectBinding</code>
+ * proxy, and endpoint MUST honor the values of the {@code RespectBinding}
  * annotation.
  * <p>
  *
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/RespectBindingFeature.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/RespectBindingFeature.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -28,7 +28,7 @@
 import javax.xml.ws.soap.AddressingFeature;
 
 /**
- * This feature clarifies the use of the <code>wsdl:binding</code>
+ * This feature clarifies the use of the {@code wsdl:binding}
  * in a JAX-WS runtime.
  *
  * This feature can be used during the creation of SEI proxy, and
@@ -38,26 +38,26 @@
  * <p>
  * This feature is only useful with web services that have an
  * associated WSDL. Enabling this feature requires that a JAX-WS
- * implementation inspect the <code>wsdl:binding</code> for an
- * endpoint at runtime to make sure that all <code>wsdl:extensions</code>
- * that have the <code>required</code> attribute set to <code>true</code>
+ * implementation inspect the {@code wsdl:binding} for an
+ * endpoint at runtime to make sure that all {@code wsdl:extensions}
+ * that have the {@code required} attribute set to {@code true}
  * are understood and are being used.
  * <p>
  * The following describes the affects of this feature with respect
  * to be enabled or disabled:
  * <ul>
  *  <li> ENABLED: In this Mode, a JAX-WS runtime MUST assure that all
- *  required <code>wsdl:binding</code> extensions(including policies) are
+ *  required {@code wsdl:binding} extensions(including policies) are
  *  either understood and used by the runtime, or explicitly disabled by the
  *  web service application. A web service can disable a particular
  *  extension if there is a corresponding {@link WebServiceFeature} or annotation.
  *  Similarly, a web service client can disable
- *  particular extension using the corresponding <code>WebServiceFeature</code> while
+ *  particular extension using the corresponding {@code WebServiceFeature} while
  *  creating a proxy or Dispatch instance.
  *  The runtime MUST also make sure that binding of
- *  SEI parameters/return values respect the <code>wsdl:binding</code>.
- *  With this feature enabled, if a required (<code>wsdl:required="true"</code>)
- *  <code>wsdl:binding</code> extension is in the WSDL and it is not
+ *  SEI parameters/return values respect the {@code wsdl:binding}.
+ *  With this feature enabled, if a required ({@code wsdl:required="true"})
+ *  {@code wsdl:binding} extension is in the WSDL and it is not
  *  supported by a JAX-WS runtime and it has not
  *  been explicitly turned off by the web service developer, then
  *  that JAX-WS runtime MUST behave appropriately based on whether it is
@@ -71,8 +71,8 @@
  *  </ul>
  *
  *  <li> DISABLED: In this Mode, an implementation may choose whether
- *  to inspect the <code>wsdl:binding</code> or not and to what degree
- *  the <code>wsdl:binding</code> will be inspected.  For example,
+ *  to inspect the {@code wsdl:binding} or not and to what degree
+ *  the {@code wsdl:binding} will be inspected.  For example,
  *  one implementation may choose to behave as if this feature is enabled,
  *  another implementation may only choose to verify the SEI's
  *  parameter/return type bindings.
@@ -91,7 +91,7 @@
 
 
     /**
-     * Creates an <code>RespectBindingFeature</code>.
+     * Creates an {@code RespectBindingFeature}.
      * The instance created will be enabled.
      */
     public RespectBindingFeature() {
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/Response.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/Response.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -28,14 +28,14 @@
 import java.util.Map;
 import java.util.concurrent.Future;
 
-/** The <code>Response</code> interface provides methods used to obtain the
+/** The {@code Response} interface provides methods used to obtain the
  *  payload and context of a message sent in response to an operation
  *  invocation.
  *
  *  <p>For asynchronous operation invocations it provides additional methods
- *  to check the status of the request. The <code>get(...)</code> methods may
+ *  to check the status of the request. The {@code get(...)} methods may
  *  throw the standard
- *  set of exceptions and their cause may be a <code>RemoteException</code> or a
+ *  set of exceptions and their cause may be a {@code RemoteException} or a
  *  {@link WebServiceException} that represents the error that occured during the
  *  asynchronous method invocation.</p>
  *
@@ -44,7 +44,7 @@
 public interface Response<T> extends Future<T> {
     /** Gets the contained response context.
      *
-     * @return The contained response context. May be <code>null</code> if a
+     * @return The contained response context. May be {@code null} if a
      * response is not yet available.
      *
     **/
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/ResponseWrapper.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/ResponseWrapper.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -32,11 +32,11 @@
 import java.lang.annotation.RetentionPolicy;
 /**
  * Used to annotate methods in the Service Endpoint Interface with the response
- * wrapper bean to be used at runtime. The default value of the <code>localName</code> is
- * the <code>operationName</code> as defined in <code>WebMethod</code> annotation appended with
- * <code>Response</code> and the <code>targetNamespace</code> is the target namespace of the SEI.
+ * wrapper bean to be used at runtime. The default value of the {@code localName} is
+ * the {@code operationName} as defined in {@code WebMethod} annotation appended with
+ * {@code Response} and the {@code targetNamespace} is the target namespace of the SEI.
  * <p> When starting from Java this annotation is used resolve
- * overloading conflicts in document literal mode. Only the <code>className</code>
+ * overloading conflicts in document literal mode. Only the {@code className}
  * is required in this case.
  *
  *  @since 1.6, JAX-WS 2.0
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/Service.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/Service.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -33,8 +33,8 @@
 import javax.xml.ws.spi.Provider;
 
 /**
- * <code>Service</code> objects provide the client view of a Web service.
- * <p><code>Service</code> acts as a factory of the following:
+ * {@code Service} objects provide the client view of a Web service.
+ * <p>{@code Service} acts as a factory of the following:
  * <ul>
  * <li>Proxies for a target service endpoint.</li>
  * <li>Instances of {@link javax.xml.ws.Dispatch} for
@@ -44,17 +44,17 @@
  * </ul>
  *
  * <p>The ports available on a service can be enumerated using the
- * <code>getPorts</code> method. Alternatively, you can pass a
- * service endpoint interface to the unary <code>getPort</code> method
+ * {@code getPorts} method. Alternatively, you can pass a
+ * service endpoint interface to the unary {@code getPort} method
  * and let the runtime select a compatible port.
  *
- * <p>Handler chains for all the objects created by a <code>Service</code>
- * can be set by means of a <code>HandlerResolver</code>.
+ * <p>Handler chains for all the objects created by a {@code Service}
+ * can be set by means of a {@code HandlerResolver}.
  *
- * <p>An <code>Executor</code> may be set on the service in order
+ * <p>An {@code Executor} may be set on the service in order
  * to gain better control over the threads used to dispatch asynchronous
  * callbacks. For instance, thread pooling with certain parameters
- * can be enabled by creating a <code>ThreadPoolExecutor</code> and
+ * can be enabled by creating a {@code ThreadPoolExecutor} and
  * registering it with the service.
  *
  * @since 1.6, JAX-WS 2.0
@@ -67,8 +67,8 @@
 
     private ServiceDelegate delegate;
     /**
-     * The orientation of a dynamic client or service. <code>MESSAGE</code> provides
-     * access to entire protocol message, <code>PAYLOAD</code> to protocol message
+     * The orientation of a dynamic client or service. {@code MESSAGE} provides
+     * access to entire protocol message, {@code PAYLOAD} to protocol message
      * payload only.
      **/
     public enum Mode { MESSAGE, PAYLOAD }
@@ -87,9 +87,9 @@
 
 
     /**
-     * The <code>getPort</code> method returns a proxy. A service client
+     * The {@code getPort} method returns a proxy. A service client
      * uses this proxy to invoke operations on the target
-     * service endpoint. The <code>serviceEndpointInterface</code>
+     * service endpoint. The {@code serviceEndpointInterface}
      * specifies the service endpoint interface that is supported by
      * the created dynamic proxy instance.
      *
@@ -108,8 +108,8 @@
      *                  <LI>If there is any missing WSDL metadata
      *                      as required by this method.
      *                  <LI>If an illegal
-     *                      <code>serviceEndpointInterface</code>
-     *                      or <code>portName</code> is specified.
+     *                      {@code serviceEndpointInterface}
+     *                      or {@code portName} is specified.
      *                  </UL>
      * @see java.lang.reflect.Proxy
      * @see java.lang.reflect.InvocationHandler
@@ -120,9 +120,9 @@
     }
 
     /**
-     * The <code>getPort</code> method returns a proxy. A service client
+     * The {@code getPort} method returns a proxy. A service client
      * uses this proxy to invoke operations on the target
-     * service endpoint. The <code>serviceEndpointInterface</code>
+     * service endpoint. The {@code serviceEndpointInterface}
      * specifies the service endpoint interface that is supported by
      * the created dynamic proxy instance.
      *
@@ -131,8 +131,8 @@
      * @param serviceEndpointInterface Service endpoint interface
      *                  supported by the dynamic proxy instance.
      * @param features  A list of WebServiceFeatures to configure on the
-     *                proxy.  Supported features not in the <code>features
-     *                </code> parameter will have their default values.
+     *                proxy.  Supported features not in the {@code features
+     *                } parameter will have their default values.
      * @return Object Proxy instance that
      *                supports the specified service endpoint
      *                interface.
@@ -144,8 +144,8 @@
      *                  <LI>If there is any missing WSDL metadata
      *                      as required by this method.
      *                  <LI>If an illegal
-     *                      <code>serviceEndpointInterface</code>
-     *                      or <code>portName</code> is specified.
+     *                      {@code serviceEndpointInterface}
+     *                      or {@code portName} is specified.
      *                  <LI>If a feature is enabled that is not compatible
      *                      with this port or is unsupported.
      *                  </UL>
@@ -162,8 +162,8 @@
 
 
     /**
-     * The <code>getPort</code> method returns a proxy. The parameter
-     * <code>serviceEndpointInterface</code> specifies the service
+     * The {@code getPort} method returns a proxy. The parameter
+     * {@code serviceEndpointInterface} specifies the service
      * endpoint interface that is supported by the returned proxy.
      * In the implementation of this method, the JAX-WS
      * runtime system takes the responsibility of selecting a protocol
@@ -180,7 +180,7 @@
      *                  <LI>If there is any missing WSDL metadata
      *                      as required by this method.
      *                  <LI>If an illegal
-     *                      <code>serviceEndpointInterface</code>
+     *                      {@code serviceEndpointInterface}
      *                      is specified.
      *                  </UL>
      **/
@@ -190,8 +190,8 @@
 
 
     /**
-     * The <code>getPort</code> method returns a proxy. The parameter
-     * <code>serviceEndpointInterface</code> specifies the service
+     * The {@code getPort} method returns a proxy. The parameter
+     * {@code serviceEndpointInterface} specifies the service
      * endpoint interface that is supported by the returned proxy.
      * In the implementation of this method, the JAX-WS
      * runtime system takes the responsibility of selecting a protocol
@@ -200,8 +200,8 @@
      *
      * @param serviceEndpointInterface Service endpoint interface.
      * @param features  A list of WebServiceFeatures to configure on the
-     *                proxy.  Supported features not in the <code>features
-     *                </code> parameter will have their default values.
+     *                proxy.  Supported features not in the {@code features
+     *                } parameter will have their default values.
      * @return Object instance that supports the
      *                  specified service endpoint interface.
      * @throws WebServiceException
@@ -211,7 +211,7 @@
      *                  <LI>If there is any missing WSDL metadata
      *                      as required by this method.
      *                  <LI>If an illegal
-     *                      <code>serviceEndpointInterface</code>
+     *                      {@code serviceEndpointInterface}
      *                      is specified.
      *                  <LI>If a feature is enabled that is not compatible
      *                      with this port or is unsupported.
@@ -228,31 +228,31 @@
 
 
     /**
-     * The <code>getPort</code> method returns a proxy.
-     * The parameter <code>endpointReference</code> specifies the
+     * The {@code getPort} method returns a proxy.
+     * The parameter {@code endpointReference} specifies the
      * endpoint that will be invoked by the returned proxy.  If there
      * are any reference parameters in the
-     * <code>endpointReference</code>, then those reference
+     * {@code endpointReference}, then those reference
      * parameters MUST appear as SOAP headers, indicating them to be
      * reference parameters, on all messages sent to the endpoint.
-     * The <code>endpointReference's</code> address MUST be used
+     * The {@code endpointReference's} address MUST be used
      * for invocations on the endpoint.
-     * The parameter <code>serviceEndpointInterface</code> specifies
+     * The parameter {@code serviceEndpointInterface} specifies
      * the service endpoint interface that is supported by the
      * returned proxy.
      * In the implementation of this method, the JAX-WS
      * runtime system takes the responsibility of selecting a protocol
      * binding (and a port) and configuring the proxy accordingly from
-     * the WSDL associated with this <code>Service</code> instance or
-     * from the metadata from the <code>endpointReference</code>.
-     * If this <code>Service</code> instance has a WSDL and
-     * the <code>endpointReference</code> metadata
+     * the WSDL associated with this {@code Service} instance or
+     * from the metadata from the {@code endpointReference}.
+     * If this {@code Service} instance has a WSDL and
+     * the {@code endpointReference} metadata
      * also has a WSDL, then the WSDL from this instance MUST be used.
-     * If this <code>Service</code> instance does not have a WSDL and
-     * the <code>endpointReference</code> does have a WSDL, then the
-     * WSDL from the <code>endpointReference</code> MAY be used.
+     * If this {@code Service} instance does not have a WSDL and
+     * the {@code endpointReference} does have a WSDL, then the
+     * WSDL from the {@code endpointReference} MAY be used.
      * The returned proxy should not be reconfigured by the client.
-     * If this <code>Service</code> instance has a known proxy
+     * If this {@code Service} instance has a known proxy
      * port that matches the information contained in
      * the WSDL,
      * then that proxy is returned, otherwise a WebServiceException
@@ -260,20 +260,20 @@
      * <p>
      * Calling this method has the same behavior as the following
      * <pre>
-     * <code>port = service.getPort(portName, serviceEndpointInterface);</code>
+     * {@code port = service.getPort(portName, serviceEndpointInterface);}
      * </pre>
-     * where the <code>portName</code> is retrieved from the
-     * metadata of the <code>endpointReference</code> or from the
-     * <code>serviceEndpointInterface</code> and the WSDL
-     * associated with this <code>Service</code> instance.
+     * where the {@code portName} is retrieved from the
+     * metadata of the {@code endpointReference} or from the
+     * {@code serviceEndpointInterface} and the WSDL
+     * associated with this {@code Service} instance.
      *
-     * @param endpointReference  The <code>EndpointReference</code>
+     * @param endpointReference  The {@code EndpointReference}
      * for the target service endpoint that will be invoked by the
      * returned proxy.
      * @param serviceEndpointInterface Service endpoint interface.
-     * @param features  A list of <code>WebServiceFeatures</code> to configure on the
-     *                proxy.  Supported features not in the <code>features
-     *                </code> parameter will have their default values.
+     * @param features  A list of {@code WebServiceFeatures} to configure on the
+     *                proxy.  Supported features not in the {@code features
+     *                } parameter will have their default values.
      * @return Object Proxy instance that supports the
      *                  specified service endpoint interface.
      * @throws WebServiceException
@@ -282,16 +282,16 @@
      *                      of the proxy.
      *                  <LI>If there is any missing WSDL metadata
      *                      as required by this method.
-     *                  <LI>If the <code>endpointReference</code> metadata does
-     *                      not match the <code>serviceName</code> of this
-     *                      <code>Service</code> instance.
-     *                  <LI>If a <code>portName</code> cannot be extracted
-     *                      from the WSDL or <code>endpointReference</code> metadata.
+     *                  <LI>If the {@code endpointReference} metadata does
+     *                      not match the {@code serviceName} of this
+     *                      {@code Service} instance.
+     *                  <LI>If a {@code portName} cannot be extracted
+     *                      from the WSDL or {@code endpointReference} metadata.
      *                  <LI>If an invalid
-     *                      <code>endpointReference</code>
+     *                      {@code endpointReference}
      *                      is specified.
      *                  <LI>If an invalid
-     *                      <code>serviceEndpointInterface</code>
+     *                      {@code serviceEndpointInterface}
      *                      is specified.
      *                  <LI>If a feature is enabled that is not compatible
      *                      with this port or is unsupported.
@@ -307,7 +307,7 @@
     /**
      * Creates a new port for the service. Ports created in this way contain
      * no WSDL port type information and can only be used for creating
-     * <code>Dispatch</code>instances.
+     * {@code Dispatch}instances.
      *
      * @param portName  Qualified name for the target service endpoint.
      * @param bindingId A String identifier of a binding.
@@ -325,14 +325,14 @@
 
 
     /**
-     * Creates a <code>Dispatch</code> instance for use with objects of
+     * Creates a {@code Dispatch} instance for use with objects of
      * the client's choosing.
      *
      * @param portName  Qualified name for the target service endpoint
      * @param type The class of object used for messages or message
      * payloads. Implementations are required to support
-     * <code>javax.xml.transform.Source</code>, <code>javax.xml.soap.SOAPMessage</code>
-     * and <code>javax.activation.DataSource</code>, depending on
+     * {@code javax.xml.transform.Source}, {@code javax.xml.soap.SOAPMessage}
+     * and {@code javax.activation.DataSource}, depending on
      * the binding in use.
      * @param mode Controls whether the created dispatch instance is message
      * or payload oriented, i.e. whether the client will work with complete
@@ -343,7 +343,7 @@
      *
      * @return Dispatch instance.
      * @throws WebServiceException If any error in the creation of
-     *                  the <code>Dispatch</code> object.
+     *                  the {@code Dispatch} object.
      *
      * @see javax.xml.transform.Source
      * @see javax.xml.soap.SOAPMessage
@@ -354,26 +354,26 @@
 
 
     /**
-     * Creates a <code>Dispatch</code> instance for use with objects of
+     * Creates a {@code Dispatch} instance for use with objects of
      * the client's choosing.
      *
      * @param portName  Qualified name for the target service endpoint
      * @param type The class of object used for messages or message
      * payloads. Implementations are required to support
-     * <code>javax.xml.transform.Source</code> and <code>javax.xml.soap.SOAPMessage</code>.
+     * {@code javax.xml.transform.Source} and {@code javax.xml.soap.SOAPMessage}.
      * @param mode Controls whether the created dispatch instance is message
      * or payload oriented, i.e. whether the client will work with complete
      * protocol messages or message payloads. E.g. when using the SOAP
      * protocol, this parameter controls whether the client will work with
-     * SOAP messages or the contents of a SOAP body. Mode MUST be <code>MESSAGE</code>
-     * when type is <code>SOAPMessage</code>.
-     * @param features  A list of <code>WebServiceFeatures</code> to configure on the
-     *                proxy.  Supported features not in the <code>features
-     *                </code> parameter will have their default values.
+     * SOAP messages or the contents of a SOAP body. Mode MUST be {@code MESSAGE}
+     * when type is {@code SOAPMessage}.
+     * @param features  A list of {@code WebServiceFeatures} to configure on the
+     *                proxy.  Supported features not in the {@code features
+     *                } parameter will have their default values.
      *
      * @return Dispatch instance.
      * @throws WebServiceException If any error in the creation of
-     *                  the <code>Dispatch</code> object or if a
+     *                  the {@code Dispatch} object or if a
      *                  feature is enabled that is not compatible with
      *                  this port or is unsupported.
      *
@@ -390,64 +390,64 @@
 
 
     /**
-     * Creates a <code>Dispatch</code> instance for use with objects of
+     * Creates a {@code Dispatch} instance for use with objects of
      * the client's choosing. If there
      * are any reference parameters in the
-     * <code>endpointReference</code>, then those reference
+     * {@code endpointReference}, then those reference
      * parameters MUST appear as SOAP headers, indicating them to be
      * reference parameters, on all messages sent to the endpoint.
-     * The <code>endpointReference's</code> address MUST be used
+     * The {@code endpointReference's} address MUST be used
      * for invocations on the endpoint.
      * In the implementation of this method, the JAX-WS
      * runtime system takes the responsibility of selecting a protocol
      * binding (and a port) and configuring the dispatch accordingly from
-     * the WSDL associated with this <code>Service</code> instance or
-     * from the metadata from the <code>endpointReference</code>.
-     * If this <code>Service</code> instance has a WSDL and
-     * the <code>endpointReference</code>
+     * the WSDL associated with this {@code Service} instance or
+     * from the metadata from the {@code endpointReference}.
+     * If this {@code Service} instance has a WSDL and
+     * the {@code endpointReference}
      * also has a WSDL in its metadata, then the WSDL from this instance MUST be used.
-     * If this <code>Service</code> instance does not have a WSDL and
-     * the <code>endpointReference</code> does have a WSDL, then the
-     * WSDL from the <code>endpointReference</code> MAY be used.
-     * An implementation MUST be able to retrieve the <code>portName</code> from the
-     * <code>endpointReference</code> metadata.
+     * If this {@code Service} instance does not have a WSDL and
+     * the {@code endpointReference} does have a WSDL, then the
+     * WSDL from the {@code endpointReference} MAY be used.
+     * An implementation MUST be able to retrieve the {@code portName} from the
+     * {@code endpointReference} metadata.
      * <p>
      * This method behaves the same as calling
      * <pre>
-     * <code>dispatch = service.createDispatch(portName, type, mode, features);</code>
+     * {@code dispatch = service.createDispatch(portName, type, mode, features);}
      * </pre>
-     * where the <code>portName</code> is retrieved from the
-     * WSDL or <code>EndpointReference</code> metadata.
+     * where the {@code portName} is retrieved from the
+     * WSDL or {@code EndpointReference} metadata.
      *
-     * @param endpointReference  The <code>EndpointReference</code>
+     * @param endpointReference  The {@code EndpointReference}
      * for the target service endpoint that will be invoked by the
-     * returned <code>Dispatch</code> object.
+     * returned {@code Dispatch} object.
      * @param type The class of object used to messages or message
      * payloads. Implementations are required to support
-     * <code>javax.xml.transform.Source</code> and <code>javax.xml.soap.SOAPMessage</code>.
+     * {@code javax.xml.transform.Source} and {@code javax.xml.soap.SOAPMessage}.
      * @param mode Controls whether the created dispatch instance is message
      * or payload oriented, i.e. whether the client will work with complete
      * protocol messages or message payloads. E.g. when using the SOAP
      * protocol, this parameter controls whether the client will work with
-     * SOAP messages or the contents of a SOAP body. Mode MUST be <code>MESSAGE</code>
-     * when type is <code>SOAPMessage</code>.
-     * @param features  An array of <code>WebServiceFeatures</code> to configure on the
-     *                proxy.  Supported features not in the <code>features
-     *                </code> parameter will have their default values.
+     * SOAP messages or the contents of a SOAP body. Mode MUST be {@code MESSAGE}
+     * when type is {@code SOAPMessage}.
+     * @param features  An array of {@code WebServiceFeatures} to configure on the
+     *                proxy.  Supported features not in the {@code features
+     *                } parameter will have their default values.
      *
      * @return Dispatch instance
      * @throws WebServiceException
      *                  <UL>
      *                    <LI>If there is any missing WSDL metadata
      *                      as required by this method.
-     *                    <li>If the <code>endpointReference</code> metadata does
-     *                      not match the <code>serviceName</code> or <code>portName</code>
+     *                    <li>If the {@code endpointReference} metadata does
+     *                      not match the {@code serviceName} or {@code portName}
      *                      of a WSDL associated
-     *                      with this <code>Service</code> instance.
-     *                    <li>If the <code>portName</code> cannot be determined
-     *                    from the <code>EndpointReference</code> metadata.
+     *                      with this {@code Service} instance.
+     *                    <li>If the {@code portName} cannot be determined
+     *                    from the {@code EndpointReference} metadata.
      *                    <li>If any error in the creation of
-     *                     the <code>Dispatch</code> object.
+     *                     the {@code Dispatch} object.
      *                    <li>If a feature is enabled that is not
      *                    compatible with this port or is unsupported.
      *                  </UL>
@@ -465,7 +465,7 @@
     }
 
     /**
-     * Creates a <code>Dispatch</code> instance for use with JAXB
+     * Creates a {@code Dispatch} instance for use with JAXB
      * generated objects.
      *
      * @param portName  Qualified name for the target service endpoint
@@ -479,7 +479,7 @@
      *
      * @return Dispatch instance.
      * @throws WebServiceException If any error in the creation of
-     *                  the <code>Dispatch</code> object.
+     *                  the {@code Dispatch} object.
      *
      * @see javax.xml.bind.JAXBContext
      **/
@@ -490,7 +490,7 @@
 
 
     /**
-     * Creates a <code>Dispatch</code> instance for use with JAXB
+     * Creates a {@code Dispatch} instance for use with JAXB
      * generated objects.
      *
      * @param portName  Qualified name for the target service endpoint
@@ -501,13 +501,13 @@
      * protocol messages or message payloads. E.g. when using the SOAP
      * protocol, this parameter controls whether the client will work with
      * SOAP messages or the contents of a SOAP body.
-     * @param features  A list of <code>WebServiceFeatures</code> to configure on the
-     *                proxy.  Supported features not in the <code>features
-     *                </code> parameter will have their default values.
+     * @param features  A list of {@code WebServiceFeatures} to configure on the
+     *                proxy.  Supported features not in the {@code features
+     *                } parameter will have their default values.
      *
      * @return Dispatch instance.
      * @throws WebServiceException If any error in the creation of
-     *                  the <code>Dispatch</code> object or if a
+     *                  the {@code Dispatch} object or if a
      *                  feature is enabled that is not compatible with
      *                  this port or is unsupported.
      *
@@ -523,39 +523,39 @@
 
 
     /**
-     * Creates a <code>Dispatch</code> instance for use with JAXB
+     * Creates a {@code Dispatch} instance for use with JAXB
      * generated objects. If there
      * are any reference parameters in the
-     * <code>endpointReference</code>, then those reference
+     * {@code endpointReference}, then those reference
      * parameters MUST appear as SOAP headers, indicating them to be
      * reference parameters, on all messages sent to the endpoint.
-     * The <code>endpointReference's</code> address MUST be used
+     * The {@code endpointReference's} address MUST be used
      * for invocations on the endpoint.
      * In the implementation of this method, the JAX-WS
      * runtime system takes the responsibility of selecting a protocol
      * binding (and a port) and configuring the dispatch accordingly from
-     * the WSDL associated with this <code>Service</code> instance or
-     * from the metadata from the <code>endpointReference</code>.
-     * If this <code>Service</code> instance has a WSDL and
-     * the <code>endpointReference</code>
+     * the WSDL associated with this {@code Service} instance or
+     * from the metadata from the {@code endpointReference}.
+     * If this {@code Service} instance has a WSDL and
+     * the {@code endpointReference}
      * also has a WSDL in its metadata, then the WSDL from this instance
      * MUST be used.
-     * If this <code>Service</code> instance does not have a WSDL and
-     * the <code>endpointReference</code> does have a WSDL, then the
-     * WSDL from the <code>endpointReference</code> MAY be used.
-     * An implementation MUST be able to retrieve the <code>portName</code> from the
-     * <code>endpointReference</code> metadata.
+     * If this {@code Service} instance does not have a WSDL and
+     * the {@code endpointReference} does have a WSDL, then the
+     * WSDL from the {@code endpointReference} MAY be used.
+     * An implementation MUST be able to retrieve the {@code portName} from the
+     * {@code endpointReference} metadata.
      * <p>
      * This method behavies the same as calling
      * <pre>
-     * <code>dispatch = service.createDispatch(portName, context, mode, features);</code>
+     * {@code dispatch = service.createDispatch(portName, context, mode, features);}
      * </pre>
-     * where the <code>portName</code> is retrieved from the
-     * WSDL or <code>endpointReference</code> metadata.
+     * where the {@code portName} is retrieved from the
+     * WSDL or {@code endpointReference} metadata.
      *
-     * @param endpointReference  The <code>EndpointReference</code>
+     * @param endpointReference  The {@code EndpointReference}
      * for the target service endpoint that will be invoked by the
-     * returned <code>Dispatch</code> object.
+     * returned {@code Dispatch} object.
      * @param context The JAXB context used to marshall and unmarshall
      * messages or message payloads.
      * @param mode Controls whether the created dispatch instance is message
@@ -563,23 +563,23 @@
      * protocol messages or message payloads. E.g. when using the SOAP
      * protocol, this parameter controls whether the client will work with
      * SOAP messages or the contents of a SOAP body.
-     * @param features  An array of <code>WebServiceFeatures</code> to configure on the
-     *                proxy.  Supported features not in the <code>features
-     *                </code> parameter will have their default values.
+     * @param features  An array of {@code WebServiceFeatures} to configure on the
+     *                proxy.  Supported features not in the {@code features
+     *                } parameter will have their default values.
      *
      * @return Dispatch instance
      * @throws WebServiceException
      *                  <UL>
      *                    <li>If there is any missing WSDL metadata
      *                      as required by this method.
-     *                    <li>If the <code>endpointReference</code> metadata does
-     *                    not match the <code>serviceName</code> or <code>portName</code>
+     *                    <li>If the {@code endpointReference} metadata does
+     *                    not match the {@code serviceName} or {@code portName}
      *                    of a WSDL associated
-     *                    with this <code>Service</code> instance.
-     *                    <li>If the <code>portName</code> cannot be determined
-     *                    from the <code>EndpointReference</code> metadata.
+     *                    with this {@code Service} instance.
+     *                    <li>If the {@code portName} cannot be determined
+     *                    from the {@code EndpointReference} metadata.
      *                    <li>If any error in the creation of
-     *                    the <code>Dispatch</code> object.
+     *                    the {@code Dispatch} object.
      *                    <li>if a feature is enabled that is not
      *                    compatible with this port or is unsupported.
      *                  </UL>
@@ -604,12 +604,12 @@
     }
 
     /**
-     * Returns an <code>Iterator</code> for the list of
-     * <code>QName</code>s of service endpoints grouped by this
+     * Returns an {@code Iterator} for the list of
+     * {@code QName}s of service endpoints grouped by this
      * service
      *
-     * @return Returns <code>java.util.Iterator</code> with elements
-     *         of type <code>javax.xml.namespace.QName</code>.
+     * @return Returns {@code java.util.Iterator} with elements
+     *         of type {@code javax.xml.namespace.QName}.
      * @throws WebServiceException If this Service class does not
      *         have access to the required WSDL metadata.
      **/
@@ -630,8 +630,8 @@
     /**
      * Returns the configured handler resolver.
      *
-     * @return HandlerResolver The <code>HandlerResolver</code> being
-     *         used by this <code>Service</code> instance, or <code>null</code>
+     * @return HandlerResolver The {@code HandlerResolver} being
+     *         used by this {@code Service} instance, or {@code null}
      *         if there isn't one.
      **/
     public HandlerResolver getHandlerResolver() {
@@ -639,14 +639,14 @@
     }
 
     /**
-     * Sets the <code>HandlerResolver</code> for this <code>Service</code>
+     * Sets the {@code HandlerResolver} for this {@code Service}
      * instance.
      * <p>
      * The handler resolver, if present, will be called once for each
      * proxy or dispatch instance that is created, and the handler chain
      * returned by the resolver will be set on the instance.
      *
-     * @param handlerResolver The <code>HandlerResolver</code> to use
+     * @param handlerResolver The {@code HandlerResolver} to use
      *        for all subsequently created proxy/dispatch objects.
      *
      * @see javax.xml.ws.handler.HandlerResolver
@@ -656,12 +656,12 @@
     }
 
     /**
-     * Returns the executor for this <code>Service</code>instance.
+     * Returns the executor for this {@code Service}instance.
      *
      * The executor is used for all asynchronous invocations that
      * require callbacks.
      *
-     * @return The <code>java.util.concurrent.Executor</code> to be
+     * @return The {@code java.util.concurrent.Executor} to be
      *         used to invoke a callback.
      *
      * @see java.util.concurrent.Executor
@@ -671,12 +671,12 @@
     }
 
     /**
-     * Sets the executor for this <code>Service</code> instance.
+     * Sets the executor for this {@code Service} instance.
      *
      * The executor is used for all asynchronous invocations that
      * require callbacks.
      *
-     * @param executor The <code>java.util.concurrent.Executor</code>
+     * @param executor The {@code java.util.concurrent.Executor}
      *        to be used to invoke a callback.
      *
      * @throws SecurityException If the instance does not support
@@ -690,14 +690,14 @@
     }
 
     /**
-     * Creates a <code>Service</code> instance.
+     * Creates a {@code Service} instance.
      *
      * The specified WSDL document location and service qualified name MUST
-     * uniquely identify a <code>wsdl:service</code> element.
+     * uniquely identify a {@code wsdl:service} element.
      *
-     * @param wsdlDocumentLocation <code>URL</code> for the WSDL document location
+     * @param wsdlDocumentLocation {@code URL} for the WSDL document location
      *                             for the service
-     * @param serviceName <code>QName</code> for the service
+     * @param serviceName {@code QName} for the service
      * @throws WebServiceException If any error in creation of the
      *                    specified service.
      **/
@@ -708,15 +708,15 @@
     }
 
     /**
-     * Creates a <code>Service</code> instance. The created instance is
+     * Creates a {@code Service} instance. The created instance is
      * configured with the web service features.
      *
      * The specified WSDL document location and service qualified name MUST
-     * uniquely identify a <code>wsdl:service</code> element.
+     * uniquely identify a {@code wsdl:service} element.
      *
-     * @param wsdlDocumentLocation <code>URL</code> for the WSDL document location
+     * @param wsdlDocumentLocation {@code URL} for the WSDL document location
      *                             for the service
-     * @param serviceName <code>QName</code> for the service
+     * @param serviceName {@code QName} for the service
      * @param features Web Service features that must be configured on
      *        the service. If the provider doesn't understand a feature,
      *        it must throw a WebServiceException.
@@ -731,9 +731,9 @@
     }
 
     /**
-     * Creates a <code>Service</code> instance.
+     * Creates a {@code Service} instance.
      *
-     * @param serviceName <code>QName</code> for the service
+     * @param serviceName {@code QName} for the service
      * @throws WebServiceException If any error in creation of the
      *                    specified service
      */
@@ -742,10 +742,10 @@
     }
 
     /**
-     * Creates a <code>Service</code> instance. The created instance is
+     * Creates a {@code Service} instance. The created instance is
      * configured with the web service features.
      *
-     * @param serviceName <code>QName</code> for the service
+     * @param serviceName {@code QName} for the service
      * @param features Web Service features that must be configured on
      *        the service. If the provider doesn't understand a feature,
      *        it must throw a WebServiceException.
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/ServiceMode.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/ServiceMode.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -44,9 +44,9 @@
 @Documented
 public @interface ServiceMode {
   /**
-   * Service mode. <code>PAYLOAD</code> indicates that the <code>Provider</code> implementation
-   * wishes to work with protocol message payloads only. <code>MESSAGE</code> indicates
-   * that the <code>Provider</code> implementation wishes to work with entire protocol
+   * Service mode. {@code PAYLOAD} indicates that the {@code Provider} implementation
+   * wishes to work with protocol message payloads only. {@code MESSAGE} indicates
+   * that the {@code Provider} implementation wishes to work with entire protocol
    * messages.
   **/
   public Service.Mode value() default Service.Mode.PAYLOAD;
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/WebEndpoint.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/WebEndpoint.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -36,9 +36,9 @@
  *  methods of a generated service interface.
  *
  *  <p>The information specified in this annotation is sufficient
- *  to uniquely identify a <code>wsdl:port</code> element
- *  inside a <code>wsdl:service</code>. The latter is
- *  determined based on the value of the <code>WebServiceClient</code>
+ *  to uniquely identify a {@code wsdl:port} element
+ *  inside a {@code wsdl:service}. The latter is
+ *  determined based on the value of the {@code WebServiceClient}
  *  annotation on the generated service interface itself.
  *
  *  @since 1.6, JAX-WS 2.0
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/WebServiceClient.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/WebServiceClient.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -35,8 +35,8 @@
  *  Used to annotate a generated service interface.
  *
  *  <p>The information specified in this annotation is sufficient
- *  to uniquely identify a <code>wsdl:service</code>
- *  element inside a WSDL document. This <code>wsdl:service</code>
+ *  to uniquely identify a {@code wsdl:service}
+ *  element inside a WSDL document. This {@code wsdl:service}
  *  element represents the Web service for which the generated
  *  service interface provides a client view.
  *
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/WebServiceContext.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/WebServiceContext.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -32,14 +32,14 @@
 
 
 /**
- *  A <code>WebServiceContext</code> makes it possible for
+ *  A {@code WebServiceContext} makes it possible for
  *  a web service endpoint implementation class to access
  *  message context and security information relative to
  *  a request being served.
  *
- *  Typically a <code>WebServiceContext</code> is injected
+ *  Typically a {@code WebServiceContext} is injected
  *  into an endpoint implementation class using the
- *  <code>Resource</code> annotation.
+ *  {@code Resource} annotation.
  *
  *  @since 1.6, JAX-WS 2.0
  *
@@ -48,7 +48,7 @@
 public interface WebServiceContext {
 
     /**
-     * Returns the <code>MessageContext</code> for the request being served
+     * Returns the {@code MessageContext} for the request being served
      * at the time this method is called. Only properties with
      * APPLICATION scope will be visible to the application.
      *
@@ -68,7 +68,7 @@
      * Returns the Principal that identifies the sender
      * of the request currently being serviced. If the
      * sender has not been authenticated, the method
-     * returns <code>null</code>.
+     * returns {@code null}.
      *
      * @return Principal The principal object.
      *
@@ -85,11 +85,11 @@
      * Returns a boolean indicating whether the
      * authenticated user is included in the specified
      * logical role. If the user has not been
-     * authenticated, the method returns <code>false</code>.
+     * authenticated, the method returns {@code false}.
      *
-     * @param role  A <code>String</code> specifying the name of the role
+     * @param role  A {@code String} specifying the name of the role
      *
-     * @return a <code>boolean</code> indicating whether
+     * @return a {@code boolean} indicating whether
      * the sender of the request belongs to a given role
      *
      * @throws IllegalStateException This exception is thrown
@@ -99,20 +99,20 @@
     public boolean isUserInRole(String role);
 
     /**
-     * Returns the <code>EndpointReference</code> for this
+     * Returns the {@code EndpointReference} for this
      * endpoint.
      * <p>
-     * If the {@link Binding} for this <code>bindingProvider</code> is
+     * If the {@link Binding} for this {@code bindingProvider} is
      * either SOAP1.1/HTTP or SOAP1.2/HTTP, then a
-     * <code>W3CEndpointReference</code> MUST be returned.
+     * {@code W3CEndpointReference} MUST be returned.
      *
      * @param referenceParameters Reference parameters to be associated with the
-     * returned <code>EndpointReference</code> instance.
+     * returned {@code EndpointReference} instance.
      * @return EndpointReference of the endpoint associated with this
-     * <code>WebServiceContext</code>.
-     * If the returned <code>EndpointReference</code> is of type
-     * <code>W3CEndpointReference</code> then it MUST contain the
-     * the specified <code>referenceParameters</code>.
+     * {@code WebServiceContext}.
+     * If the returned {@code EndpointReference} is of type
+     * {@code W3CEndpointReference} then it MUST contain the
+     * the specified {@code referenceParameters}.
      *
      * @throws IllegalStateException This exception is thrown
      *         if the method is called while no request is
@@ -125,24 +125,24 @@
     public EndpointReference getEndpointReference(Element... referenceParameters);
 
     /**
-     * Returns the <code>EndpointReference</code> associated with
+     * Returns the {@code EndpointReference} associated with
      * this endpoint.
      *
-     * @param clazz The type of <code>EndpointReference</code> that
+     * @param clazz The type of {@code EndpointReference} that
      * MUST be returned.
      * @param referenceParameters Reference parameters to be associated with the
-     * returned <code>EndpointReference</code> instance.
-     * @return EndpointReference of type <code>clazz</code> of the endpoint
-     * associated with this <code>WebServiceContext</code> instance.
-     * If the returned <code>EndpointReference</code> is of type
-     * <code>W3CEndpointReference</code> then it MUST contain the
-     * the specified <code>referenceParameters</code>.
+     * returned {@code EndpointReference} instance.
+     * @return EndpointReference of type {@code clazz} of the endpoint
+     * associated with this {@code WebServiceContext} instance.
+     * If the returned {@code EndpointReference} is of type
+     * {@code W3CEndpointReference} then it MUST contain the
+     * the specified {@code referenceParameters}.
      *
      * @throws IllegalStateException This exception is thrown
      *         if the method is called while no request is
      *         being serviced.
-     * @throws WebServiceException If the <code>clazz</code> type of
-     * <code>EndpointReference</code> is not supported.
+     * @throws WebServiceException If the {@code clazz} type of
+     * {@code EndpointReference} is not supported.
      *
      * @since 1.6, JAX-WS 2.1
      **/
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/WebServiceException.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/WebServiceException.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -25,7 +25,7 @@
 
 package javax.xml.ws;
 
-/** The <code>WebServiceException</code> class is the base
+/** The {@code WebServiceException} class is the base
  *  exception class for all JAX-WS API runtime exceptions.
  *
  *  @since 1.6, JAX-WS 2.0
@@ -33,7 +33,7 @@
 
 public class WebServiceException extends java.lang.RuntimeException {
 
-  /** Constructs a new exception with <code>null</code> as its
+  /** Constructs a new exception with {@code null} as its
    *  detail message. The cause is not initialized.
   **/
   public WebServiceException() {
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/WebServiceFeature.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/WebServiceFeature.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -34,7 +34,7 @@
  * JAX-WS implementors are free to define additional features if
  * necessary.  Vendor specific features may not be portable so
  * caution should be used when using them. Each Feature definition
- * MUST define a <code>public static final String ID</code>
+ * MUST define a {@code public static final String ID}
  * that can be used in the Feature annotation to refer
  * to the feature. This ID MUST be unique across all features
  * of all vendors.  When defining a vendor specific feature ID,
@@ -71,9 +71,9 @@
 
 
    /**
-    * Returns <code>true</code> if this feature is enabled.
+    * Returns {@code true} if this feature is enabled.
     *
-    * @return <code>true</code> if and only if the feature is enabled .
+    * @return {@code true} if and only if the feature is enabled .
     */
    public boolean isEnabled() {
        return enabled;
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/WebServiceRef.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/WebServiceRef.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -34,7 +34,7 @@
 import java.lang.annotation.RetentionPolicy;
 
 /**
- * The <code>WebServiceRef</code> annotation is used to
+ * The {@code WebServiceRef} annotation is used to
  * define a reference to a web service and
  * (optionally) an injection target for it.
  * It can be used to inject both service and proxy
@@ -47,21 +47,21 @@
  * Web service references are resources in the Java EE 5 sense.
  * The annotations (for example, {@link Addressing}) annotated with
  * meta-annotation {@link WebServiceFeatureAnnotation}
- * can be used in conjunction with <code>WebServiceRef</code>.
+ * can be used in conjunction with {@code WebServiceRef}.
  * The created reference MUST be configured with annotation's web service
  * feature.
  *
  * <p>
  * For example, in the code below, the injected
- * <code>StockQuoteProvider</code> proxy MUST
+ * {@code StockQuoteProvider} proxy MUST
  * have WS-Addressing enabled as specifed by the
  * {@link Addressing}
  * annotation.
  *
  * <pre><code>
  *    public class MyClient {
- *       &#64;Addressing
- *       &#64;WebServiceRef(StockQuoteService.class)
+ *       {@literal @}Addressing
+ *       {@literal @}WebServiceRef(StockQuoteService.class)
  *       private StockQuoteProvider stockQuoteProvider;
  *       ...
  *    }
@@ -69,8 +69,8 @@
  *
  * <p>
  * If a JAX-WS implementation encounters an unsupported or unrecognized
- * annotation annotated with the <code>WebServiceFeatureAnnotation</code>
- * that is specified with <code>WebServiceRef</code>, an ERROR MUST be given.
+ * annotation annotated with the {@code WebServiceFeatureAnnotation}
+ * that is specified with {@code WebServiceRef}, an ERROR MUST be given.
  *
  * @see javax.annotation.Resource
  * @see WebServiceFeatureAnnotation
@@ -91,7 +91,7 @@
      * and this MUST be specified.
      *
      * The JNDI name can be absolute(with any logical namespace) or relative
-     * to JNDI <code>java:comp/env</code> namespace.
+     * to JNDI {@code java:comp/env} namespace.
      */
     String name() default "";
 
@@ -106,11 +106,11 @@
 
     /**
      * A product specific name that this resource should be mapped to.
-     * The name of this resource, as defined by the <code>name</code>
+     * The name of this resource, as defined by the {@code name}
      * element or defaulted, is a name that is local to the application
      * component using the resource.  (When a relative JNDI name
      * is specified, then it's a name in the JNDI
-     * <code>java:comp/env</code> namespace.)  Many application servers
+     * {@code java:comp/env} namespace.)  Many application servers
      * provide a way to map these local names to names of resources
      * known to the application server.  This mapped name is often a
      * <i>global</i> JNDI name, but may be a name of any form.
@@ -124,7 +124,7 @@
 
     /**
      * The service class, always a type extending
-     * <code>javax.xml.ws.Service</code>. This element MUST be specified
+     * {@code javax.xml.ws.Service}. This element MUST be specified
      * whenever the type of the reference is a service endpoint interface.
      */
     // 2.1 has Class value() default Object.class;
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/WebServiceRefs.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/WebServiceRefs.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -32,7 +32,7 @@
 import static java.lang.annotation.RetentionPolicy.*;
 
 /**
- * The <code>WebServiceRefs</code> annotation allows
+ * The {@code WebServiceRefs} annotation allows
  * multiple web service references to be declared at the
  * class level.
  *
@@ -50,13 +50,13 @@
  * to inject the resource along with its features.
  *
  * <p>
- * <b>Example</b>: The <code>StockQuoteProvider</code>
- * proxy instance, and the <code>StockQuoteService</code> service
+ * <b>Example</b>: The {@code StockQuoteProvider}
+ * proxy instance, and the {@code StockQuoteService} service
  * instance are injected using @WebServiceRefs.
  *
  * <pre><code>
- *    &#64;WebServiceRefs({&#64;WebServiceRef(name="service/stockquoteservice", value=StockQuoteService.class),
- *                     &#64;WebServiceRef(name="service/stockquoteprovider", type=StockQuoteProvider.class, value=StockQuoteService.class})
+ *    {@literal @}WebServiceRefs({{@literal @}WebServiceRef(name="service/stockquoteservice", value=StockQuoteService.class),
+ *                     {@literal @}WebServiceRef(name="service/stockquoteprovider", type=StockQuoteProvider.class, value=StockQuoteService.class})
  *    public class MyClient {
  *        void init() {
  *            Context ic = new InitialContext();
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/handler/Handler.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/handler/Handler.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -28,14 +28,14 @@
 import javax.xml.ws.ProtocolException;
 import javax.xml.ws.handler.MessageContext;
 
-/** The <code>Handler</code> interface
+/** The {@code Handler} interface
  *  is the base interface for JAX-WS handlers.
  *
  *  @since 1.6, JAX-WS 2.0
 **/
 public interface Handler<C extends MessageContext> {
 
-  /** The <code>handleMessage</code> method is invoked for normal processing
+  /** The {@code handleMessage} method is invoked for normal processing
    *  of inbound and outbound messages. Refer to the description of the handler
    *  framework in the JAX-WS specification for full details.
    *
@@ -43,9 +43,9 @@
    *  @return An indication of whether handler processing should continue for
    *  the current message
    *                 <ul>
-   *                 <li>Return <code>true</code> to continue
+   *                 <li>Return {@code true} to continue
    *                     processing.</li>
-   *                 <li>Return <code>false</code> to block
+   *                 <li>Return {@code false} to block
    *                     processing.</li>
    *                  </ul>
    *  @throws RuntimeException Causes the JAX-WS runtime to cease
@@ -55,7 +55,7 @@
   **/
   public boolean handleMessage(C context);
 
-  /** The <code>handleFault</code> method is invoked for fault message
+  /** The {@code handleFault} method is invoked for fault message
    *  processing.  Refer to the description of the handler
    *  framework in the JAX-WS specification for full details.
    *
@@ -63,9 +63,9 @@
    *  @return An indication of whether handler fault processing should continue
    *  for the current message
    *                 <ul>
-   *                 <li>Return <code>true</code> to continue
+   *                 <li>Return {@code true} to continue
    *                     processing.</li>
-   *                 <li>Return <code>false</code> to block
+   *                 <li>Return {@code false} to block
    *                     processing.</li>
    *                  </ul>
    *  @throws RuntimeException Causes the JAX-WS runtime to cease
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/handler/LogicalHandler.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/handler/LogicalHandler.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -25,7 +25,7 @@
 
 package javax.xml.ws.handler;
 
-/** The <code>LogicalHandler</code> extends
+/** The {@code LogicalHandler} extends
  *  Handler to provide typesafety for the message context parameter.
  *
  *  @since 1.6, JAX-WS 2.0
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/handler/LogicalMessageContext.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/handler/LogicalMessageContext.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -27,8 +27,8 @@
 
 import javax.xml.ws.LogicalMessage;
 
-/** The <code>LogicalMessageContext</code> interface extends
- *  <code>MessageContext</code> to
+/** The {@code LogicalMessageContext} interface extends
+ *  {@code MessageContext} to
  *  provide access to a the contained message as a protocol neutral
  *  LogicalMessage
  *
@@ -39,7 +39,7 @@
 
   /** Gets the message from this message context
    *
-   *  @return The contained message; returns <code>null</code> if no
+   *  @return The contained message; returns {@code null} if no
    *          message is present in this message context
   **/
   public LogicalMessage getMessage();
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/handler/PortInfo.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/handler/PortInfo.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -28,8 +28,8 @@
 import javax.xml.namespace.QName;
 
 /**
- *  The <code>PortInfo</code> interface is used by a
- *  <code>HandlerResolver</code> to query information about
+ *  The {@code PortInfo} interface is used by a
+ *  {@code HandlerResolver} to query information about
  *  the port it is being asked to create a handler chain for.
  *  <p>
  *  This interface is never implemented by an application,
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/handler/soap/SOAPHandler.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/handler/soap/SOAPHandler.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -29,7 +29,7 @@
 import javax.xml.ws.handler.Handler;
 import java.util.Set;
 
-/** The <code>SOAPHandler</code> class extends <code>Handler</code>
+/** The {@code SOAPHandler} class extends {@code Handler}
  *  to provide typesafety for the message context parameter and add a method
  *  to obtain access to the headers that may be processed by the handler.
  *
@@ -41,8 +41,8 @@
   /** Gets the header blocks that can be processed by this Handler
    *  instance.
    *
-   *  @return Set of <code>QNames</code> of header blocks processed by this
-   *           handler instance. <code>QName</code> is the qualified
+   *  @return Set of {@code QNames} of header blocks processed by this
+   *           handler instance. {@code QName} is the qualified
    *           name of the outermost element of the Header block.
   **/
   Set<QName> getHeaders();
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/handler/soap/SOAPMessageContext.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/handler/soap/SOAPMessageContext.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -30,9 +30,9 @@
 import javax.xml.namespace.QName;
 import java.util.Set;
 
-/** The interface <code>SOAPMessageContext</code>
+/** The interface {@code SOAPMessageContext}
  *  provides access to the SOAP message for either RPC request or
- *  response. The <code>javax.xml.soap.SOAPMessage</code> specifies
+ *  response. The {@code javax.xml.soap.SOAPMessage} specifies
  *  the standard Java API for the representation of a SOAP 1.1 message
  *  with attachments.
  *
@@ -43,20 +43,20 @@
 public interface SOAPMessageContext
                     extends javax.xml.ws.handler.MessageContext {
 
-  /** Gets the <code>SOAPMessage</code> from this message context. Modifications
-   *  to the returned <code>SOAPMessage</code> change the message in-place, there
-   *  is no need to subsequently call <code>setMessage</code>.
+  /** Gets the {@code SOAPMessage} from this message context. Modifications
+   *  to the returned {@code SOAPMessage} change the message in-place, there
+   *  is no need to subsequently call {@code setMessage}.
    *
-   *  @return Returns the <code>SOAPMessage</code>; returns <code>null</code> if no
-   *          <code>SOAPMessage</code> is present in this message context
+   *  @return Returns the {@code SOAPMessage}; returns {@code null} if no
+   *          {@code SOAPMessage} is present in this message context
   **/
   public SOAPMessage getMessage();
 
   /** Sets the SOAPMessage in this message context
    *
    *  @param  message SOAP message
-   *  @throws WebServiceException If any error during the setting
-   *          of the <code>SOAPMessage</code> in this message context
+   *  @throws javax.xml.ws.WebServiceException If any error during the setting
+   *          of the {@code SOAPMessage} in this message context
    *  @throws java.lang.UnsupportedOperationException If this
    *          operation is not supported
   **/
@@ -69,16 +69,16 @@
    *  @param  header The XML qualified name of the SOAP header(s).
    *  @param  context The JAXBContext that should be used to unmarshall the
    *          header
-   *  @param  allRoles If <code>true</code> then returns headers for all SOAP
-   *          roles, if <code>false</code> then only returns headers targetted
+   *  @param  allRoles If {@code true} then returns headers for all SOAP
+   *          roles, if {@code false} then only returns headers targetted
    *          at the roles currently being played by this SOAP node, see
-   *          <code>getRoles</code>.
+   *          {@code getRoles}.
    *  @return An array of unmarshalled headers; returns an empty array if no
    *          message is present in this message context or no headers match
    *          the supplied qualified name.
-   *  @throws WebServiceException If an error occurs when using the supplied
-   *     <code>JAXBContext</code> to unmarshall. The cause of
-   *     the <code>WebServiceException</code> is the original <code>JAXBException</code>.
+   *  @throws javax.xml.ws.WebServiceException If an error occurs when using the supplied
+   *     {@code JAXBContext} to unmarshall. The cause of
+   *     the {@code WebServiceException} is the original {@code JAXBException}.
   **/
   public Object[] getHeaders(QName header, JAXBContext context,
     boolean allRoles);
@@ -87,13 +87,13 @@
    *  of the handler chain.
    *  Note that SOAP actor roles apply to the SOAP node and
    *  are managed using {@link javax.xml.ws.soap.SOAPBinding#setRoles} and
-   *  {@link javax.xml.ws.soap.SOAPBinding#getRoles}. <code>Handler</code> instances in
+   *  {@link javax.xml.ws.soap.SOAPBinding#getRoles}. {@code Handler} instances in
    *  the handler chain use this information about the SOAP actor
    *  roles to process the SOAP header blocks. Note that the
    *  SOAP actor roles are invariant during the processing of
    *  SOAP message through the handler chain.
    *
-   *  @return Array of <code>String</code> for SOAP actor roles
+   *  @return Array of {@code String} for SOAP actor roles
   **/
   public Set<String> getRoles();
 }
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/http/HTTPBinding.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/http/HTTPBinding.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -28,7 +28,7 @@
 
 import javax.xml.ws.Binding;
 
-/** The <code>HTTPBinding</code> interface is an
+/** The {@code HTTPBinding} interface is an
  *  abstraction for the XML/HTTP binding.
  *
  *  @since 1.6, JAX-WS 2.0
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/http/HTTPException.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/http/HTTPException.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -26,7 +26,7 @@
 package javax.xml.ws.http;
 
 
-/** The <code>HTTPException</code> exception represents a
+/** The {@code HTTPException} exception represents a
  *  XML/HTTP fault.
  *
  *  <p>Since there is no standard format for faults or exceptions
@@ -39,7 +39,7 @@
   private int statusCode;
 
   /** Constructor for the HTTPException
-   *  @param statusCode   <code>int</code> for the HTTP status code
+   *  @param statusCode   {@code int} for the HTTP status code
   **/
   public HTTPException(int statusCode) {
     super();
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/soap/Addressing.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/soap/Addressing.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -46,12 +46,12 @@
  * This annotation MUST only be used in conjunction with the
  * {@link javax.jws.WebService}, {@link WebServiceProvider},
  *  and {@link WebServiceRef} annotations.
- * When used with a <code>javax.jws.WebService</code> annotation, this
+ * When used with a {@code javax.jws.WebService} annotation, this
  * annotation MUST only be used on the service endpoint implementation
  * class.
- * When used with a <code>WebServiceRef</code> annotation, this annotation
+ * When used with a {@code WebServiceRef} annotation, this annotation
  * MUST only be used when a proxy instance is created. The injected SEI
- * proxy, and endpoint MUST honor the values of the <code>Addressing</code>
+ * proxy, and endpoint MUST honor the values of the {@code Addressing}
  * annotation.
  * <p>
  * This annotation's behaviour is defined by the corresponding feature
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/soap/SOAPBinding.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/soap/SOAPBinding.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -70,7 +70,7 @@
   /** Sets the roles played by the SOAP binding instance.
    *
    *  @param roles    The set of roles played by the binding instance.
-   *  @throws WebServiceException On an error in the configuration of
+   *  @throws javax.xml.ws.WebServiceException On an error in the configuration of
    *                  the list of roles.
   **/
   public void setRoles(Set<String> roles);
@@ -88,7 +88,7 @@
    *
    * @param flag   A {@code boolean} specifying whether the use of MTOM should
    *               be enabled or disabled.
-   * @throws WebServiceException If the specified setting is not supported
+   * @throws javax.xml.ws.WebServiceException If the specified setting is not supported
    *                  by this binding instance.
    *
    **/
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/soap/SOAPFaultException.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/soap/SOAPFaultException.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -27,18 +27,18 @@
 
 import javax.xml.soap.SOAPFault;
 
-/** The <code>SOAPFaultException</code> exception represents a
+/** The {@code SOAPFaultException} exception represents a
  *  SOAP 1.1 or 1.2 fault.
  *
- *  <p>A <code>SOAPFaultException</code> wraps a SAAJ <code>SOAPFault</code>
+ *  <p>A {@code SOAPFaultException} wraps a SAAJ {@code SOAPFault}
  *  that manages the SOAP-specific representation of faults.
- *  The <code>createFault</code> method of
- *  <code>javax.xml.soap.SOAPFactory</code> may be used to create an instance
- *  of <code>javax.xml.soap.SOAPFault</code> for use with the
- *  constructor. <code>SOAPBinding</code> contains an accessor for the
- *  <code>SOAPFactory</code> used by the binding instance.
+ *  The {@code createFault} method of
+ *  {@code javax.xml.soap.SOAPFactory} may be used to create an instance
+ *  of {@code javax.xml.soap.SOAPFault} for use with the
+ *  constructor. {@code SOAPBinding} contains an accessor for the
+ *  {@code SOAPFactory} used by the binding instance.
  *
- *  <p>Note that the value of <code>getFault</code> is the only part of the
+ *  <p>Note that the value of {@code getFault} is the only part of the
  *  exception used when searializing a SOAP fault.
  *
  *  <p>Refer to the SOAP specification for a complete
@@ -55,7 +55,7 @@
     private SOAPFault fault;
 
     /** Constructor for SOAPFaultException
-     *  @param fault   <code>SOAPFault</code> representing the fault
+     *  @param fault   {@code SOAPFault} representing the fault
      *
      *  @see javax.xml.soap.SOAPFactory#createFault
      **/
@@ -64,9 +64,9 @@
         this.fault = fault;
     }
 
-    /** Gets the embedded <code>SOAPFault</code> instance.
+    /** Gets the embedded {@code SOAPFault} instance.
      *
-     *  @return <code>javax.xml.soap.SOAPFault</code> SOAP
+     *  @return {@code javax.xml.soap.SOAPFault} SOAP
      *          fault element
      **/
     public javax.xml.soap.SOAPFault getFault() {
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/spi/FactoryFinder.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/spi/FactoryFinder.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -34,7 +34,7 @@
 
     /**
      * Creates an instance of the specified class using the specified
-     * <code>ClassLoader</code> object.
+     * {@code ClassLoader} object.
      *
      * @exception WebServiceException if the given class could not be found
      *            or could not be instantiated
@@ -56,22 +56,22 @@
     }
 
     /**
-     * Finds the implementation <code>Class</code> object for the given
-     * factory name, or if that fails, finds the <code>Class</code> object
+     * Finds the implementation {@code Class} object for the given
+     * factory name, or if that fails, finds the {@code Class} object
      * for the given fallback class name. The arguments supplied MUST be
      * used in order. If using the first argument is successful, the second
      * one will not be used.
      * <P>
      * This method is package private so that this code can be shared.
      *
-     * @return the <code>Class</code> object of the specified message factory;
-     *         may not be <code>null</code>
+     * @return the {@code Class} object of the specified message factory;
+     *         may not be {@code null}
      *
      * @param factoryId             the name of the factory to find, which is
      *                              a system property
      * @param fallbackClassName     the implementation class name, which is
      *                              to be used only if nothing else
-     *                              is found; <code>null</code> to indicate that
+     *                              is found; {@code null} to indicate that
      *                              there is no fallback class name
      * @exception WebServiceException if there is an error
      */
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/spi/Invoker.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/spi/Invoker.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2009, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2009, 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
@@ -37,8 +37,8 @@
  * for a web service invocation. Finally, Invoker does the actual
  * invocation of web service on endpoint instance.
  *
- * Container also injects the provided <code>WebServiceContext</code> and takes
- * care of invoking <code>javax.annotation.PostConstruct</code> methods,
+ * Container also injects the provided {@code WebServiceContext} and takes
+ * care of invoking {@code javax.annotation.PostConstruct} methods,
  * if present, on the endpoint implementation.
  *
  * @see Provider#createEndpoint(String, Class, Invoker, WebServiceFeature...)
@@ -51,7 +51,7 @@
     /**
      * JAX-WS runtimes calls this method to ask container to inject
      * WebServiceContext on the endpoint instance. The
-     * <code>WebServiceContext</code> object uses thread-local information
+     * {@code WebServiceContext} object uses thread-local information
      * to return the correct information during the actual endpoint invocation
      * regardless of how many threads are concurrently being used to serve
      * requests.
@@ -70,7 +70,7 @@
     /**
      * JAX-WS runtime calls this method to do the actual web service
      * invocation on endpoint instance. The injected
-     * <code>WebServiceContext.getMessageContext()</code> gives the correct
+     * {@code WebServiceContext.getMessageContext()} gives the correct
      * information for this invocation.
      *
      * @param m Method to be invoked on the service
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/spi/Provider.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/spi/Provider.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -288,7 +288,7 @@
      * method can automatically determine the {@code address} of
      * an endpoint that is published by the same Java EE application and is
      * identified by the {@code serviceName} and
-     * {@code portName} propeties.  If the {@code address} is
+     * {@code portName} properties.  If the {@code address} is
      * {@code null} and the {@code serviceName} and
      * {@code portName} do not identify an endpoint published by the
      * same Java EE application, a
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/spi/ServiceDelegate.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/spi/ServiceDelegate.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -37,11 +37,11 @@
 
 
 /**
- * Service delegates are used internally by <code>Service</code> objects
+ * Service delegates are used internally by {@code Service} objects
  * to allow pluggability of JAX-WS implementations.
  * <p>
- * Every <code>Service</code> object has its own delegate, created using
- * the {@link javax.xml.ws.spi.Provider#createServiceDelegate} method. A <code>Service</code>
+ * Every {@code Service} object has its own delegate, created using
+ * the {@link javax.xml.ws.spi.Provider#createServiceDelegate} method. A {@code Service}
  * object delegates all of its instance methods to its delegate.
  *
  * @see javax.xml.ws.Service
@@ -55,9 +55,9 @@
     }
 
     /**
-     * The <code>getPort</code> method returns a proxy. A service client
+     * The {@code getPort} method returns a proxy. A service client
      * uses this proxy to invoke operations on the target
-     * service endpoint. The <code>serviceEndpointInterface</code>
+     * service endpoint. The {@code serviceEndpointInterface}
      * specifies the service endpoint interface that is supported by
      * the created dynamic proxy instance.
      *
@@ -76,8 +76,8 @@
      *                  <LI>If there is any missing WSDL metadata
      *                      as required by this method
      *                  <LI>If an illegal
-     *                      <code>serviceEndpointInterface</code>
-     *                      or <code>portName</code> is specified
+     *                      {@code serviceEndpointInterface}
+     *                      or {@code portName} is specified
      *                  </UL>
      * @see java.lang.reflect.Proxy
      * @see java.lang.reflect.InvocationHandler
@@ -86,9 +86,9 @@
             Class<T> serviceEndpointInterface);
 
     /**
-     * The <code>getPort</code> method returns a proxy. A service client
+     * The {@code getPort} method returns a proxy. A service client
      * uses this proxy to invoke operations on the target
-     * service endpoint. The <code>serviceEndpointInterface</code>
+     * service endpoint. The {@code serviceEndpointInterface}
      * specifies the service endpoint interface that is supported by
      * the created dynamic proxy instance.
      *
@@ -97,8 +97,8 @@
      * @param serviceEndpointInterface Service endpoint interface
      *                  supported by the dynamic proxy or instance
      * @param features  A list of WebServiceFeatures to configure on the
-     *                proxy.  Supported features not in the <code>features
-     *                </code> parameter will have their default values.
+     *                proxy.  Supported features not in the {@code features
+     *                } parameter will have their default values.
      * @return Object Proxy instance that
      *                supports the specified service endpoint
      *                interface
@@ -110,8 +110,8 @@
      *                  <LI>If there is any missing WSDL metadata
      *                      as required by this method
      *                  <LI>If an illegal
-     *                      <code>serviceEndpointInterface</code>
-     *                      or <code>portName</code> is specified
+     *                      {@code serviceEndpointInterface}
+     *                      or {@code portName} is specified
      *                  <LI>If a feature is enabled that is not compatible
      *                      with this port or is unsupported.
      *                  </UL>
@@ -125,31 +125,31 @@
             Class<T> serviceEndpointInterface, WebServiceFeature... features);
 
     /**
-     * The <code>getPort</code> method returns a proxy.
-     * The parameter <code>endpointReference</code> specifies the
+     * The {@code getPort} method returns a proxy.
+     * The parameter {@code endpointReference} specifies the
      * endpoint that will be invoked by the returned proxy.  If there
      * are any reference parameters in the
-     * <code>endpointReference</code>, then those reference
+     * {@code endpointReference}, then those reference
      * parameters MUST appear as SOAP headers, indicating them to be
      * reference parameters, on all messages sent to the endpoint.
-     * The <code>endpointReference's</code> address MUST be used
+     * The {@code endpointReference's} address MUST be used
      * for invocations on the endpoint.
-     * The parameter <code>serviceEndpointInterface</code> specifies
+     * The parameter {@code serviceEndpointInterface} specifies
      * the service endpoint interface that is supported by the
      * returned proxy.
      * In the implementation of this method, the JAX-WS
      * runtime system takes the responsibility of selecting a protocol
      * binding (and a port) and configuring the proxy accordingly from
-     * the WSDL associated with this <code>Service</code> instance or
-     * from the metadata from the <code>endpointReference</code>.
-     * If this <code>Service</code> instance has a WSDL and
-     * the <code>endpointReference</code> metadata
+     * the WSDL associated with this {@code Service} instance or
+     * from the metadata from the {@code endpointReference}.
+     * If this {@code Service} instance has a WSDL and
+     * the {@code endpointReference} metadata
      * also has a WSDL, then the WSDL from this instance MUST be used.
-     * If this <code>Service</code> instance does not have a WSDL and
-     * the <code>endpointReference</code> does have a WSDL, then the
-     * WSDL from the <code>endpointReference</code> MAY be used.
+     * If this {@code Service} instance does not have a WSDL and
+     * the {@code endpointReference} does have a WSDL, then the
+     * WSDL from the {@code endpointReference} MAY be used.
      * The returned proxy should not be reconfigured by the client.
-     * If this <code>Service</code> instance has a known proxy
+     * If this {@code Service} instance has a known proxy
      * port that matches the information contained in
      * the WSDL,
      * then that proxy is returned, otherwise a WebServiceException
@@ -157,20 +157,20 @@
      * <p>
      * Calling this method has the same behavior as the following
      * <pre>
-     * <code>port = service.getPort(portName, serviceEndpointInterface);</code>
+     * {@code port = service.getPort(portName, serviceEndpointInterface);}
      * </pre>
-     * where the <code>portName</code> is retrieved from the
-     * metadata of the <code>endpointReference</code> or from the
-     * <code>serviceEndpointInterface</code> and the WSDL
-     * associated with this <code>Service</code> instance.
+     * where the {@code portName} is retrieved from the
+     * metadata of the {@code endpointReference} or from the
+     * {@code serviceEndpointInterface} and the WSDL
+     * associated with this {@code Service} instance.
      *
-     * @param endpointReference  The <code>EndpointReference</code>
+     * @param endpointReference  The {@code EndpointReference}
      * for the target service endpoint that will be invoked by the
      * returned proxy.
      * @param serviceEndpointInterface Service endpoint interface.
-     * @param features  A list of <code>WebServiceFeatures</code> to configure on the
-     *                proxy.  Supported features not in the <code>features
-     *                </code> parameter will have their default values.
+     * @param features  A list of {@code WebServiceFeatures} to configure on the
+     *                proxy.  Supported features not in the {@code features
+     *                } parameter will have their default values.
      * @return Object Proxy instance that supports the
      *                  specified service endpoint interface.
      * @throws WebServiceException
@@ -179,16 +179,16 @@
      *                      of the proxy.
      *                  <LI>If there is any missing WSDL metadata
      *                      as required by this method.
-     *                  <LI>If the <code>endpointReference</code> metadata does
-     *                      not match the <code>serviceName</code> of this
-     *                      <code>Service</code> instance.
-     *                  <LI>If a <code>portName</code> cannot be extracted
-     *                      from the WSDL or <code>endpointReference</code> metadata.
+     *                  <LI>If the {@code endpointReference} metadata does
+     *                      not match the {@code serviceName} of this
+     *                      {@code Service} instance.
+     *                  <LI>If a {@code portName} cannot be extracted
+     *                      from the WSDL or {@code endpointReference} metadata.
      *                  <LI>If an invalid
-     *                      <code>endpointReference</code>
+     *                      {@code endpointReference}
      *                      is specified.
      *                  <LI>If an invalid
-     *                      <code>serviceEndpointInterface</code>
+     *                      {@code serviceEndpointInterface}
      *                      is specified.
      *                  <LI>If a feature is enabled that is not compatible
      *                      with this port or is unsupported.
@@ -201,8 +201,8 @@
 
 
     /**
-     * The <code>getPort</code> method returns a proxy. The parameter
-     * <code>serviceEndpointInterface</code> specifies the service
+     * The {@code getPort} method returns a proxy. The parameter
+     * {@code serviceEndpointInterface} specifies the service
      * endpoint interface that is supported by the returned proxy.
      * In the implementation of this method, the JAX-WS
      * runtime system takes the responsibility of selecting a protocol
@@ -219,7 +219,7 @@
      *                  <LI>If there is any missing WSDL metadata
      *                      as required by this method
      *                  <LI>If an illegal
-     *                      <code>serviceEndpointInterface</code>
+     *                      {@code serviceEndpointInterface}
      *                      is specified
      *                  </UL>
      **/
@@ -227,8 +227,8 @@
 
 
     /**
-     * The <code>getPort</code> method returns a proxy. The parameter
-     * <code>serviceEndpointInterface</code> specifies the service
+     * The {@code getPort} method returns a proxy. The parameter
+     * {@code serviceEndpointInterface} specifies the service
      * endpoint interface that is supported by the returned proxy.
      * In the implementation of this method, the JAX-WS
      * runtime system takes the responsibility of selecting a protocol
@@ -236,9 +236,9 @@
      * The returned proxy should not be reconfigured by the client.
      *
      * @param serviceEndpointInterface Service endpoint interface
-     * @param features  An array of <code>WebServiceFeatures</code> to configure on the
-     *                proxy.  Supported features not in the <code>features
-     *                </code> parameter will have their default values.
+     * @param features  An array of {@code WebServiceFeatures} to configure on the
+     *                proxy.  Supported features not in the {@code features
+     *                } parameter will have their default values.
      * @return Object instance that supports the
      *                  specified service endpoint interface
      * @throws WebServiceException
@@ -248,7 +248,7 @@
      *                  <LI>If there is any missing WSDL metadata
      *                      as required by this method
      *                  <LI>If an illegal
-     *                      <code>serviceEndpointInterface</code>
+     *                      {@code serviceEndpointInterface}
      *                      is specified
      *                  <LI>If a feature is enabled that is not compatible
      *                      with this port or is unsupported.
@@ -265,7 +265,7 @@
     /**
      * Creates a new port for the service. Ports created in this way contain
      * no WSDL port type information and can only be used for creating
-     * <code>Dispatch</code>instances.
+     * {@code Dispatch}instances.
      *
      * @param portName  Qualified name for the target service endpoint
      * @param bindingId A URI identifier of a binding.
@@ -283,23 +283,23 @@
 
 
     /**
-     * Creates a <code>Dispatch</code> instance for use with objects of
+     * Creates a {@code Dispatch} instance for use with objects of
      * the user's choosing.
      *
      * @param portName  Qualified name for the target service endpoint
      * @param type The class of object used for messages or message
      * payloads. Implementations are required to support
-     * <code>javax.xml.transform.Source</code> and <code>javax.xml.soap.SOAPMessage</code>.
+     * {@code javax.xml.transform.Source} and {@code javax.xml.soap.SOAPMessage}.
      * @param mode Controls whether the created dispatch instance is message
      * or payload oriented, i.e. whether the user will work with complete
      * protocol messages or message payloads. E.g. when using the SOAP
      * protocol, this parameter controls whether the user will work with
-     * SOAP messages or the contents of a SOAP body. Mode MUST be <code>MESSAGE</code>
-     * when type is <code>SOAPMessage</code>.
+     * SOAP messages or the contents of a SOAP body. Mode MUST be {@code MESSAGE}
+     * when type is {@code SOAPMessage}.
      *
      * @return Dispatch instance
      * @throws WebServiceException If any error in the creation of
-     *                  the <code>Dispatch</code> object
+     *                  the {@code Dispatch} object
      * @see javax.xml.transform.Source
      * @see javax.xml.soap.SOAPMessage
      **/
@@ -307,26 +307,26 @@
             Service.Mode mode);
 
     /**
-     * Creates a <code>Dispatch</code> instance for use with objects of
+     * Creates a {@code Dispatch} instance for use with objects of
      * the user's choosing.
      *
      * @param portName  Qualified name for the target service endpoint
      * @param type The class of object used for messages or message
      * payloads. Implementations are required to support
-     * <code>javax.xml.transform.Source</code> and <code>javax.xml.soap.SOAPMessage</code>.
+     * {@code javax.xml.transform.Source} and {@code javax.xml.soap.SOAPMessage}.
      * @param mode Controls whether the created dispatch instance is message
      * or payload oriented, i.e. whether the user will work with complete
      * protocol messages or message payloads. E.g. when using the SOAP
      * protocol, this parameter controls whether the user will work with
-     * SOAP messages or the contents of a SOAP body. Mode MUST be <code>MESSAGE</code>
-     * when type is <code>SOAPMessage</code>.
-     * @param features  A list of <code>WebServiceFeatures</code> to configure on the
-     *                proxy.  Supported features not in the <code>features
-     *                </code> parameter will have their default values.
+     * SOAP messages or the contents of a SOAP body. Mode MUST be {@code MESSAGE}
+     * when type is {@code SOAPMessage}.
+     * @param features  A list of {@code WebServiceFeatures} to configure on the
+     *                proxy.  Supported features not in the {@code features
+     *                } parameter will have their default values.
      *
      * @return Dispatch instance
      * @throws WebServiceException If any error in the creation of
-     *                  the <code>Dispatch</code> object or if a
+     *                  the {@code Dispatch} object or if a
      *                  feature is enabled that is not compatible with
      *                  this port or is unsupported.
      *
@@ -340,64 +340,64 @@
             Service.Mode mode, WebServiceFeature... features);
 
     /**
-     * Creates a <code>Dispatch</code> instance for use with objects of
+     * Creates a {@code Dispatch} instance for use with objects of
      * the user's choosing. If there
      * are any reference parameters in the
-     * <code>endpointReference</code>, then those reference
+     * {@code endpointReference}, then those reference
      * parameters MUST appear as SOAP headers, indicating them to be
      * reference parameters, on all messages sent to the endpoint.
-     * The <code>endpointReference's</code> address MUST be used
+     * The {@code endpointReference's} address MUST be used
      * for invocations on the endpoint.
      * In the implementation of this method, the JAX-WS
      * runtime system takes the responsibility of selecting a protocol
      * binding (and a port) and configuring the dispatch accordingly from
-     * the WSDL associated with this <code>Service</code> instance or
-     * from the metadata from the <code>endpointReference</code>.
-     * If this <code>Service</code> instance has a WSDL and
-     * the <code>endpointReference</code>
+     * the WSDL associated with this {@code Service} instance or
+     * from the metadata from the {@code endpointReference}.
+     * If this {@code Service} instance has a WSDL and
+     * the {@code endpointReference}
      * also has a WSDL in its metadata, then the WSDL from this instance MUST be used.
-     * If this <code>Service</code> instance does not have a WSDL and
-     * the <code>endpointReference</code> does have a WSDL, then the
-     * WSDL from the <code>endpointReference</code> MAY be used.
-     * An implementation MUST be able to retrieve the <code>portName</code> from the
-     * <code>endpointReference</code> metadata.
+     * If this {@code Service} instance does not have a WSDL and
+     * the {@code endpointReference} does have a WSDL, then the
+     * WSDL from the {@code endpointReference} MAY be used.
+     * An implementation MUST be able to retrieve the {@code portName} from the
+     * {@code endpointReference} metadata.
      * <p>
      * This method behaves the same as calling
      * <pre>
-     * <code>dispatch = service.createDispatch(portName, type, mode, features);</code>
+     * {@code dispatch = service.createDispatch(portName, type, mode, features);}
      * </pre>
-     * where the <code>portName</code> is retrieved from the
-     * WSDL or <code>EndpointReference</code> metadata.
+     * where the {@code portName} is retrieved from the
+     * WSDL or {@code EndpointReference} metadata.
      *
-     * @param endpointReference  The <code>EndpointReference</code>
+     * @param endpointReference  The {@code EndpointReference}
      * for the target service endpoint that will be invoked by the
-     * returned <code>Dispatch</code> object.
+     * returned {@code Dispatch} object.
      * @param type The class of object used to messages or message
      * payloads. Implementations are required to support
-     * <code>javax.xml.transform.Source</code> and <code>javax.xml.soap.SOAPMessage</code>.
+     * {@code javax.xml.transform.Source} and {@code javax.xml.soap.SOAPMessage}.
      * @param mode Controls whether the created dispatch instance is message
      * or payload oriented, i.e. whether the user will work with complete
      * protocol messages or message payloads. E.g. when using the SOAP
      * protocol, this parameter controls whether the user will work with
-     * SOAP messages or the contents of a SOAP body. Mode MUST be <code>MESSAGE</code>
-     * when type is <code>SOAPMessage</code>.
-     * @param features  An array of <code>WebServiceFeatures</code> to configure on the
-     *                proxy.  Supported features not in the <code>features
-     *                </code> parameter will have their default values.
+     * SOAP messages or the contents of a SOAP body. Mode MUST be {@code MESSAGE}
+     * when type is {@code SOAPMessage}.
+     * @param features  An array of {@code WebServiceFeatures} to configure on the
+     *                proxy.  Supported features not in the {@code features
+     *                } parameter will have their default values.
      *
      * @return Dispatch instance
      * @throws WebServiceException
      *                  <UL>
      *                    <LI>If there is any missing WSDL metadata
      *                      as required by this method.
-     *                    <li>If the <code>endpointReference</code> metadata does
-     *                      not match the <code>serviceName</code> or <code>portName</code>
+     *                    <li>If the {@code endpointReference} metadata does
+     *                      not match the {@code serviceName} or {@code portName}
      *                      of a WSDL associated
-     *                      with this <code>Service</code> instance.
-     *                    <li>If the <code>portName</code> cannot be determined
-     *                    from the <code>EndpointReference</code> metadata.
+     *                      with this {@code Service} instance.
+     *                    <li>If the {@code portName} cannot be determined
+     *                    from the {@code EndpointReference} metadata.
      *                    <li>If any error in the creation of
-     *                     the <code>Dispatch</code> object.
+     *                     the {@code Dispatch} object.
      *                    <li>If a feature is enabled that is not
      *                    compatible with this port or is unsupported.
      *                  </UL>
@@ -415,7 +415,7 @@
 
 
     /**
-     * Creates a <code>Dispatch</code> instance for use with JAXB
+     * Creates a {@code Dispatch} instance for use with JAXB
      * generated objects.
      *
      * @param portName  Qualified name for the target service endpoint
@@ -429,7 +429,7 @@
      *
      * @return Dispatch instance
      * @throws WebServiceException If any error in the creation of
-     *                  the <code>Dispatch</code> object
+     *                  the {@code Dispatch} object
      *
      * @see javax.xml.bind.JAXBContext
      **/
@@ -438,7 +438,7 @@
 
 
     /**
-     * Creates a <code>Dispatch</code> instance for use with JAXB
+     * Creates a {@code Dispatch} instance for use with JAXB
      * generated objects.
      *
      * @param portName  Qualified name for the target service endpoint
@@ -449,13 +449,13 @@
      * protocol messages or message payloads. E.g. when using the SOAP
      * protocol, this parameter controls whether the user will work with
      * SOAP messages or the contents of a SOAP body.
-     * @param features  A list of <code>WebServiceFeatures</code> to configure on the
-     *                proxy.  Supported features not in the <code>features
-     *                </code> parameter will have their default values.
+     * @param features  A list of {@code WebServiceFeatures} to configure on the
+     *                proxy.  Supported features not in the {@code features
+     *                } parameter will have their default values.
      *
      * @return Dispatch instance
      * @throws WebServiceException If any error in the creation of
-     *                  the <code>Dispatch</code> object or if a
+     *                  the {@code Dispatch} object or if a
      *                  feature is enabled that is not compatible with
      *                  this port or is unsupported.
      *
@@ -468,39 +468,39 @@
             JAXBContext context, Service.Mode mode, WebServiceFeature... features);
 
     /**
-     * Creates a <code>Dispatch</code> instance for use with JAXB
+     * Creates a {@code Dispatch} instance for use with JAXB
      * generated objects. If there
      * are any reference parameters in the
-     * <code>endpointReference</code>, then those reference
+     * {@code endpointReference}, then those reference
      * parameters MUST appear as SOAP headers, indicating them to be
      * reference parameters, on all messages sent to the endpoint.
-     * The <code>endpointReference's</code> address MUST be used
+     * The {@code endpointReference's} address MUST be used
      * for invocations on the endpoint.
      * In the implementation of this method, the JAX-WS
      * runtime system takes the responsibility of selecting a protocol
      * binding (and a port) and configuring the dispatch accordingly from
-     * the WSDL associated with this <code>Service</code> instance or
-     * from the metadata from the <code>endpointReference</code>.
-     * If this <code>Service</code> instance has a WSDL and
-     * the <code>endpointReference</code>
+     * the WSDL associated with this {@code Service} instance or
+     * from the metadata from the {@code endpointReference}.
+     * If this {@code Service} instance has a WSDL and
+     * the {@code endpointReference}
      * also has a WSDL in its metadata, then the WSDL from this instance
      * MUST be used.
-     * If this <code>Service</code> instance does not have a WSDL and
-     * the <code>endpointReference</code> does have a WSDL, then the
-     * WSDL from the <code>endpointReference</code> MAY be used.
-     * An implementation MUST be able to retrieve the <code>portName</code> from the
-     * <code>endpointReference</code> metadata.
+     * If this {@code Service} instance does not have a WSDL and
+     * the {@code endpointReference} does have a WSDL, then the
+     * WSDL from the {@code endpointReference} MAY be used.
+     * An implementation MUST be able to retrieve the {@code portName} from the
+     * {@code endpointReference} metadata.
      * <p>
      * This method behavies the same as calling
      * <pre>
-     * <code>dispatch = service.createDispatch(portName, context, mode, features);</code>
+     * {@code dispatch = service.createDispatch(portName, context, mode, features);}
      * </pre>
-     * where the <code>portName</code> is retrieved from the
-     * WSDL or <code>endpointReference</code> metadata.
+     * where the {@code portName} is retrieved from the
+     * WSDL or {@code endpointReference} metadata.
      *
-     * @param endpointReference  The <code>EndpointReference</code>
+     * @param endpointReference  The {@code EndpointReference}
      * for the target service endpoint that will be invoked by the
-     * returned <code>Dispatch</code> object.
+     * returned {@code Dispatch} object.
      * @param context The JAXB context used to marshall and unmarshall
      * messages or message payloads.
      * @param mode Controls whether the created dispatch instance is message
@@ -508,23 +508,23 @@
      * protocol messages or message payloads. E.g. when using the SOAP
      * protocol, this parameter controls whether the user will work with
      * SOAP messages or the contents of a SOAP body.
-     * @param features  An array of <code>WebServiceFeatures</code> to configure on the
-     *                proxy.  Supported features not in the <code>features
-     *                </code> parameter will have their default values.
+     * @param features  An array of {@code WebServiceFeatures} to configure on the
+     *                proxy.  Supported features not in the {@code features
+     *                } parameter will have their default values.
      *
      * @return Dispatch instance
      * @throws WebServiceException
      *                  <UL>
      *                    <li>If there is any missing WSDL metadata
      *                      as required by this method.
-     *                    <li>If the <code>endpointReference</code> metadata does
-     *                    not match the <code>serviceName</code> or <code>portName</code>
+     *                    <li>If the {@code endpointReference} metadata does
+     *                    not match the {@code serviceName} or {@code portName}
      *                    of a WSDL associated
-     *                    with this <code>Service</code> instance.
-     *                    <li>If the <code>portName</code> cannot be determined
-     *                    from the <code>EndpointReference</code> metadata.
+     *                    with this {@code Service} instance.
+     *                    <li>If the {@code portName} cannot be determined
+     *                    from the {@code EndpointReference} metadata.
      *                    <li>If any error in the creation of
-     *                    the <code>Dispatch</code> object.
+     *                    the {@code Dispatch} object.
      *                    <li>if a feature is enabled that is not
      *                    compatible with this port or is unsupported.
      *                  </UL>
@@ -546,12 +546,12 @@
     public abstract QName getServiceName();
 
     /**
-     * Returns an <code>Iterator</code> for the list of
-     * <code>QName</code>s of service endpoints grouped by this
+     * Returns an {@code Iterator} for the list of
+     * {@code QName}s of service endpoints grouped by this
      * service
      *
-     * @return Returns <code>java.util.Iterator</code> with elements
-     *         of type <code>javax.xml.namespace.QName</code>
+     * @return Returns {@code java.util.Iterator} with elements
+     *         of type {@code javax.xml.namespace.QName}
      * @throws WebServiceException If this Service class does not
      *         have access to the required WSDL metadata
      **/
@@ -568,21 +568,21 @@
     /**
      * Returns the configured handler resolver.
      *
-     * @return HandlerResolver The <code>HandlerResolver</code> being
-     *         used by this <code>Service</code> instance, or <code>null</code>
+     * @return HandlerResolver The {@code HandlerResolver} being
+     *         used by this {@code Service} instance, or {@code null}
      *         if there isn't one.
      **/
     public abstract HandlerResolver getHandlerResolver();
 
     /**
-     * Sets the <code>HandlerResolver</code> for this <code>Service</code>
+     * Sets the {@code HandlerResolver} for this {@code Service}
      * instance.
      * <p>
      * The handler resolver, if present, will be called once for each
      * proxy or dispatch instance that is created, and the handler chain
      * returned by the resolver will be set on the instance.
      *
-     * @param handlerResolver The <code>HandlerResolver</code> to use
+     * @param handlerResolver The {@code HandlerResolver} to use
      *        for all subsequently created proxy/dispatch objects.
      *
      * @see javax.xml.ws.handler.HandlerResolver
@@ -590,12 +590,12 @@
     public abstract void setHandlerResolver(HandlerResolver handlerResolver);
 
     /**
-     * Returns the executor for this <code>Service</code>instance.
+     * Returns the executor for this {@code Service}instance.
      *
      * The executor is used for all asynchronous invocations that
      * require callbacks.
      *
-     * @return The <code>java.util.concurrent.Executor</code> to be
+     * @return The {@code java.util.concurrent.Executor} to be
      *         used to invoke a callback.
      *
      * @see java.util.concurrent.Executor
@@ -603,12 +603,12 @@
     public abstract java.util.concurrent.Executor getExecutor();
 
     /**
-     * Sets the executor for this <code>Service</code> instance.
+     * Sets the executor for this {@code Service} instance.
      *
      * The executor is used for all asynchronous invocations that
      * require callbacks.
      *
-     * @param executor The <code>java.util.concurrent.Executor</code>
+     * @param executor The {@code java.util.concurrent.Executor}
      *        to be used to invoke a callback.
      *
      * @throws SecurityException If the instance does not support
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/spi/http/HttpExchange.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/spi/http/HttpExchange.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -41,7 +41,7 @@
  * for examining the request from the client, and for building and
  * sending the response.
  * <p>
- * A <code>HttpExchange</code> must be closed to free or reuse
+ * A {@code HttpExchange} must be closed to free or reuse
  * underlying resources. The effect of failing to close an exchange
  * is undefined.
  *
@@ -277,7 +277,7 @@
 
     /**
      * Returns an attribute that is associated with this
-     * <code>HttpExchange</code>. JAX-WS handlers and endpoints may then
+     * {@code HttpExchange}. JAX-WS handlers and endpoints may then
      * access the attribute via {@link MessageContext}.
      * <p>
      * Servlet containers must expose {@link MessageContext#SERVLET_CONTEXT},
@@ -299,7 +299,7 @@
 
     /**
      * Gives all the attribute names that are associated with
-     * this <code>HttpExchange</code>.
+     * this {@code HttpExchange}.
      *
      * @return set of all attribute names
      * @see #getAttribute(String)
@@ -308,7 +308,7 @@
 
     /**
      * Returns the {@link Principal} that represents the authenticated
-     * user for this <code>HttpExchange</code>.
+     * user for this {@code HttpExchange}.
      *
      * @return Principal for an authenticated user, or
      *         <tt>null</tt> if not authenticated
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/wsaddressing/W3CEndpointReference.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/wsaddressing/W3CEndpointReference.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -90,7 +90,7 @@
      *   If the source does NOT contain a valid W3C WS-Addressing
      *   EndpointReference.
      * @throws NullPointerException
-     *   If the <code>null</code> <code>source</code> value is given
+     *   If the {@code null} {@code source} value is given
      */
     public W3CEndpointReference(Source source) {
         try {
--- a/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/wsaddressing/W3CEndpointReferenceBuilder.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jaxws/src/java.xml.ws/share/classes/javax/xml/ws/wsaddressing/W3CEndpointReferenceBuilder.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -38,35 +38,35 @@
 
 
 /**
- * This class is used to build <code>W3CEndpointReference</code>
+ * This class is used to build {@code W3CEndpointReference}
  * instances. The intended use of this clsss is for
  * an application component, for example a factory component,
- * to create an <code>W3CEndpointReference</code> for a
+ * to create an {@code W3CEndpointReference} for a
  * web service endpoint published by the same
  * Java EE application. It can also be used to create
- * <code>W3CEndpointReferences</code> for an Java SE based
- * endpoint by providing the <code>address</code> property.
+ * {@code W3CEndpointReferences} for an Java SE based
+ * endpoint by providing the {@code address} property.
  * <p>
- * When creating a <code>W3CEndpointReference</code> for an
+ * When creating a {@code W3CEndpointReference} for an
  * endpoint that is not published by the same Java EE application,
- * the <code>address</code> property MUST be specified.
+ * the {@code address} property MUST be specified.
  * <p>
- * When creating a <code>W3CEndpointReference</code> for an endpoint
- * published by the same Java EE application, the <code>address</code>
- * property MAY be <code>null</code> but then the <code>serviceName</code>
- * and <code>endpointName</code> MUST specify an endpoint published by
+ * When creating a {@code W3CEndpointReference} for an endpoint
+ * published by the same Java EE application, the {@code address}
+ * property MAY be {@code null} but then the {@code serviceName}
+ * and {@code endpointName} MUST specify an endpoint published by
  * the same Java EE application.
  * <p>
- * When the <code>wsdlDocumentLocation</code> is specified it MUST refer
- * to a valid WSDL document and the <code>serviceName</code> and
- * <code>endpointName</code> (if specified) MUST match a service and port
+ * When the {@code wsdlDocumentLocation} is specified it MUST refer
+ * to a valid WSDL document and the {@code serviceName} and
+ * {@code endpointName} (if specified) MUST match a service and port
  * in the WSDL document.
  *
  * @since 1.6, JAX-WS 2.1
  */
 public final class W3CEndpointReferenceBuilder {
     /**
-     * Creates a new <code>W3CEndpointReferenceBuilder</code> instance.
+     * Creates a new {@code W3CEndpointReferenceBuilder} instance.
      */
     public W3CEndpointReferenceBuilder() {
         referenceParameters = new ArrayList<Element>();
@@ -76,20 +76,20 @@
     }
 
     /**
-     * Sets the <code>address</code> to the
-     * <code>W3CEndpointReference</code> instance's
-     * <code>wsa:Address</code>.
+     * Sets the {@code address} to the
+     * {@code W3CEndpointReference} instance's
+     * {@code wsa:Address}.
      * <p>
-     * The <code>address</code> MUST be set to a non-<code>null</code>
-     * value when building a <code>W3CEndpointReference</code> for a
+     * The {@code address} MUST be set to a non-{@code null}
+     * value when building a {@code W3CEndpointReference} for a
      * web service endpoint that is not published by the same
      * Java EE application or when running on Java SE.
      *
      * @param address The address of the endpoint to be targeted
-     *      by the returned <code>W3CEndpointReference</code>.
+     *      by the returned {@code W3CEndpointReference}.
      *
-     * @return A <code>W3CEndpointReferenceBuilder</code> instance with
-     *   the <code>address</code> set to the <code>wsa:Address</code>.
+     * @return A {@code W3CEndpointReferenceBuilder} instance with
+     *   the {@code address} set to the {@code wsa:Address}.
      */
     public W3CEndpointReferenceBuilder address(String address) {
         this.address = address;
@@ -97,19 +97,19 @@
     }
 
     /**
-     * Sets the <code>interfaceName</code> as the
-     * <code>wsam:InterfaceName</code> element in the
-     * <code>wsa:Metadata</code> element.
+     * Sets the {@code interfaceName} as the
+     * {@code wsam:InterfaceName} element in the
+     * {@code wsa:Metadata} element.
      *
      * See <a href="http://www.w3.org/TR/2007/REC-ws-addr-metadata-20070904/#refmetadatfromepr">
      * 2.1 Referencing WSDL Metadata from an EPR</a> for more details.
      *
      * @param interfaceName The port type name of the endpoint to be targeted
-     *      by the returned <code>W3CEndpointReference</code>.
+     *      by the returned {@code W3CEndpointReference}.
      *
-     * @return A <code>W3CEndpointReferenceBuilder</code> instance with
-     *   the <code>interfaceName</code> as <code>wsam:InterfaceName</code>
-     *   element added to the <code>wsa:Metadata</code> element
+     * @return A {@code W3CEndpointReferenceBuilder} instance with
+     *   the {@code interfaceName} as {@code wsam:InterfaceName}
+     *   element added to the {@code wsa:Metadata} element
      * @since 1.7
      */
     public W3CEndpointReferenceBuilder interfaceName(QName interfaceName) {
@@ -118,22 +118,22 @@
     }
 
     /**
-     * Sets the <code>serviceName</code> as the
-     * <code>wsam:ServiceName</code> element in the
-     * <code>wsa:Metadata</code> element.
+     * Sets the {@code serviceName} as the
+     * {@code wsam:ServiceName} element in the
+     * {@code wsa:Metadata} element.
      *
      * See <a href="http://www.w3.org/TR/2007/REC-ws-addr-metadata-20070904/#refmetadatfromepr">
      * 2.1 Referencing WSDL Metadata from an EPR</a> for more details.
      *
      * @param serviceName The service name of the endpoint to be targeted
-     *      by the returned <code>W3CEndpointReference</code>.  This property
-     *      may also be used with the <code>endpointName</code> (portName)
-     *      property to lookup the <code>address</code> of a web service
+     *      by the returned {@code W3CEndpointReference}.  This property
+     *      may also be used with the {@code endpointName} (portName)
+     *      property to lookup the {@code address} of a web service
      *      endpoint that is published by the same Java EE application.
      *
-     * @return A <code>W3CEndpointReferenceBuilder</code> instance with
-     *   the <code>serviceName</code> as <code>wsam:ServiceName</code>
-     *   element added to the <code>wsa:Metadata</code> element
+     * @return A {@code W3CEndpointReferenceBuilder} instance with
+     *   the {@code serviceName} as {@code wsam:ServiceName}
+     *   element added to the {@code wsa:Metadata} element
      *
      */
     public W3CEndpointReferenceBuilder serviceName(QName serviceName) {
@@ -142,30 +142,31 @@
     }
 
     /**
-     * Sets the <code>endpointName</code> as
-     * <code>wsam:ServiceName/@EndpointName</code> in the
-     * <code>wsa:Metadata</code> element. This method can only be called
+     * Sets the {@code endpointName} as
+     * {@code wsam:ServiceName/@EndpointName} in the
+     * {@code wsa:Metadata} element. This method can only be called
      * after the {@link #serviceName} method has been called.
      * <p>
      * See <a href="http://www.w3.org/TR/2007/REC-ws-addr-metadata-20070904/#refmetadatfromepr">
      * 2.1 Referencing WSDL Metadata from an EPR</a> for more details.
      *
      * @param endpointName The name of the endpoint to be targeted
-     *      by the returned <code>W3CEndpointReference</code>. The
-     *      <code>endpointName</code> (portName) property may also be
-     *      used with the <code>serviceName</code> property to lookup
-     *      the <code>address</code> of a web service
+     *      by the returned {@code W3CEndpointReference}. The
+     *      {@code endpointName} (portName) property may also be
+     *      used with the {@code serviceName} property to lookup
+     *      the {@code address} of a web service
      *      endpoint published by the same Java EE application.
      *
-     * @return A <code>W3CEndpointReferenceBuilder</code> instance with
-     *   the <code>endpointName</code> as
-     * <code>wsam:ServiceName/@EndpointName</code> in the
-     * <code>wsa:Metadata</code> element.
+     * @return A {@code W3CEndpointReferenceBuilder} instance with
+     *   the {@code endpointName} as
+     *   {@code wsam:ServiceName/@EndpointName} in the
+     *   {@code wsa:Metadata} element.
      *
-     * @throws IllegalStateException, if the <code>serviceName</code>
-     * has not been set.
-     * @throws IllegalArgumentException, if the <code>endpointName</code>'s
-     * Namespace URI doesn't match <code>serviceName</code>'s Namespace URI
+     * @throws java.lang.IllegalStateException if the {@code serviceName}
+     *   has not been set
+     *
+     * @throws java.lang.IllegalArgumentException if the {@code endpointName}'s
+     *   Namespace URI doesn't match {@code serviceName}'s Namespace URI
      *
      */
     public W3CEndpointReferenceBuilder endpointName(QName endpointName) {
@@ -178,8 +179,8 @@
     }
 
     /**
-     * Sets the <code>wsdlDocumentLocation</code> that will be referenced
-     * as <code>wsa:Metadata/@wsdli:wsdlLocation</code>. The namespace name
+     * Sets the {@code wsdlDocumentLocation} that will be referenced
+     * as {@code wsa:Metadata/@wsdli:wsdlLocation}. The namespace name
      * for the wsdli:wsdlLocation's value can be taken from the WSDL itself.
      *
      * <p>
@@ -187,10 +188,10 @@
      * 2.1 Referencing WSDL Metadata from an EPR</a> for more details.
      *
      * @param wsdlDocumentLocation The location of the WSDL document to
-     *      be referenced in the <code>wsa:Metadata</code> of the
-     *     <code>W3CEndpointReference</code>.
-     * @return A <code>W3CEndpointReferenceBuilder</code> instance with
-     *   the <code>wsdlDocumentLocation</code> that is to be referenced.
+     *      be referenced in the {@code wsa:Metadata} of the
+     *     {@code W3CEndpointReference}.
+     * @return A {@code W3CEndpointReferenceBuilder} instance with
+     *   the {@code wsdlDocumentLocation} that is to be referenced.
      */
     public W3CEndpointReferenceBuilder wsdlDocumentLocation(String wsdlDocumentLocation) {
         this.wsdlDocumentLocation = wsdlDocumentLocation;
@@ -198,19 +199,19 @@
     }
 
     /**
-     * Adds the <code>referenceParameter</code> to the
-     * <code>W3CEndpointReference</code> instance
-     * <code>wsa:ReferenceParameters</code> element.
+     * Adds the {@code referenceParameter} to the
+     * {@code W3CEndpointReference} instance
+     * {@code wsa:ReferenceParameters} element.
      *
      * @param referenceParameter The element to be added to the
-     *      <code>wsa:ReferenceParameters</code> element.
+     *      {@code wsa:ReferenceParameters} element.
      *
-     * @return A <code>W3CEndpointReferenceBuilder</code> instance with
-     *   the <code>referenceParameter</code> added to the
-     *   <code>wsa:ReferenceParameters</code> element.
+     * @return A {@code W3CEndpointReferenceBuilder} instance with
+     *   the {@code referenceParameter} added to the
+     *   {@code wsa:ReferenceParameters} element.
      *
-     * @throws java.lang.IllegalArgumentException if <code>referenceParameter</code>
-     * is <code>null</code>.
+     * @throws java.lang.IllegalArgumentException if {@code referenceParameter}
+     * is {@code null}.
      */
     public W3CEndpointReferenceBuilder referenceParameter(Element referenceParameter) {
         if (referenceParameter == null)
@@ -220,19 +221,19 @@
     }
 
     /**
-     * Adds the <code>metadataElement</code> to the
-     * <code>W3CEndpointReference</code> instance's
-     * <code>wsa:Metadata</code> element.
+     * Adds the {@code metadataElement} to the
+     * {@code W3CEndpointReference} instance's
+     * {@code wsa:Metadata} element.
      *
      * @param metadataElement The element to be added to the
-     *      <code>wsa:Metadata</code> element.
+     *      {@code wsa:Metadata} element.
      *
-     * @return A <code>W3CEndpointReferenceBuilder</code> instance with
-     *   the <code>metadataElement</code> added to the
-     *    <code>wsa:Metadata</code> element.
+     * @return A {@code W3CEndpointReferenceBuilder} instance with
+     *   the {@code metadataElement} added to the
+     *    {@code wsa:Metadata} element.
      *
-     * @throws java.lang.IllegalArgumentException if <code>metadataElement</code>
-     * is <code>null</code>.
+     * @throws java.lang.IllegalArgumentException if {@code metadataElement}
+     * is {@code null}.
      */
     public W3CEndpointReferenceBuilder metadata(Element metadataElement) {
         if (metadataElement == null)
@@ -243,16 +244,16 @@
 
     /**
      * Adds an extension element to the
-     * <code>W3CEndpointReference</code> instance's
-     * <code>wsa:EndpointReference</code> element.
+     * {@code W3CEndpointReference} instance's
+     * {@code wsa:EndpointReference} element.
      *
      * @param element The extension element to be added to the
-     *   <code>W3CEndpointReference</code>
-     * @return A <code>W3CEndpointReferenceBuilder</code> instance with
-     *   the extension <code>element</code> added to the
-     *    <code>W3CEndpointReference</code> instance.
-     * @throws java.lang.IllegalArgumentException if <code>element</code>
-     * is <code>null</code>.
+     *   {@code W3CEndpointReference}
+     * @return A {@code W3CEndpointReferenceBuilder} instance with
+     *   the extension {@code element} added to the
+     *    {@code W3CEndpointReference} instance.
+     * @throws java.lang.IllegalArgumentException if {@code element}
+     * is {@code null}.
      *
      * @since 1.7, JAX-WS 2.2
      */
@@ -266,17 +267,17 @@
 
     /**
      * Adds an extension attribute to the
-     * <code>W3CEndpointReference</code> instance's
-     * <code>wsa:EndpointReference</code> element.
+     * {@code W3CEndpointReference} instance's
+     * {@code wsa:EndpointReference} element.
      *
      * @param name The name of the extension attribute to be added to the
-     *   <code>W3CEndpointReference</code>
+     *   {@code W3CEndpointReference}
      * @param value extension attribute value
-     * @return A <code>W3CEndpointReferenceBuilder</code> instance with
-     *   the extension attribute added to the <code>W3CEndpointReference</code>
+     * @return A {@code W3CEndpointReferenceBuilder} instance with
+     *   the extension attribute added to the {@code W3CEndpointReference}
      *   instance.
-     * @throws java.lang.IllegalArgumentException if <code>name</code>
-     *   or <code>value</code> is <code>null</code>.
+     * @throws java.lang.IllegalArgumentException if {@code name}
+     *   or {@code value} is {@code null}.
      *
      * @since 1.7, JAX-WS 2.2
      */
@@ -289,48 +290,48 @@
     }
 
     /**
-     * Builds a <code>W3CEndpointReference</code> from the accumulated
-     * properties set on this <code>W3CEndpointReferenceBuilder</code>
+     * Builds a {@code W3CEndpointReference} from the accumulated
+     * properties set on this {@code W3CEndpointReferenceBuilder}
      * instance.
      * <p>
-     * This method can be used to create a <code>W3CEndpointReference</code>
-     * for any endpoint by specifying the <code>address</code> property along
+     * This method can be used to create a {@code W3CEndpointReference}
+     * for any endpoint by specifying the {@code address} property along
      * with any other desired properties.  This method
-     * can also be used to create a <code>W3CEndpointReference</code> for
+     * can also be used to create a {@code W3CEndpointReference} for
      * an endpoint that is published by the same Java EE application.
-     * This method can automatically determine the <code>address</code> of
+     * This method can automatically determine the {@code address} of
      * an endpoint published by the same Java EE application that is identified by the
-     * <code>serviceName</code> and
-     * <code>endpointName</code> properties.  If the <code>address</code> is
-     * <code>null</code> and the <code>serviceName</code> and
-     * <code>endpointName</code>
+     * {@code serviceName} and
+     * {@code endpointName} properties.  If the {@code address} is
+     * {@code null} and the {@code serviceName} and
+     * {@code endpointName}
      * do not identify an endpoint published by the same Java EE application, a
-     * <code>java.lang.IllegalStateException</code> MUST be thrown.
+     * {@code java.lang.IllegalStateException} MUST be thrown.
      *
      *
-     * @return <code>W3CEndpointReference</code> from the accumulated
-     * properties set on this <code>W3CEndpointReferenceBuilder</code>
-     * instance. This method never returns <code>null</code>.
+     * @return {@code W3CEndpointReference} from the accumulated
+     * properties set on this {@code W3CEndpointReferenceBuilder}
+     * instance. This method never returns {@code null}.
      *
      * @throws IllegalStateException
      *     <ul>
-     *        <li>If the <code>address</code>, <code>serviceName</code> and
-     *            <code>endpointName</code> are all <code>null</code>.
-     *        <li>If the <code>serviceName</code> service is <code>null</code> and the
-     *            <code>endpointName</code> is NOT <code>null</code>.
-     *        <li>If the <code>address</code> property is <code>null</code> and
-     *            the <code>serviceName</code> and <code>endpointName</code> do not
+     *        <li>If the {@code address}, {@code serviceName} and
+     *            {@code endpointName} are all {@code null}.
+     *        <li>If the {@code serviceName} service is {@code null} and the
+     *            {@code endpointName} is NOT {@code null}.
+     *        <li>If the {@code address} property is {@code null} and
+     *            the {@code serviceName} and {@code endpointName} do not
      *            specify a valid endpoint published by the same Java EE
      *            application.
-     *        <li>If the <code>serviceName</code> is NOT <code>null</code>
+     *        <li>If the {@code serviceName} is NOT {@code null}
      *             and is not present in the specified WSDL.
-     *        <li>If the <code>endpointName</code> port is not <code>null</code> and it
-     *             is not present in <code>serviceName</code> service in the WSDL.
-     *        <li>If the <code>wsdlDocumentLocation</code> is NOT <code>null</code>
+     *        <li>If the {@code endpointName} port is not {@code null} and it
+     *             is not present in {@code serviceName} service in the WSDL.
+     *        <li>If the {@code wsdlDocumentLocation} is NOT {@code null}
      *            and does not represent a valid WSDL.
      *     </ul>
      * @throws WebServiceException If an error occurs while creating the
-     *                             <code>W3CEndpointReference</code>.
+     *                             {@code W3CEndpointReference}.
      *
      */
     public W3CEndpointReference build() {
--- a/jdk/.hgtags	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/.hgtags	Wed Jul 05 20:42:36 2017 +0200
@@ -315,3 +315,4 @@
 a7f731125b7fb0e4b0186172f85a21e2d5139f7e jdk9-b70
 e47d3bfbc61accc3fbd372a674fdce2933b54f31 jdk9-b71
 f376824d4940f45719d91838f3f6249f873440db jdk9-b72
+1c8bca2ebba13948199de33a1b71e2d6f1c7a8a6 jdk9-b73
--- a/jdk/make/Tools.gmk	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/make/Tools.gmk	Wed Jul 05 20:42:36 2017 +0200
@@ -144,7 +144,6 @@
     SETUP := GENERATE_OLDBYTECODE, \
     SRC := $(JDK_TOPDIR)/src/java.base/share/classes, \
     INCLUDES := $(JIMAGE_PKGS), \
-    EXCLUDES := jdk/internal/jimage/concurrent, \
     BIN := $(BUILDTOOLS_OUTPUTDIR)/interim_jimage_classes))
 
 # Because of the explicit INCLUDES in the compilation setup above, the service provider
--- a/jdk/make/data/characterdata/CharacterData00.java.template	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/make/data/characterdata/CharacterData00.java.template	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 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
@@ -226,6 +226,11 @@
             case 0xA77D : mapChar = 0x1D79; break;
             case 0xA78D : mapChar = 0x0265; break;
             case 0xA7AA : mapChar = 0x0266; break;
+            case 0xA7AB : mapChar = 0x025C; break;
+            case 0xA7AC : mapChar = 0x0261; break;
+            case 0xA7AD : mapChar = 0x026C; break;
+            case 0xA7B0 : mapChar = 0x029E; break;
+            case 0xA7B1 : mapChar = 0x0287; break;
               // default mapChar is already set, so no
               // need to redo it here.
               // default       : mapChar = ch;
@@ -284,10 +289,15 @@
             case 0x0250 : mapChar = 0x2C6F; break;
             case 0x0251 : mapChar = 0x2C6D; break;
             case 0x0252 : mapChar = 0x2C70; break;
+            case 0x025C : mapChar = 0xA7AB; break;
+            case 0x0261 : mapChar = 0xA7AC; break;
             case 0x0265 : mapChar = 0xA78D; break;
             case 0x0266 : mapChar = 0xA7AA; break;
             case 0x026B : mapChar = 0x2C62; break;
+            case 0x026C : mapChar = 0xA7AD; break;
             case 0x0271 : mapChar = 0x2C6E; break;
+            case 0x0287 : mapChar = 0xA7B1; break;
+            case 0x029E : mapChar = 0xA7B0; break;
             case 0x027D : mapChar = 0x2C64; break;
             case 0x1D79 : mapChar = 0xA77D; break;
             case 0x1D7D : mapChar = 0x2C63; break;
@@ -503,6 +513,22 @@
                     // This is the only char with RLO
                     directionality = Character.DIRECTIONALITY_RIGHT_TO_LEFT_OVERRIDE;
                     break;
+                case 0x2066 :
+                    // This is the only char with LRI
+                    directionality = Character.DIRECTIONALITY_LEFT_TO_RIGHT_ISOLATE;
+                    break;
+                case 0x2067 :
+                    // This is the only char with RLI
+                    directionality = Character.DIRECTIONALITY_RIGHT_TO_LEFT_ISOLATE;
+                    break;
+                case 0x2068 :
+                    // This is the only char with FSI
+                    directionality = Character.DIRECTIONALITY_FIRST_STRONG_ISOLATE;
+                    break;
+                case 0x2069 :
+                    // This is the only char with PDI
+                    directionality = Character.DIRECTIONALITY_POP_DIRECTIONAL_ISOLATE;
+                    break;
                 default :
                     directionality = Character.DIRECTIONALITY_UNDEFINED;
                     break;
@@ -537,11 +563,16 @@
                     case 0x0250 : mapChar = 0x2C6F; break;
                     case 0x0251 : mapChar = 0x2C6D; break;
                     case 0x0252 : mapChar = 0x2C70; break;
+                    case 0x025C : mapChar = 0xA7AB; break;
+                    case 0x0261 : mapChar = 0xA7AC; break;
                     case 0x0265 : mapChar = 0xA78D; break;
                     case 0x0266 : mapChar = 0xA7AA; break;
                     case 0x026B : mapChar = 0x2C62; break;
+                    case 0x026C : mapChar = 0xA7AD; break;
                     case 0x0271 : mapChar = 0x2C6E; break;
                     case 0x027D : mapChar = 0x2C64; break;
+                    case 0x0287 : mapChar = 0xA7B1; break;
+                    case 0x029E : mapChar = 0xA7B0; break;
                     case 0x1D79 : mapChar = 0xA77D; break;
                     case 0x1D7D : mapChar = 0x2C63; break;
                     case 0x2C65 : mapChar = 0x023A; break;
--- a/jdk/make/data/characterdata/CharacterData01.java.template	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/make/data/characterdata/CharacterData01.java.template	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 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
@@ -244,81 +244,118 @@
             case 0x10132: retval = 80000; break;   // AEGEAN NUMBER EIGHTY THOUSAND
             case 0x10133: retval = 90000; break;   // AEGEAN NUMBER NINETY THOUSAND
             case 0x10323: retval = 50; break;      // OLD ITALIC NUMERAL FIFTY
-
-            case 0x010144: retval = 50; break;     // ACROPHONIC ATTIC FIFTY
-            case 0x010145: retval = 500; break;    // ACROPHONIC ATTIC FIVE HUNDRED
-            case 0x010146: retval = 5000; break;   // ACROPHONIC ATTIC FIVE THOUSAND
-            case 0x010147: retval = 50000; break;  // ACROPHONIC ATTIC FIFTY THOUSAND
-            case 0x01014A: retval = 50; break;     // ACROPHONIC ATTIC FIFTY TALENTS
-            case 0x01014B: retval = 100; break;    // ACROPHONIC ATTIC ONE HUNDRED TALENTS
-            case 0x01014C: retval = 500; break;    // ACROPHONIC ATTIC FIVE HUNDRED TALENTS
-            case 0x01014D: retval = 1000; break;   // ACROPHONIC ATTIC ONE THOUSAND TALENTS
-            case 0x01014E: retval = 5000; break;   // ACROPHONIC ATTIC FIVE THOUSAND TALENTS
-            case 0x010151: retval = 50; break;     // ACROPHONIC ATTIC FIFTY STATERS
-            case 0x010152: retval = 100; break;    // ACROPHONIC ATTIC ONE HUNDRED STATERS
-            case 0x010153: retval = 500; break;    // ACROPHONIC ATTIC FIVE HUNDRED STATERS
-            case 0x010154: retval = 1000; break;   // ACROPHONIC ATTIC ONE THOUSAND STATERS
-            case 0x010155: retval = 10000; break;  // ACROPHONIC ATTIC TEN THOUSAND STATERS
-            case 0x010156: retval = 50000; break;  // ACROPHONIC ATTIC FIFTY THOUSAND STATERS
-            case 0x010166: retval = 50; break;     // ACROPHONIC TROEZENIAN FIFTY
-            case 0x010167: retval = 50; break;     // ACROPHONIC TROEZENIAN FIFTY ALTERNATE FORM
-            case 0x010168: retval = 50; break;     // ACROPHONIC HERMIONIAN FIFTY
-            case 0x010169: retval = 50; break;     // ACROPHONIC THESPIAN FIFTY
-            case 0x01016A: retval = 100; break;    // ACROPHONIC THESPIAN ONE HUNDRED
-            case 0x01016B: retval = 300; break;    // ACROPHONIC THESPIAN THREE HUNDRED
-            case 0x01016C: retval = 500; break;    // ACROPHONIC EPIDAUREAN FIVE HUNDRED
-            case 0x01016D: retval = 500; break;    // ACROPHONIC TROEZENIAN FIVE HUNDRED
-            case 0x01016E: retval = 500; break;    // ACROPHONIC THESPIAN FIVE HUNDRED
-            case 0x01016F: retval = 500; break;    // ACROPHONIC CARYSTIAN FIVE HUNDRED
-            case 0x010170: retval = 500; break;    // ACROPHONIC NAXIAN FIVE HUNDRED
-            case 0x010171: retval = 1000; break;   // ACROPHONIC THESPIAN ONE THOUSAND
-            case 0x010172: retval = 5000; break;   // ACROPHONIC THESPIAN FIVE THOUSAND
-            case 0x010174: retval = 50; break;     // ACROPHONIC STRATIAN FIFTY MNAS
-            case 0x010341: retval = 90; break;     // GOTHIC LETTER NINETY
-            case 0x01034A: retval = 900; break;    // GOTHIC LETTER NINE HUNDRED
-            case 0x0103D5: retval = 100; break;    // OLD PERSIAN NUMBER HUNDRED
-            case 0x01085D: retval = 100; break;    // IMPERIAL ARAMAIC NUMBER ONE HUNDRED
-            case 0x01085E: retval = 1000; break;   // IMPERIAL ARAMAIC NUMBER ONE THOUSAND
-            case 0x01085F: retval = 10000; break;  // IMPERIAL ARAMAIC NUMBER TEN THOUSAND
-            case 0x010919: retval = 100; break;    // PHOENICIAN NUMBER ONE HUNDRED
-            case 0x010A46: retval = 100; break;    // KHAROSHTHI NUMBER ONE HUNDRED
-            case 0x010A47: retval = 1000; break;   // KHAROSHTHI NUMBER ONE THOUSAND
-            case 0x010A7E: retval = 50; break;     // OLD SOUTH ARABIAN NUMBER FIFTY
-            case 0x010B5E: retval = 100; break;    // INSCRIPTIONAL PARTHIAN NUMBER ONE HUNDRED
-            case 0x010B5F: retval = 1000; break;   // INSCRIPTIONAL PARTHIAN NUMBER ONE THOUSAND
-            case 0x010B7E: retval = 100; break;    // INSCRIPTIONAL PAHLAVI NUMBER ONE HUNDRED
-            case 0x010B7F: retval = 1000; break;   // INSCRIPTIONAL PAHLAVI NUMBER ONE THOUSAND
-            case 0x010E6C: retval = 40; break;     // RUMI NUMBER FORTY
-            case 0x010E6D: retval = 50; break;     // RUMI NUMBER FIFTY
-            case 0x010E6E: retval = 60; break;     // RUMI NUMBER SIXTY
-            case 0x010E6F: retval = 70; break;     // RUMI NUMBER SEVENTY
-            case 0x010E70: retval = 80; break;     // RUMI NUMBER EIGHTY
-            case 0x010E71: retval = 90; break;     // RUMI NUMBER NINETY
-            case 0x010E72: retval = 100; break;    // RUMI NUMBER ONE HUNDRED
-            case 0x010E73: retval = 200; break;    // RUMI NUMBER TWO HUNDRED
-            case 0x010E74: retval = 300; break;    // RUMI NUMBER THREE HUNDRED
-            case 0x010E75: retval = 400; break;    // RUMI NUMBER FOUR HUNDRED
-            case 0x010E76: retval = 500; break;    // RUMI NUMBER FIVE HUNDRED
-            case 0x010E77: retval = 600; break;    // RUMI NUMBER SIX HUNDRED
-            case 0x010E78: retval = 700; break;    // RUMI NUMBER SEVEN HUNDRED
-            case 0x010E79: retval = 800; break;    // RUMI NUMBER EIGHT HUNDRED
-            case 0x010E7A: retval = 900; break;    // RUMI NUMBER NINE HUNDRED
-            case 0x01105E: retval = 40; break;     // BRAHMI NUMBER FORTY
-            case 0x01105F: retval = 50; break;     // BRAHMI NUMBER FIFTY
-            case 0x011060: retval = 60; break;     // BRAHMI NUMBER SIXTY
-            case 0x011061: retval = 70; break;     // BRAHMI NUMBER SEVENTY
-            case 0x011062: retval = 80; break;     // BRAHMI NUMBER EIGHTY
-            case 0x011063: retval = 90; break;     // BRAHMI NUMBER NINETY
-            case 0x011064: retval = 100; break;    // BRAHMI NUMBER ONE HUNDRED
-            case 0x011065: retval = 1000; break;   // BRAHMI NUMBER ONE THOUSAND
-            case 0x012432: retval = 216000; break;   // CUNEIFORM NUMERIC SIGN SHAR2 TIMES GAL PLUS DISH
-            case 0x012433: retval = 432000; break;   // CUNEIFORM NUMERIC SIGN SHAR2 TIMES GAL PLUS MIN
-            case 0x01D36C: retval = 40; break;     // COUNTING ROD TENS DIGIT FOUR
-            case 0x01D36D: retval = 50; break;     // COUNTING ROD TENS DIGIT FIVE
-            case 0x01D36E: retval = 60; break;     // COUNTING ROD TENS DIGIT SIX
-            case 0x01D36F: retval = 70; break;     // COUNTING ROD TENS DIGIT SEVEN
-            case 0x01D370: retval = 80; break;     // COUNTING ROD TENS DIGIT EIGHT
-            case 0x01D371: retval = 90; break;     // COUNTING ROD TENS DIGIT NINE
+            case 0x10144: retval = 50; break;      // ACROPHONIC ATTIC FIFTY
+            case 0x10145: retval = 500; break;     // ACROPHONIC ATTIC FIVE HUNDRED
+            case 0x10146: retval = 5000; break;    // ACROPHONIC ATTIC FIVE THOUSAND
+            case 0x10147: retval = 50000; break;   // ACROPHONIC ATTIC FIFTY THOUSAND
+            case 0x1014A: retval = 50; break;      // ACROPHONIC ATTIC FIFTY TALENTS
+            case 0x1014B: retval = 100; break;     // ACROPHONIC ATTIC ONE HUNDRED TALENTS
+            case 0x1014C: retval = 500; break;     // ACROPHONIC ATTIC FIVE HUNDRED TALENTS
+            case 0x1014D: retval = 1000; break;    // ACROPHONIC ATTIC ONE THOUSAND TALENTS
+            case 0x1014E: retval = 5000; break;    // ACROPHONIC ATTIC FIVE THOUSAND TALENTS
+            case 0x10151: retval = 50; break;      // ACROPHONIC ATTIC FIFTY STATERS
+            case 0x10152: retval = 100; break;     // ACROPHONIC ATTIC ONE HUNDRED STATERS
+            case 0x10153: retval = 500; break;     // ACROPHONIC ATTIC FIVE HUNDRED STATERS
+            case 0x10154: retval = 1000; break;    // ACROPHONIC ATTIC ONE THOUSAND STATERS
+            case 0x10155: retval = 10000; break;   // ACROPHONIC ATTIC TEN THOUSAND STATERS
+            case 0x10156: retval = 50000; break;   // ACROPHONIC ATTIC FIFTY THOUSAND STATERS
+            case 0x10166: retval = 50; break;      // ACROPHONIC TROEZENIAN FIFTY
+            case 0x10167: retval = 50; break;      // ACROPHONIC TROEZENIAN FIFTY ALTERNATE FORM
+            case 0x10168: retval = 50; break;      // ACROPHONIC HERMIONIAN FIFTY
+            case 0x10169: retval = 50; break;      // ACROPHONIC THESPIAN FIFTY
+            case 0x1016A: retval = 100; break;     // ACROPHONIC THESPIAN ONE HUNDRED
+            case 0x1016B: retval = 300; break;     // ACROPHONIC THESPIAN THREE HUNDRED
+            case 0x1016C: retval = 500; break;     // ACROPHONIC EPIDAUREAN FIVE HUNDRED
+            case 0x1016D: retval = 500; break;     // ACROPHONIC TROEZENIAN FIVE HUNDRED
+            case 0x1016E: retval = 500; break;     // ACROPHONIC THESPIAN FIVE HUNDRED
+            case 0x1016F: retval = 500; break;     // ACROPHONIC CARYSTIAN FIVE HUNDRED
+            case 0x10170: retval = 500; break;     // ACROPHONIC NAXIAN FIVE HUNDRED
+            case 0x10171: retval = 1000; break;    // ACROPHONIC THESPIAN ONE THOUSAND
+            case 0x10172: retval = 5000; break;    // ACROPHONIC THESPIAN FIVE THOUSAND
+            case 0x10174: retval = 50; break;      // ACROPHONIC STRATIAN FIFTY MNAS
+            case 0x102ED: retval = 40; break;      // COPTIC EPACT NUMBER FORTY
+            case 0x102EE: retval = 50; break;      // COPTIC EPACT NUMBER FIFTY
+            case 0x102EF: retval = 60; break;      // COPTIC EPACT NUMBER SIXTY
+            case 0x102F0: retval = 70; break;      // COPTIC EPACT NUMBER SEVENTY
+            case 0x102F1: retval = 80; break;      // COPTIC EPACT NUMBER EIGHTY
+            case 0x102F2: retval = 90; break;      // COPTIC EPACT NUMBER NINETY
+            case 0x102F3: retval = 100; break;     // COPTIC EPACT NUMBER ONE HUNDRED
+            case 0x102F4: retval = 200; break;     // COPTIC EPACT NUMBER TWO HUNDRED
+            case 0x102F5: retval = 300; break;     // COPTIC EPACT NUMBER THREE HUNDRED
+            case 0x102F6: retval = 400; break;     // COPTIC EPACT NUMBER FOUR HUNDRED
+            case 0x102F7: retval = 500; break;     // COPTIC EPACT NUMBER FIVE HUNDRED
+            case 0x102F8: retval = 600; break;     // COPTIC EPACT NUMBER SIX HUNDRED
+            case 0x102F9: retval = 700; break;     // COPTIC EPACT NUMBER SEVEN HUNDRED
+            case 0x102FA: retval = 800; break;     // COPTIC EPACT NUMBER EIGHT HUNDRED
+            case 0x102FB: retval = 900; break;     // COPTIC EPACT NUMBER NINE HUNDRED
+            case 0x10341: retval = 90; break;      // GOTHIC LETTER NINETY
+            case 0x1034A: retval = 900; break;     // GOTHIC LETTER NINE HUNDRED
+            case 0x103D5: retval = 100; break;     // OLD PERSIAN NUMBER HUNDRED
+            case 0x1085D: retval = 100; break;     // IMPERIAL ARAMAIC NUMBER ONE HUNDRED
+            case 0x1085E: retval = 1000; break;    // IMPERIAL ARAMAIC NUMBER ONE THOUSAND
+            case 0x1085F: retval = 10000; break;   // IMPERIAL ARAMAIC NUMBER TEN THOUSAND
+            case 0x108AF: retval = 100; break;     // NABATAEAN NUMBER ONE HUNDRED
+            case 0x10919: retval = 100; break;     // PHOENICIAN NUMBER ONE HUNDRED
+            case 0x10A46: retval = 100; break;     // KHAROSHTHI NUMBER ONE HUNDRED
+            case 0x10A47: retval = 1000; break;    // KHAROSHTHI NUMBER ONE THOUSAND
+            case 0x10A7E: retval = 50; break;      // OLD SOUTH ARABIAN NUMBER FIFTY
+            case 0x10AEF: retval = 100; break;     // MANICHAEAN NUMBER ONE HUNDRED
+            case 0x10B5E: retval = 100; break;     // INSCRIPTIONAL PARTHIAN NUMBER ONE HUNDRED
+            case 0x10B5F: retval = 1000; break;    // INSCRIPTIONAL PARTHIAN NUMBER ONE THOUSAND
+            case 0x10B7E: retval = 100; break;     // INSCRIPTIONAL PAHLAVI NUMBER ONE HUNDRED
+            case 0x10B7F: retval = 1000; break;    // INSCRIPTIONAL PAHLAVI NUMBER ONE THOUSAND
+            case 0x10BAF: retval = 100; break;     // PSALTER PAHLAVI NUMBER ONE HUNDRED
+            case 0x10E6C: retval = 40; break;      // RUMI NUMBER FORTY
+            case 0x10E6D: retval = 50; break;      // RUMI NUMBER FIFTY
+            case 0x10E6E: retval = 60; break;      // RUMI NUMBER SIXTY
+            case 0x10E6F: retval = 70; break;      // RUMI NUMBER SEVENTY
+            case 0x10E70: retval = 80; break;      // RUMI NUMBER EIGHTY
+            case 0x10E71: retval = 90; break;      // RUMI NUMBER NINETY
+            case 0x10E72: retval = 100; break;     // RUMI NUMBER ONE HUNDRED
+            case 0x10E73: retval = 200; break;     // RUMI NUMBER TWO HUNDRED
+            case 0x10E74: retval = 300; break;     // RUMI NUMBER THREE HUNDRED
+            case 0x10E75: retval = 400; break;     // RUMI NUMBER FOUR HUNDRED
+            case 0x10E76: retval = 500; break;     // RUMI NUMBER FIVE HUNDRED
+            case 0x10E77: retval = 600; break;     // RUMI NUMBER SIX HUNDRED
+            case 0x10E78: retval = 700; break;     // RUMI NUMBER SEVEN HUNDRED
+            case 0x10E79: retval = 800; break;     // RUMI NUMBER EIGHT HUNDRED
+            case 0x10E7A: retval = 900; break;     // RUMI NUMBER NINE HUNDRED
+            case 0x1105E: retval = 40; break;      // BRAHMI NUMBER FORTY
+            case 0x1105F: retval = 50; break;      // BRAHMI NUMBER FIFTY
+            case 0x11060: retval = 60; break;      // BRAHMI NUMBER SIXTY
+            case 0x11061: retval = 70; break;      // BRAHMI NUMBER SEVENTY
+            case 0x11062: retval = 80; break;      // BRAHMI NUMBER EIGHTY
+            case 0x11063: retval = 90; break;      // BRAHMI NUMBER NINETY
+            case 0x11064: retval = 100; break;     // BRAHMI NUMBER ONE HUNDRED
+            case 0x11065: retval = 1000; break;    // BRAHMI NUMBER ONE THOUSAND
+            case 0x111ED: retval = 40; break;      // SINHALA ARCHAIC NUMBER FORTY
+            case 0x111EE: retval = 50; break;      // SINHALA ARCHAIC NUMBER FIFTY
+            case 0x111EF: retval = 60; break;      // SINHALA ARCHAIC NUMBER SIXTY
+            case 0x111F0: retval = 70; break;      // SINHALA ARCHAIC NUMBER SEVENTY
+            case 0x111F1: retval = 80; break;      // SINHALA ARCHAIC NUMBER EIGHTY
+            case 0x111F2: retval = 90; break;      // SINHALA ARCHAIC NUMBER NINETY
+            case 0x111F3: retval = 100; break;     // SINHALA ARCHAIC NUMBER ONE HUNDRED
+            case 0x111F4: retval = 1000; break;    // SINHALA ARCHAIC NUMBER ONE THOUSAND
+            case 0x118ED: retval = 40; break;      // WARANG CITI NUMBER FORTY
+            case 0x118EE: retval = 50; break;      // WARANG CITI NUMBER FIFTY
+            case 0x118EF: retval = 60; break;      // WARANG CITI NUMBER SIXTY
+            case 0x118F0: retval = 70; break;      // WARANG CITI NUMBER SEVENTY
+            case 0x118F1: retval = 80; break;      // WARANG CITI NUMBER EIGHTY
+            case 0x118F2: retval = 90; break;      // WARANG CITI NUMBER NINETY
+            case 0x12432: retval = 216000; break;  // CUNEIFORM NUMERIC SIGN SHAR2 TIMES GAL PLUS DISH
+            case 0x12433: retval = 432000; break;  // CUNEIFORM NUMERIC SIGN SHAR2 TIMES GAL PLUS MIN
+            case 0x12467: retval = 40; break;      // CUNEIFORM NUMERIC SIGN ELAMITE FORTY
+            case 0x12468: retval = 50; break;      // CUNEIFORM NUMERIC SIGN ELAMITE FIFTY
+            case 0x16B5C: retval = 100; break;     // PAHAWH HMONG NUMBER HUNDREDS
+            case 0x16B5D: retval = 10000; break;   // PAHAWH HMONG NUMBER TEN THOUSANDS
+            case 0x16B5E: retval = 1000000; break; // PAHAWH HMONG NUMBER MILLIONS
+            case 0x16B5F: retval = 100000000; break;// PAHAWH HMONG NUMBER HUNDRED MILLIONS
+            case 0x1D36C: retval = 40; break;      // COUNTING ROD TENS DIGIT FOUR
+            case 0x1D36D: retval = 50; break;      // COUNTING ROD TENS DIGIT FIVE
+            case 0x1D36E: retval = 60; break;      // COUNTING ROD TENS DIGIT SIX
+            case 0x1D36F: retval = 70; break;      // COUNTING ROD TENS DIGIT SEVEN
+            case 0x1D370: retval = 80; break;      // COUNTING ROD TENS DIGIT EIGHT
+            case 0x1D371: retval = 90; break;      // COUNTING ROD TENS DIGIT NINE
             default: retval = -2; break;
             }
             
--- a/jdk/make/data/unicodedata/PropList.txt	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/make/data/unicodedata/PropList.txt	Wed Jul 05 20:42:36 2017 +0200
@@ -1,8 +1,8 @@
-# PropList-6.2.0.txt
-# Date: 2012-05-23, 20:34:59 GMT [MD]
+# PropList-7.0.0.txt
+# Date: 2014-02-19, 15:51:26 GMT [MD]
 #
 # Unicode Character Database
-# Copyright (c) 1991-2012 Unicode, Inc.
+# Copyright (c) 1991-2014 Unicode, Inc.
 # For terms of use, see http://www.unicode.org/terms_of_use.html
 # For documentation, see http://www.unicode.org/reports/tr44/
 
@@ -13,7 +13,6 @@
 0085          ; White_Space # Cc       <control-0085>
 00A0          ; White_Space # Zs       NO-BREAK SPACE
 1680          ; White_Space # Zs       OGHAM SPACE MARK
-180E          ; White_Space # Zs       MONGOLIAN VOWEL SEPARATOR
 2000..200A    ; White_Space # Zs  [11] EN QUAD..HAIR SPACE
 2028          ; White_Space # Zl       LINE SEPARATOR
 2029          ; White_Space # Zp       PARAGRAPH SEPARATOR
@@ -21,14 +20,16 @@
 205F          ; White_Space # Zs       MEDIUM MATHEMATICAL SPACE
 3000          ; White_Space # Zs       IDEOGRAPHIC SPACE
 
-# Total code points: 26
+# Total code points: 25
 
 # ================================================
 
+061C          ; Bidi_Control # Cf       ARABIC LETTER MARK
 200E..200F    ; Bidi_Control # Cf   [2] LEFT-TO-RIGHT MARK..RIGHT-TO-LEFT MARK
 202A..202E    ; Bidi_Control # Cf   [5] LEFT-TO-RIGHT EMBEDDING..RIGHT-TO-LEFT OVERRIDE
+2066..2069    ; Bidi_Control # Cf   [4] LEFT-TO-RIGHT ISOLATE..POP DIRECTIONAL ISOLATE
 
-# Total code points: 7
+# Total code points: 12
 
 # ================================================
 
@@ -51,6 +52,7 @@
 2E17          ; Dash # Pd       DOUBLE OBLIQUE HYPHEN
 2E1A          ; Dash # Pd       HYPHEN WITH DIAERESIS
 2E3A..2E3B    ; Dash # Pd   [2] TWO-EM DASH..THREE-EM DASH
+2E40          ; Dash # Pd       DOUBLE HYPHEN
 301C          ; Dash # Pd       WAVE DASH
 3030          ; Dash # Pd       WAVY DASH
 30A0          ; Dash # Pd       KATAKANA-HIRAGANA DOUBLE HYPHEN
@@ -59,7 +61,7 @@
 FE63          ; Dash # Pd       SMALL HYPHEN-MINUS
 FF0D          ; Dash # Pd       FULLWIDTH HYPHEN-MINUS
 
-# Total code points: 27
+# Total code points: 28
 
 # ================================================
 
@@ -91,6 +93,7 @@
 201F          ; Quotation_Mark # Pi       DOUBLE HIGH-REVERSED-9 QUOTATION MARK
 2039          ; Quotation_Mark # Pi       SINGLE LEFT-POINTING ANGLE QUOTATION MARK
 203A          ; Quotation_Mark # Pf       SINGLE RIGHT-POINTING ANGLE QUOTATION MARK
+2E42          ; Quotation_Mark # Ps       DOUBLE LOW-REVERSED-9 QUOTATION MARK
 300C          ; Quotation_Mark # Ps       LEFT CORNER BRACKET
 300D          ; Quotation_Mark # Pe       RIGHT CORNER BRACKET
 300E          ; Quotation_Mark # Ps       LEFT WHITE CORNER BRACKET
@@ -106,7 +109,7 @@
 FF62          ; Quotation_Mark # Ps       HALFWIDTH LEFT CORNER BRACKET
 FF63          ; Quotation_Mark # Pe       HALFWIDTH RIGHT CORNER BRACKET
 
-# Total code points: 29
+# Total code points: 30
 
 # ================================================
 
@@ -136,6 +139,7 @@
 1361..1368    ; Terminal_Punctuation # Po   [8] ETHIOPIC WORDSPACE..ETHIOPIC PARAGRAPH SEPARATOR
 166D..166E    ; Terminal_Punctuation # Po   [2] CANADIAN SYLLABICS CHI SIGN..CANADIAN SYLLABICS FULL STOP
 16EB..16ED    ; Terminal_Punctuation # Po   [3] RUNIC SINGLE PUNCTUATION..RUNIC CROSS PUNCTUATION
+1735..1736    ; Terminal_Punctuation # Po   [2] PHILIPPINE SINGLE PUNCTUATION..PHILIPPINE DOUBLE PUNCTUATION
 17D4..17D6    ; Terminal_Punctuation # Po   [3] KHMER SIGN KHAN..KHMER SIGN CAMNUC PII KUUH
 17DA          ; Terminal_Punctuation # Po       KHMER SIGN KOOMUUT
 1802..1805    ; Terminal_Punctuation # Po   [4] MONGOLIAN COMMA..MONGOLIAN FOUR DOTS
@@ -149,6 +153,8 @@
 203C..203D    ; Terminal_Punctuation # Po   [2] DOUBLE EXCLAMATION MARK..INTERROBANG
 2047..2049    ; Terminal_Punctuation # Po   [3] DOUBLE QUESTION MARK..EXCLAMATION QUESTION MARK
 2E2E          ; Terminal_Punctuation # Po       REVERSED QUESTION MARK
+2E3C          ; Terminal_Punctuation # Po       STENOGRAPHIC FULL STOP
+2E41          ; Terminal_Punctuation # Po       REVERSED COMMA
 3001..3002    ; Terminal_Punctuation # Po   [2] IDEOGRAPHIC COMMA..IDEOGRAPHIC FULL STOP
 A4FE..A4FF    ; Terminal_Punctuation # Po   [2] LISU PUNCTUATION COMMA..LISU PUNCTUATION FULL STOP
 A60D..A60F    ; Terminal_Punctuation # Po   [3] VAI COMMA..VAI QUESTION MARK
@@ -174,14 +180,27 @@
 103D0         ; Terminal_Punctuation # Po       OLD PERSIAN WORD DIVIDER
 10857         ; Terminal_Punctuation # Po       IMPERIAL ARAMAIC SECTION SIGN
 1091F         ; Terminal_Punctuation # Po       PHOENICIAN WORD SEPARATOR
+10A56..10A57  ; Terminal_Punctuation # Po   [2] KHAROSHTHI PUNCTUATION DANDA..KHAROSHTHI PUNCTUATION DOUBLE DANDA
+10AF0..10AF5  ; Terminal_Punctuation # Po   [6] MANICHAEAN PUNCTUATION STAR..MANICHAEAN PUNCTUATION TWO DOTS
 10B3A..10B3F  ; Terminal_Punctuation # Po   [6] TINY TWO DOTS OVER ONE DOT PUNCTUATION..LARGE ONE RING OVER TWO RINGS PUNCTUATION
+10B99..10B9C  ; Terminal_Punctuation # Po   [4] PSALTER PAHLAVI SECTION MARK..PSALTER PAHLAVI FOUR DOTS WITH DOT
 11047..1104D  ; Terminal_Punctuation # Po   [7] BRAHMI DANDA..BRAHMI PUNCTUATION LOTUS
 110BE..110C1  ; Terminal_Punctuation # Po   [4] KAITHI SECTION MARK..KAITHI DOUBLE DANDA
 11141..11143  ; Terminal_Punctuation # Po   [3] CHAKMA DANDA..CHAKMA QUESTION MARK
 111C5..111C6  ; Terminal_Punctuation # Po   [2] SHARADA DANDA..SHARADA DOUBLE DANDA
-12470..12473  ; Terminal_Punctuation # Po   [4] CUNEIFORM PUNCTUATION SIGN OLD ASSYRIAN WORD DIVIDER..CUNEIFORM PUNCTUATION SIGN DIAGONAL TRICOLON
+111CD         ; Terminal_Punctuation # Po       SHARADA SUTRA MARK
+11238..1123C  ; Terminal_Punctuation # Po   [5] KHOJKI DANDA..KHOJKI DOUBLE SECTION MARK
+115C2..115C5  ; Terminal_Punctuation # Po   [4] SIDDHAM DANDA..SIDDHAM SEPARATOR BAR
+115C9         ; Terminal_Punctuation # Po       SIDDHAM END OF TEXT MARK
+11641..11642  ; Terminal_Punctuation # Po   [2] MODI DANDA..MODI DOUBLE DANDA
+12470..12474  ; Terminal_Punctuation # Po   [5] CUNEIFORM PUNCTUATION SIGN OLD ASSYRIAN WORD DIVIDER..CUNEIFORM PUNCTUATION SIGN DIAGONAL QUADCOLON
+16A6E..16A6F  ; Terminal_Punctuation # Po   [2] MRO DANDA..MRO DOUBLE DANDA
+16AF5         ; Terminal_Punctuation # Po       BASSA VAH FULL STOP
+16B37..16B39  ; Terminal_Punctuation # Po   [3] PAHAWH HMONG SIGN VOS THOM..PAHAWH HMONG SIGN CIM CHEEM
+16B44         ; Terminal_Punctuation # Po       PAHAWH HMONG SIGN XAUS
+1BC9F         ; Terminal_Punctuation # Po       DUPLOYAN PUNCTUATION CHINOOK FULL STOP
 
-# Total code points: 176
+# Total code points: 214
 
 # ================================================
 
@@ -230,6 +249,10 @@
 21D5..21DB    ; Other_Math # So   [7] UP DOWN DOUBLE ARROW..RIGHTWARDS TRIPLE ARROW
 21DD          ; Other_Math # So       RIGHTWARDS SQUIGGLE ARROW
 21E4..21E5    ; Other_Math # So   [2] LEFTWARDS ARROW TO BAR..RIGHTWARDS ARROW TO BAR
+2308          ; Other_Math # Ps       LEFT CEILING
+2309          ; Other_Math # Pe       RIGHT CEILING
+230A          ; Other_Math # Ps       LEFT FLOOR
+230B          ; Other_Math # Pe       RIGHT FLOOR
 23B4..23B5    ; Other_Math # So   [2] TOP SQUARE BRACKET..BOTTOM SQUARE BRACKET
 23B7          ; Other_Math # So       RADICAL SYMBOL BOTTOM
 23D0          ; Other_Math # So       VERTICAL LINE EXTENSION
@@ -358,7 +381,7 @@
 1EEA5..1EEA9  ; Other_Math # Lo   [5] ARABIC MATHEMATICAL DOUBLE-STRUCK WAW..ARABIC MATHEMATICAL DOUBLE-STRUCK YEH
 1EEAB..1EEBB  ; Other_Math # Lo  [17] ARABIC MATHEMATICAL DOUBLE-STRUCK LAM..ARABIC MATHEMATICAL DOUBLE-STRUCK GHAIN
 
-# Total code points: 1358
+# Total code points: 1362
 
 # ================================================
 
@@ -403,8 +426,7 @@
 0825..0827    ; Other_Alphabetic # Mn   [3] SAMARITAN VOWEL SIGN SHORT A..SAMARITAN VOWEL SIGN U
 0829..082C    ; Other_Alphabetic # Mn   [4] SAMARITAN VOWEL SIGN LONG I..SAMARITAN VOWEL SIGN SUKUN
 08E4..08E9    ; Other_Alphabetic # Mn   [6] ARABIC CURLY FATHA..ARABIC CURLY KASRATAN
-08F0..08FE    ; Other_Alphabetic # Mn  [15] ARABIC OPEN FATHATAN..ARABIC DAMMA WITH DOT
-0900..0902    ; Other_Alphabetic # Mn   [3] DEVANAGARI SIGN INVERTED CANDRABINDU..DEVANAGARI SIGN ANUSVARA
+08F0..0902    ; Other_Alphabetic # Mn  [19] ARABIC OPEN FATHATAN..DEVANAGARI SIGN ANUSVARA
 0903          ; Other_Alphabetic # Mc       DEVANAGARI SIGN VISARGA
 093A          ; Other_Alphabetic # Mn       DEVANAGARI VOWEL SIGN OE
 093B          ; Other_Alphabetic # Mc       DEVANAGARI VOWEL SIGN OOE
@@ -457,6 +479,7 @@
 0BC6..0BC8    ; Other_Alphabetic # Mc   [3] TAMIL VOWEL SIGN E..TAMIL VOWEL SIGN AI
 0BCA..0BCC    ; Other_Alphabetic # Mc   [3] TAMIL VOWEL SIGN O..TAMIL VOWEL SIGN AU
 0BD7          ; Other_Alphabetic # Mc       TAMIL AU LENGTH MARK
+0C00          ; Other_Alphabetic # Mn       TELUGU SIGN COMBINING CANDRABINDU ABOVE
 0C01..0C03    ; Other_Alphabetic # Mc   [3] TELUGU SIGN CANDRABINDU..TELUGU SIGN VISARGA
 0C3E..0C40    ; Other_Alphabetic # Mn   [3] TELUGU VOWEL SIGN AA..TELUGU VOWEL SIGN II
 0C41..0C44    ; Other_Alphabetic # Mc   [4] TELUGU VOWEL SIGN U..TELUGU VOWEL SIGN VOCALIC RR
@@ -464,6 +487,7 @@
 0C4A..0C4C    ; Other_Alphabetic # Mn   [3] TELUGU VOWEL SIGN O..TELUGU VOWEL SIGN AU
 0C55..0C56    ; Other_Alphabetic # Mn   [2] TELUGU LENGTH MARK..TELUGU AI LENGTH MARK
 0C62..0C63    ; Other_Alphabetic # Mn   [2] TELUGU VOWEL SIGN VOCALIC L..TELUGU VOWEL SIGN VOCALIC LL
+0C81          ; Other_Alphabetic # Mn       KANNADA SIGN CANDRABINDU
 0C82..0C83    ; Other_Alphabetic # Mc   [2] KANNADA SIGN ANUSVARA..KANNADA SIGN VISARGA
 0CBE          ; Other_Alphabetic # Mc       KANNADA VOWEL SIGN AA
 0CBF          ; Other_Alphabetic # Mn       KANNADA VOWEL SIGN I
@@ -474,6 +498,7 @@
 0CCC          ; Other_Alphabetic # Mn       KANNADA VOWEL SIGN AU
 0CD5..0CD6    ; Other_Alphabetic # Mc   [2] KANNADA LENGTH MARK..KANNADA AI LENGTH MARK
 0CE2..0CE3    ; Other_Alphabetic # Mn   [2] KANNADA VOWEL SIGN VOCALIC L..KANNADA VOWEL SIGN VOCALIC LL
+0D01          ; Other_Alphabetic # Mn       MALAYALAM SIGN CANDRABINDU
 0D02..0D03    ; Other_Alphabetic # Mc   [2] MALAYALAM SIGN ANUSVARA..MALAYALAM SIGN VISARGA
 0D3E..0D40    ; Other_Alphabetic # Mc   [3] MALAYALAM VOWEL SIGN AA..MALAYALAM VOWEL SIGN II
 0D41..0D44    ; Other_Alphabetic # Mn   [4] MALAYALAM VOWEL SIGN U..MALAYALAM VOWEL SIGN VOCALIC RR
@@ -538,7 +563,8 @@
 19B0..19C0    ; Other_Alphabetic # Mc  [17] NEW TAI LUE VOWEL SIGN VOWEL SHORTENER..NEW TAI LUE VOWEL SIGN IY
 19C8..19C9    ; Other_Alphabetic # Mc   [2] NEW TAI LUE TONE MARK-1..NEW TAI LUE TONE MARK-2
 1A17..1A18    ; Other_Alphabetic # Mn   [2] BUGINESE VOWEL SIGN I..BUGINESE VOWEL SIGN U
-1A19..1A1B    ; Other_Alphabetic # Mc   [3] BUGINESE VOWEL SIGN E..BUGINESE VOWEL SIGN AE
+1A19..1A1A    ; Other_Alphabetic # Mc   [2] BUGINESE VOWEL SIGN E..BUGINESE VOWEL SIGN O
+1A1B          ; Other_Alphabetic # Mn       BUGINESE VOWEL SIGN AE
 1A55          ; Other_Alphabetic # Mc       TAI THAM CONSONANT SIGN MEDIAL RA
 1A56          ; Other_Alphabetic # Mn       TAI THAM CONSONANT SIGN MEDIAL LA
 1A57          ; Other_Alphabetic # Mc       TAI THAM CONSONANT SIGN LA TANG LAI
@@ -564,7 +590,7 @@
 1BA2..1BA5    ; Other_Alphabetic # Mn   [4] SUNDANESE CONSONANT SIGN PANYAKRA..SUNDANESE VOWEL SIGN PANYUKU
 1BA6..1BA7    ; Other_Alphabetic # Mc   [2] SUNDANESE VOWEL SIGN PANAELAENG..SUNDANESE VOWEL SIGN PANOLONG
 1BA8..1BA9    ; Other_Alphabetic # Mn   [2] SUNDANESE VOWEL SIGN PAMEPET..SUNDANESE VOWEL SIGN PANEULEUNG
-1BAC..1BAD    ; Other_Alphabetic # Mc   [2] SUNDANESE CONSONANT SIGN PASANGAN MA..SUNDANESE CONSONANT SIGN PASANGAN WA
+1BAC..1BAD    ; Other_Alphabetic # Mn   [2] SUNDANESE CONSONANT SIGN PASANGAN MA..SUNDANESE CONSONANT SIGN PASANGAN WA
 1BE7          ; Other_Alphabetic # Mc       BATAK VOWEL SIGN E
 1BE8..1BE9    ; Other_Alphabetic # Mn   [2] BATAK VOWEL SIGN PAKPAK E..BATAK VOWEL SIGN EE
 1BEA..1BEC    ; Other_Alphabetic # Mc   [3] BATAK VOWEL SIGN I..BATAK VOWEL SIGN O
@@ -575,6 +601,7 @@
 1C2C..1C33    ; Other_Alphabetic # Mn   [8] LEPCHA VOWEL SIGN E..LEPCHA CONSONANT SIGN T
 1C34..1C35    ; Other_Alphabetic # Mc   [2] LEPCHA CONSONANT SIGN NYIN-DO..LEPCHA CONSONANT SIGN KANG
 1CF2..1CF3    ; Other_Alphabetic # Mc   [2] VEDIC SIGN ARDHAVISARGA..VEDIC SIGN ROTATED ARDHAVISARGA
+1DE7..1DF4    ; Other_Alphabetic # Mn  [14] COMBINING LATIN SMALL LETTER ALPHA..COMBINING LATIN SMALL LETTER U WITH DIAERESIS
 24B6..24E9    ; Other_Alphabetic # So  [52] CIRCLED LATIN CAPITAL LETTER A..CIRCLED LATIN SMALL LETTER Z
 2DE0..2DFF    ; Other_Alphabetic # Mn  [32] COMBINING CYRILLIC LETTER BE..COMBINING CYRILLIC LETTER IOTIFIED BIG YUS
 A674..A67B    ; Other_Alphabetic # Mn   [8] COMBINING CYRILLIC LETTER UKRAINIAN IE..COMBINING CYRILLIC LETTER OMEGA
@@ -616,6 +643,7 @@
 ABE8          ; Other_Alphabetic # Mn       MEETEI MAYEK VOWEL SIGN UNAP
 ABE9..ABEA    ; Other_Alphabetic # Mc   [2] MEETEI MAYEK VOWEL SIGN CHEINAP..MEETEI MAYEK VOWEL SIGN NUNG
 FB1E          ; Other_Alphabetic # Mn       HEBREW POINT JUDEO-SPANISH VARIKA
+10376..1037A  ; Other_Alphabetic # Mn   [5] COMBINING OLD PERMIC LETTER AN..COMBINING OLD PERMIC LETTER SII
 10A01..10A03  ; Other_Alphabetic # Mn   [3] KHAROSHTHI VOWEL SIGN I..KHAROSHTHI VOWEL SIGN VOCALIC R
 10A05..10A06  ; Other_Alphabetic # Mn   [2] KHAROSHTHI VOWEL SIGN E..KHAROSHTHI VOWEL SIGN O
 10A0C..10A0F  ; Other_Alphabetic # Mn   [4] KHAROSHTHI VOWEL LENGTH MARK..KHAROSHTHI SIGN VISARGA
@@ -636,14 +664,54 @@
 111B3..111B5  ; Other_Alphabetic # Mc   [3] SHARADA VOWEL SIGN AA..SHARADA VOWEL SIGN II
 111B6..111BE  ; Other_Alphabetic # Mn   [9] SHARADA VOWEL SIGN U..SHARADA VOWEL SIGN O
 111BF         ; Other_Alphabetic # Mc       SHARADA VOWEL SIGN AU
+1122C..1122E  ; Other_Alphabetic # Mc   [3] KHOJKI VOWEL SIGN AA..KHOJKI VOWEL SIGN II
+1122F..11231  ; Other_Alphabetic # Mn   [3] KHOJKI VOWEL SIGN U..KHOJKI VOWEL SIGN AI
+11232..11233  ; Other_Alphabetic # Mc   [2] KHOJKI VOWEL SIGN O..KHOJKI VOWEL SIGN AU
+11234         ; Other_Alphabetic # Mn       KHOJKI SIGN ANUSVARA
+11237         ; Other_Alphabetic # Mn       KHOJKI SIGN SHADDA
+112DF         ; Other_Alphabetic # Mn       KHUDAWADI SIGN ANUSVARA
+112E0..112E2  ; Other_Alphabetic # Mc   [3] KHUDAWADI VOWEL SIGN AA..KHUDAWADI VOWEL SIGN II
+112E3..112E8  ; Other_Alphabetic # Mn   [6] KHUDAWADI VOWEL SIGN U..KHUDAWADI VOWEL SIGN AU
+11301         ; Other_Alphabetic # Mn       GRANTHA SIGN CANDRABINDU
+11302..11303  ; Other_Alphabetic # Mc   [2] GRANTHA SIGN ANUSVARA..GRANTHA SIGN VISARGA
+1133E..1133F  ; Other_Alphabetic # Mc   [2] GRANTHA VOWEL SIGN AA..GRANTHA VOWEL SIGN I
+11340         ; Other_Alphabetic # Mn       GRANTHA VOWEL SIGN II
+11341..11344  ; Other_Alphabetic # Mc   [4] GRANTHA VOWEL SIGN U..GRANTHA VOWEL SIGN VOCALIC RR
+11347..11348  ; Other_Alphabetic # Mc   [2] GRANTHA VOWEL SIGN EE..GRANTHA VOWEL SIGN AI
+1134B..1134C  ; Other_Alphabetic # Mc   [2] GRANTHA VOWEL SIGN OO..GRANTHA VOWEL SIGN AU
+11357         ; Other_Alphabetic # Mc       GRANTHA AU LENGTH MARK
+11362..11363  ; Other_Alphabetic # Mc   [2] GRANTHA VOWEL SIGN VOCALIC L..GRANTHA VOWEL SIGN VOCALIC LL
+114B0..114B2  ; Other_Alphabetic # Mc   [3] TIRHUTA VOWEL SIGN AA..TIRHUTA VOWEL SIGN II
+114B3..114B8  ; Other_Alphabetic # Mn   [6] TIRHUTA VOWEL SIGN U..TIRHUTA VOWEL SIGN VOCALIC LL
+114B9         ; Other_Alphabetic # Mc       TIRHUTA VOWEL SIGN E
+114BA         ; Other_Alphabetic # Mn       TIRHUTA VOWEL SIGN SHORT E
+114BB..114BE  ; Other_Alphabetic # Mc   [4] TIRHUTA VOWEL SIGN AI..TIRHUTA VOWEL SIGN AU
+114BF..114C0  ; Other_Alphabetic # Mn   [2] TIRHUTA SIGN CANDRABINDU..TIRHUTA SIGN ANUSVARA
+114C1         ; Other_Alphabetic # Mc       TIRHUTA SIGN VISARGA
+115AF..115B1  ; Other_Alphabetic # Mc   [3] SIDDHAM VOWEL SIGN AA..SIDDHAM VOWEL SIGN II
+115B2..115B5  ; Other_Alphabetic # Mn   [4] SIDDHAM VOWEL SIGN U..SIDDHAM VOWEL SIGN VOCALIC RR
+115B8..115BB  ; Other_Alphabetic # Mc   [4] SIDDHAM VOWEL SIGN E..SIDDHAM VOWEL SIGN AU
+115BC..115BD  ; Other_Alphabetic # Mn   [2] SIDDHAM SIGN CANDRABINDU..SIDDHAM SIGN ANUSVARA
+115BE         ; Other_Alphabetic # Mc       SIDDHAM SIGN VISARGA
+11630..11632  ; Other_Alphabetic # Mc   [3] MODI VOWEL SIGN AA..MODI VOWEL SIGN II
+11633..1163A  ; Other_Alphabetic # Mn   [8] MODI VOWEL SIGN U..MODI VOWEL SIGN AI
+1163B..1163C  ; Other_Alphabetic # Mc   [2] MODI VOWEL SIGN O..MODI VOWEL SIGN AU
+1163D         ; Other_Alphabetic # Mn       MODI SIGN ANUSVARA
+1163E         ; Other_Alphabetic # Mc       MODI SIGN VISARGA
+11640         ; Other_Alphabetic # Mn       MODI SIGN ARDHACANDRA
 116AB         ; Other_Alphabetic # Mn       TAKRI SIGN ANUSVARA
 116AC         ; Other_Alphabetic # Mc       TAKRI SIGN VISARGA
 116AD         ; Other_Alphabetic # Mn       TAKRI VOWEL SIGN AA
 116AE..116AF  ; Other_Alphabetic # Mc   [2] TAKRI VOWEL SIGN I..TAKRI VOWEL SIGN II
 116B0..116B5  ; Other_Alphabetic # Mn   [6] TAKRI VOWEL SIGN U..TAKRI VOWEL SIGN AU
+16B30..16B36  ; Other_Alphabetic # Mn   [7] PAHAWH HMONG MARK CIM TUB..PAHAWH HMONG MARK CIM TAUM
 16F51..16F7E  ; Other_Alphabetic # Mc  [46] MIAO SIGN ASPIRATION..MIAO VOWEL SIGN NG
+1BC9E         ; Other_Alphabetic # Mn       DUPLOYAN DOUBLE MARK
+1F130..1F149  ; Other_Alphabetic # So  [26] SQUARED LATIN CAPITAL LETTER A..SQUARED LATIN CAPITAL LETTER Z
+1F150..1F169  ; Other_Alphabetic # So  [26] NEGATIVE CIRCLED LATIN CAPITAL LETTER A..NEGATIVE CIRCLED LATIN CAPITAL LETTER Z
+1F170..1F189  ; Other_Alphabetic # So  [26] NEGATIVE SQUARED LATIN CAPITAL LETTER A..NEGATIVE SQUARED LATIN CAPITAL LETTER Z
 
-# Total code points: 922
+# Total code points: 1116
 
 # ================================================
 
@@ -746,6 +814,7 @@
 1939..193B    ; Diacritic # Mn   [3] LIMBU SIGN MUKPHRENG..LIMBU SIGN SA-I
 1A75..1A7C    ; Diacritic # Mn   [8] TAI THAM SIGN TONE-1..TAI THAM SIGN KHUEN-LUE KARAN
 1A7F          ; Diacritic # Mn       TAI THAM COMBINING CRYPTOGRAMMIC DOT
+1AB0..1ABD    ; Diacritic # Mn  [14] COMBINING DOUBLED CIRCUMFLEX ACCENT..COMBINING PARENTHESES BELOW
 1B34          ; Diacritic # Mn       BALINESE SIGN REREKAN
 1B44          ; Diacritic # Mc       BALINESE ADEG ADEG
 1B6B..1B73    ; Diacritic # Mn   [9] BALINESE MUSICAL SYMBOL COMBINING TEGEH..BALINESE MUSICAL SYMBOL COMBINING GONG
@@ -760,8 +829,10 @@
 1CE2..1CE8    ; Diacritic # Mn   [7] VEDIC SIGN VISARGA SVARITA..VEDIC SIGN VISARGA ANUDATTA WITH TAIL
 1CED          ; Diacritic # Mn       VEDIC SIGN TIRYAK
 1CF4          ; Diacritic # Mn       VEDIC TONE CANDRA ABOVE
+1CF8..1CF9    ; Diacritic # Mn   [2] VEDIC TONE RING ABOVE..VEDIC TONE DOUBLE RING ABOVE
 1D2C..1D6A    ; Diacritic # Lm  [63] MODIFIER LETTER CAPITAL A..GREEK SUBSCRIPT SMALL LETTER CHI
 1DC4..1DCF    ; Diacritic # Mn  [12] COMBINING MACRON-ACUTE..COMBINING ZIGZAG BELOW
+1DF5          ; Diacritic # Mn       COMBINING UP TACK ABOVE
 1DFD..1DFF    ; Diacritic # Mn   [3] COMBINING ALMOST EQUAL TO BELOW..COMBINING RIGHT ARROWHEAD AND DOWN ARROWHEAD BELOW
 1FBD          ; Diacritic # Sk       GREEK KORONIS
 1FBF..1FC1    ; Diacritic # Sk   [3] GREEK PSILI..GREEK DIALYTIKA AND PERISPOMENI
@@ -779,6 +850,7 @@
 A66F          ; Diacritic # Mn       COMBINING CYRILLIC VZMET
 A67C..A67D    ; Diacritic # Mn   [2] COMBINING CYRILLIC KAVYKA..COMBINING CYRILLIC PAYEROK
 A67F          ; Diacritic # Lm       CYRILLIC PAYEROK
+A69C..A69D    ; Diacritic # Lm   [2] MODIFIER LETTER CYRILLIC HARD SIGN..MODIFIER LETTER CYRILLIC SOFT SIGN
 A6F0..A6F1    ; Diacritic # Mn   [2] BAMUM COMBINING MARK KOQNDON..BAMUM COMBINING MARK TUKWENTIS
 A717..A71F    ; Diacritic # Lm   [9] MODIFIER LETTER DOT VERTICAL BAR..MODIFIER LETTER LOW INVERTED EXCLAMATION MARK
 A720..A721    ; Diacritic # Sk   [2] MODIFIER LETTER STRESS AND HIGH TONE..MODIFIER LETTER STRESS AND LOW TONE
@@ -791,26 +863,45 @@
 A953          ; Diacritic # Mc       REJANG VIRAMA
 A9B3          ; Diacritic # Mn       JAVANESE SIGN CECAK TELU
 A9C0          ; Diacritic # Mc       JAVANESE PANGKON
+A9E5          ; Diacritic # Mn       MYANMAR SIGN SHAN SAW
 AA7B          ; Diacritic # Mc       MYANMAR SIGN PAO KAREN TONE
+AA7C          ; Diacritic # Mn       MYANMAR SIGN TAI LAING TONE-2
+AA7D          ; Diacritic # Mc       MYANMAR SIGN TAI LAING TONE-5
 AABF          ; Diacritic # Mn       TAI VIET TONE MAI EK
 AAC0          ; Diacritic # Lo       TAI VIET TONE MAI NUENG
 AAC1          ; Diacritic # Mn       TAI VIET TONE MAI THO
 AAC2          ; Diacritic # Lo       TAI VIET TONE MAI SONG
 AAF6          ; Diacritic # Mn       MEETEI MAYEK VIRAMA
+AB5B          ; Diacritic # Sk       MODIFIER BREVE WITH INVERTED BREVE
+AB5C..AB5F    ; Diacritic # Lm   [4] MODIFIER LETTER SMALL HENG..MODIFIER LETTER SMALL U WITH LEFT HOOK
 ABEC          ; Diacritic # Mc       MEETEI MAYEK LUM IYEK
 ABED          ; Diacritic # Mn       MEETEI MAYEK APUN IYEK
 FB1E          ; Diacritic # Mn       HEBREW POINT JUDEO-SPANISH VARIKA
-FE20..FE26    ; Diacritic # Mn   [7] COMBINING LIGATURE LEFT HALF..COMBINING CONJOINING MACRON
+FE20..FE2D    ; Diacritic # Mn  [14] COMBINING LIGATURE LEFT HALF..COMBINING CONJOINING MACRON BELOW
 FF3E          ; Diacritic # Sk       FULLWIDTH CIRCUMFLEX ACCENT
 FF40          ; Diacritic # Sk       FULLWIDTH GRAVE ACCENT
 FF70          ; Diacritic # Lm       HALFWIDTH KATAKANA-HIRAGANA PROLONGED SOUND MARK
 FF9E..FF9F    ; Diacritic # Lm   [2] HALFWIDTH KATAKANA VOICED SOUND MARK..HALFWIDTH KATAKANA SEMI-VOICED SOUND MARK
 FFE3          ; Diacritic # Sk       FULLWIDTH MACRON
+102E0         ; Diacritic # Mn       COPTIC EPACT THOUSANDS MARK
+10AE5..10AE6  ; Diacritic # Mn   [2] MANICHAEAN ABBREVIATION MARK ABOVE..MANICHAEAN ABBREVIATION MARK BELOW
 110B9..110BA  ; Diacritic # Mn   [2] KAITHI SIGN VIRAMA..KAITHI SIGN NUKTA
 11133..11134  ; Diacritic # Mn   [2] CHAKMA VIRAMA..CHAKMA MAAYYAA
+11173         ; Diacritic # Mn       MAHAJANI SIGN NUKTA
 111C0         ; Diacritic # Mc       SHARADA SIGN VIRAMA
+11235         ; Diacritic # Mc       KHOJKI SIGN VIRAMA
+11236         ; Diacritic # Mn       KHOJKI SIGN NUKTA
+112E9..112EA  ; Diacritic # Mn   [2] KHUDAWADI SIGN NUKTA..KHUDAWADI SIGN VIRAMA
+1133C         ; Diacritic # Mn       GRANTHA SIGN NUKTA
+1134D         ; Diacritic # Mc       GRANTHA SIGN VIRAMA
+11366..1136C  ; Diacritic # Mn   [7] COMBINING GRANTHA DIGIT ZERO..COMBINING GRANTHA DIGIT SIX
+11370..11374  ; Diacritic # Mn   [5] COMBINING GRANTHA LETTER A..COMBINING GRANTHA LETTER PA
+114C2..114C3  ; Diacritic # Mn   [2] TIRHUTA SIGN VIRAMA..TIRHUTA SIGN NUKTA
+115BF..115C0  ; Diacritic # Mn   [2] SIDDHAM SIGN VIRAMA..SIDDHAM SIGN NUKTA
+1163F         ; Diacritic # Mn       MODI SIGN VIRAMA
 116B6         ; Diacritic # Mc       TAKRI SIGN VIRAMA
 116B7         ; Diacritic # Mn       TAKRI SIGN NUKTA
+16AF0..16AF4  ; Diacritic # Mn   [5] BASSA VAH COMBINING HIGH TONE..BASSA VAH COMBINING HIGH-LOW TONE
 16F8F..16F92  ; Diacritic # Mn   [4] MIAO TONE RIGHT..MIAO TONE BELOW
 16F93..16F9F  ; Diacritic # Lm  [13] MIAO LETTER TONE-2..MIAO LETTER REFORMED TONE-8
 1D167..1D169  ; Diacritic # Mn   [3] MUSICAL SYMBOL COMBINING TREMOLO-1..MUSICAL SYMBOL COMBINING TREMOLO-3
@@ -818,8 +909,9 @@
 1D17B..1D182  ; Diacritic # Mn   [8] MUSICAL SYMBOL COMBINING ACCENT..MUSICAL SYMBOL COMBINING LOURE
 1D185..1D18B  ; Diacritic # Mn   [7] MUSICAL SYMBOL COMBINING DOIT..MUSICAL SYMBOL COMBINING TRIPLE TONGUE
 1D1AA..1D1AD  ; Diacritic # Mn   [4] MUSICAL SYMBOL COMBINING DOWN BOW..MUSICAL SYMBOL COMBINING SNAP PIZZICATO
+1E8D0..1E8D6  ; Diacritic # Mn   [7] MENDE KIKAKUI COMBINING NUMBER TEENS..MENDE KIKAKUI COMBINING NUMBER MILLIONS
 
-# Total code points: 693
+# Total code points: 766
 
 # ================================================
 
@@ -841,12 +933,16 @@
 A015          ; Extender # Lm       YI SYLLABLE WU
 A60C          ; Extender # Lm       VAI SYLLABLE LENGTHENER
 A9CF          ; Extender # Lm       JAVANESE PANGRANGKEP
+A9E6          ; Extender # Lm       MYANMAR MODIFIER LETTER SHAN REDUPLICATION
 AA70          ; Extender # Lm       MYANMAR MODIFIER LETTER KHAMTI REDUPLICATION
 AADD          ; Extender # Lm       TAI VIET SYMBOL SAM
 AAF3..AAF4    ; Extender # Lm   [2] MEETEI MAYEK SYLLABLE REPETITION MARK..MEETEI MAYEK WORD REPETITION MARK
 FF70          ; Extender # Lm       HALFWIDTH KATAKANA-HIRAGANA PROLONGED SOUND MARK
+1135D         ; Extender # Lo       GRANTHA SIGN PLUTA
+115C6..115C8  ; Extender # Po   [3] SIDDHAM REPETITION MARK-1..SIDDHAM REPETITION MARK-3
+16B42..16B43  ; Extender # Lm   [2] PAHAWH HMONG SIGN VOS NRUA..PAHAWH HMONG SIGN IB YAM
 
-# Total code points: 31
+# Total code points: 38
 
 # ================================================
 
@@ -866,17 +962,22 @@
 2170..217F    ; Other_Lowercase # Nl  [16] SMALL ROMAN NUMERAL ONE..SMALL ROMAN NUMERAL ONE THOUSAND
 24D0..24E9    ; Other_Lowercase # So  [26] CIRCLED LATIN SMALL LETTER A..CIRCLED LATIN SMALL LETTER Z
 2C7C..2C7D    ; Other_Lowercase # Lm   [2] LATIN SUBSCRIPT SMALL LETTER J..MODIFIER LETTER CAPITAL V
+A69C..A69D    ; Other_Lowercase # Lm   [2] MODIFIER LETTER CYRILLIC HARD SIGN..MODIFIER LETTER CYRILLIC SOFT SIGN
 A770          ; Other_Lowercase # Lm       MODIFIER LETTER US
 A7F8..A7F9    ; Other_Lowercase # Lm   [2] MODIFIER LETTER CAPITAL H WITH STROKE..MODIFIER LETTER SMALL LIGATURE OE
+AB5C..AB5F    ; Other_Lowercase # Lm   [4] MODIFIER LETTER SMALL HENG..MODIFIER LETTER SMALL U WITH LEFT HOOK
 
-# Total code points: 183
+# Total code points: 189
 
 # ================================================
 
 2160..216F    ; Other_Uppercase # Nl  [16] ROMAN NUMERAL ONE..ROMAN NUMERAL ONE THOUSAND
 24B6..24CF    ; Other_Uppercase # So  [26] CIRCLED LATIN CAPITAL LETTER A..CIRCLED LATIN CAPITAL LETTER Z
+1F130..1F149  ; Other_Uppercase # So  [26] SQUARED LATIN CAPITAL LETTER A..SQUARED LATIN CAPITAL LETTER Z
+1F150..1F169  ; Other_Uppercase # So  [26] NEGATIVE CIRCLED LATIN CAPITAL LETTER A..NEGATIVE CIRCLED LATIN CAPITAL LETTER Z
+1F170..1F189  ; Other_Uppercase # So  [26] NEGATIVE SQUARED LATIN CAPITAL LETTER A..NEGATIVE SQUARED LATIN CAPITAL LETTER Z
 
-# Total code points: 42
+# Total code points: 120
 
 # ================================================
 
@@ -918,10 +1019,15 @@
 200C..200D    ; Other_Grapheme_Extend # Cf   [2] ZERO WIDTH NON-JOINER..ZERO WIDTH JOINER
 302E..302F    ; Other_Grapheme_Extend # Mc   [2] HANGUL SINGLE DOT TONE MARK..HANGUL DOUBLE DOT TONE MARK
 FF9E..FF9F    ; Other_Grapheme_Extend # Lm   [2] HALFWIDTH KATAKANA VOICED SOUND MARK..HALFWIDTH KATAKANA SEMI-VOICED SOUND MARK
+1133E         ; Other_Grapheme_Extend # Mc       GRANTHA VOWEL SIGN AA
+11357         ; Other_Grapheme_Extend # Mc       GRANTHA AU LENGTH MARK
+114B0         ; Other_Grapheme_Extend # Mc       TIRHUTA VOWEL SIGN AA
+114BD         ; Other_Grapheme_Extend # Mc       TIRHUTA VOWEL SIGN SHORT O
+115AF         ; Other_Grapheme_Extend # Mc       SIDDHAM VOWEL SIGN AA
 1D165         ; Other_Grapheme_Extend # Mc       MUSICAL SYMBOL COMBINING STEM
 1D16E..1D172  ; Other_Grapheme_Extend # Mc   [5] MUSICAL SYMBOL COMBINING FLAG-1..MUSICAL SYMBOL COMBINING FLAG-5
 
-# Total code points: 25
+# Total code points: 30
 
 # ================================================
 
@@ -966,7 +1072,7 @@
 034F          ; Other_Default_Ignorable_Code_Point # Mn       COMBINING GRAPHEME JOINER
 115F..1160    ; Other_Default_Ignorable_Code_Point # Lo   [2] HANGUL CHOSEONG FILLER..HANGUL JUNGSEONG FILLER
 17B4..17B5    ; Other_Default_Ignorable_Code_Point # Mn   [2] KHMER VOWEL INHERENT AQ..KHMER VOWEL INHERENT AA
-2065..2069    ; Other_Default_Ignorable_Code_Point # Cn   [5] <reserved-2065>..<reserved-2069>
+2065          ; Other_Default_Ignorable_Code_Point # Cn       <reserved-2065>
 3164          ; Other_Default_Ignorable_Code_Point # Lo       HANGUL FILLER
 FFA0          ; Other_Default_Ignorable_Code_Point # Lo       HALFWIDTH HANGUL FILLER
 FFF0..FFF8    ; Other_Default_Ignorable_Code_Point # Cn   [9] <reserved-FFF0>..<reserved-FFF8>
@@ -975,7 +1081,7 @@
 E0080..E00FF  ; Other_Default_Ignorable_Code_Point # Cn [128] <reserved-E0080>..<reserved-E00FF>
 E01F0..E0FFF  ; Other_Default_Ignorable_Code_Point # Cn [3600] <reserved-E01F0>..<reserved-E0FFF>
 
-# Total code points: 3780
+# Total code points: 3776
 
 # ================================================
 
@@ -1060,8 +1166,6 @@
 0021          ; STerm # Po       EXCLAMATION MARK
 002E          ; STerm # Po       FULL STOP
 003F          ; STerm # Po       QUESTION MARK
-055C          ; STerm # Po       ARMENIAN EXCLAMATION MARK
-055E          ; STerm # Po       ARMENIAN QUESTION MARK
 0589          ; STerm # Po       ARMENIAN FULL STOP
 061F          ; STerm # Po       ARABIC QUESTION MARK
 06D4          ; STerm # Po       ARABIC FULL STOP
@@ -1084,6 +1188,7 @@
 203C..203D    ; STerm # Po   [2] DOUBLE EXCLAMATION MARK..INTERROBANG
 2047..2049    ; STerm # Po   [3] DOUBLE QUESTION MARK..EXCLAMATION QUESTION MARK
 2E2E          ; STerm # Po       REVERSED QUESTION MARK
+2E3C          ; STerm # Po       STENOGRAPHIC FULL STOP
 3002          ; STerm # Po       IDEOGRAPHIC FULL STOP
 A4FF          ; STerm # Po       LISU PUNCTUATION FULL STOP
 A60E..A60F    ; STerm # Po   [2] VAI FULL STOP..VAI QUESTION MARK
@@ -1107,8 +1212,19 @@
 110BE..110C1  ; STerm # Po   [4] KAITHI SECTION MARK..KAITHI DOUBLE DANDA
 11141..11143  ; STerm # Po   [3] CHAKMA DANDA..CHAKMA QUESTION MARK
 111C5..111C6  ; STerm # Po   [2] SHARADA DANDA..SHARADA DOUBLE DANDA
+111CD         ; STerm # Po       SHARADA SUTRA MARK
+11238..11239  ; STerm # Po   [2] KHOJKI DANDA..KHOJKI DOUBLE DANDA
+1123B..1123C  ; STerm # Po   [2] KHOJKI SECTION MARK..KHOJKI DOUBLE SECTION MARK
+115C2..115C3  ; STerm # Po   [2] SIDDHAM DANDA..SIDDHAM DOUBLE DANDA
+115C9         ; STerm # Po       SIDDHAM END OF TEXT MARK
+11641..11642  ; STerm # Po   [2] MODI DANDA..MODI DOUBLE DANDA
+16A6E..16A6F  ; STerm # Po   [2] MRO DANDA..MRO DOUBLE DANDA
+16AF5         ; STerm # Po       BASSA VAH FULL STOP
+16B37..16B38  ; STerm # Po   [2] PAHAWH HMONG SIGN VOS THOM..PAHAWH HMONG SIGN VOS TSHAB CEEB
+16B44         ; STerm # Po       PAHAWH HMONG SIGN XAUS
+1BC9F         ; STerm # Po       DUPLOYAN PUNCTUATION CHINOOK FULL STOP
 
-# Total code points: 83
+# Total code points: 99
 
 # ================================================
 
@@ -1210,7 +1326,10 @@
 21D5..21F3    ; Pattern_Syntax # So  [31] UP DOWN DOUBLE ARROW..UP DOWN WHITE ARROW
 21F4..22FF    ; Pattern_Syntax # Sm [268] RIGHT ARROW WITH SMALL CIRCLE..Z NOTATION BAG MEMBERSHIP
 2300..2307    ; Pattern_Syntax # So   [8] DIAMETER SIGN..WAVY LINE
-2308..230B    ; Pattern_Syntax # Sm   [4] LEFT CEILING..RIGHT FLOOR
+2308          ; Pattern_Syntax # Ps       LEFT CEILING
+2309          ; Pattern_Syntax # Pe       RIGHT CEILING
+230A          ; Pattern_Syntax # Ps       LEFT FLOOR
+230B          ; Pattern_Syntax # Pe       RIGHT FLOOR
 230C..231F    ; Pattern_Syntax # So  [20] BOTTOM RIGHT CROP..BOTTOM RIGHT CORNER
 2320..2321    ; Pattern_Syntax # Sm   [2] TOP HALF INTEGRAL..BOTTOM HALF INTEGRAL
 2322..2328    ; Pattern_Syntax # So   [7] FROWN..KEYBOARD
@@ -1222,8 +1341,8 @@
 239B..23B3    ; Pattern_Syntax # Sm  [25] LEFT PARENTHESIS UPPER HOOK..SUMMATION BOTTOM
 23B4..23DB    ; Pattern_Syntax # So  [40] TOP SQUARE BRACKET..FUSE
 23DC..23E1    ; Pattern_Syntax # Sm   [6] TOP PARENTHESIS..BOTTOM TORTOISE SHELL BRACKET
-23E2..23F3    ; Pattern_Syntax # So  [18] WHITE TRAPEZIUM..HOURGLASS WITH FLOWING SAND
-23F4..23FF    ; Pattern_Syntax # Cn  [12] <reserved-23F4>..<reserved-23FF>
+23E2..23FA    ; Pattern_Syntax # So  [25] WHITE TRAPEZIUM..BLACK CIRCLE FOR RECORD
+23FB..23FF    ; Pattern_Syntax # Cn   [5] <reserved-23FB>..<reserved-23FF>
 2400..2426    ; Pattern_Syntax # So  [39] SYMBOL FOR NULL..SYMBOL FOR SUBSTITUTE FORM TWO
 2427..243F    ; Pattern_Syntax # Cn  [25] <reserved-2427>..<reserved-243F>
 2440..244A    ; Pattern_Syntax # So  [11] OCR HOOK..OCR DOUBLE BACKSLASH
@@ -1236,9 +1355,7 @@
 25F8..25FF    ; Pattern_Syntax # Sm   [8] UPPER LEFT TRIANGLE..LOWER RIGHT TRIANGLE
 2600..266E    ; Pattern_Syntax # So [111] BLACK SUN WITH RAYS..MUSIC NATURAL SIGN
 266F          ; Pattern_Syntax # Sm       MUSIC SHARP SIGN
-2670..26FF    ; Pattern_Syntax # So [144] WEST SYRIAC CROSS..WHITE FLAG WITH HORIZONTAL MIDDLE BLACK STRIPE
-2700          ; Pattern_Syntax # Cn       <reserved-2700>
-2701..2767    ; Pattern_Syntax # So [103] UPPER BLADE SCISSORS..ROTATED FLORAL HEART BULLET
+2670..2767    ; Pattern_Syntax # So [248] WEST SYRIAC CROSS..ROTATED FLORAL HEART BULLET
 2768          ; Pattern_Syntax # Ps       MEDIUM LEFT PARENTHESIS ORNAMENT
 2769          ; Pattern_Syntax # Pe       MEDIUM RIGHT PARENTHESIS ORNAMENT
 276A          ; Pattern_Syntax # Ps       MEDIUM FLATTENED LEFT PARENTHESIS ORNAMENT
@@ -1306,9 +1423,16 @@
 2B30..2B44    ; Pattern_Syntax # Sm  [21] LEFT ARROW WITH SMALL CIRCLE..RIGHTWARDS ARROW THROUGH SUPERSET
 2B45..2B46    ; Pattern_Syntax # So   [2] LEFTWARDS QUADRUPLE ARROW..RIGHTWARDS QUADRUPLE ARROW
 2B47..2B4C    ; Pattern_Syntax # Sm   [6] REVERSE TILDE OPERATOR ABOVE RIGHTWARDS ARROW..RIGHTWARDS ARROW ABOVE REVERSE TILDE OPERATOR
-2B4D..2B4F    ; Pattern_Syntax # Cn   [3] <reserved-2B4D>..<reserved-2B4F>
-2B50..2B59    ; Pattern_Syntax # So  [10] WHITE MEDIUM STAR..HEAVY CIRCLED SALTIRE
-2B5A..2BFF    ; Pattern_Syntax # Cn [166] <reserved-2B5A>..<reserved-2BFF>
+2B4D..2B73    ; Pattern_Syntax # So  [39] DOWNWARDS TRIANGLE-HEADED ZIGZAG ARROW..DOWNWARDS TRIANGLE-HEADED ARROW TO BAR
+2B74..2B75    ; Pattern_Syntax # Cn   [2] <reserved-2B74>..<reserved-2B75>
+2B76..2B95    ; Pattern_Syntax # So  [32] NORTH WEST TRIANGLE-HEADED ARROW TO BAR..RIGHTWARDS BLACK ARROW
+2B96..2B97    ; Pattern_Syntax # Cn   [2] <reserved-2B96>..<reserved-2B97>
+2B98..2BB9    ; Pattern_Syntax # So  [34] THREE-D TOP-LIGHTED LEFTWARDS EQUILATERAL ARROWHEAD..UP ARROWHEAD IN A RECTANGLE BOX
+2BBA..2BBC    ; Pattern_Syntax # Cn   [3] <reserved-2BBA>..<reserved-2BBC>
+2BBD..2BC8    ; Pattern_Syntax # So  [12] BALLOT BOX WITH LIGHT X..BLACK MEDIUM RIGHT-POINTING TRIANGLE CENTRED
+2BC9          ; Pattern_Syntax # Cn       <reserved-2BC9>
+2BCA..2BD1    ; Pattern_Syntax # So   [8] TOP HALF BLACK CIRCLE..UNCERTAINTY SIGN
+2BD2..2BFF    ; Pattern_Syntax # Cn  [46] <reserved-2BD2>..<reserved-2BFF>
 2E00..2E01    ; Pattern_Syntax # Po   [2] RIGHT ANGLE SUBSTITUTION MARKER..RIGHT ANGLE DOTTED SUBSTITUTION MARKER
 2E02          ; Pattern_Syntax # Pi       LEFT SUBSTITUTION BRACKET
 2E03          ; Pattern_Syntax # Pf       RIGHT SUBSTITUTION BRACKET
@@ -1342,7 +1466,11 @@
 2E2F          ; Pattern_Syntax # Lm       VERTICAL TILDE
 2E30..2E39    ; Pattern_Syntax # Po  [10] RING POINT..TOP HALF SECTION SIGN
 2E3A..2E3B    ; Pattern_Syntax # Pd   [2] TWO-EM DASH..THREE-EM DASH
-2E3C..2E7F    ; Pattern_Syntax # Cn  [68] <reserved-2E3C>..<reserved-2E7F>
+2E3C..2E3F    ; Pattern_Syntax # Po   [4] STENOGRAPHIC FULL STOP..CAPITULUM
+2E40          ; Pattern_Syntax # Pd       DOUBLE HYPHEN
+2E41          ; Pattern_Syntax # Po       REVERSED COMMA
+2E42          ; Pattern_Syntax # Ps       DOUBLE LOW-REVERSED-9 QUOTATION MARK
+2E43..2E7F    ; Pattern_Syntax # Cn  [61] <reserved-2E43>..<reserved-2E7F>
 3001..3003    ; Pattern_Syntax # Po   [3] IDEOGRAPHIC COMMA..DITTO MARK
 3008          ; Pattern_Syntax # Ps       LEFT ANGLE BRACKET
 3009          ; Pattern_Syntax # Pe       RIGHT ANGLE BRACKET
@@ -1368,8 +1496,8 @@
 301E..301F    ; Pattern_Syntax # Pe   [2] DOUBLE PRIME QUOTATION MARK..LOW DOUBLE PRIME QUOTATION MARK
 3020          ; Pattern_Syntax # So       POSTAL MARK FACE
 3030          ; Pattern_Syntax # Pd       WAVY DASH
-FD3E          ; Pattern_Syntax # Ps       ORNATE LEFT PARENTHESIS
-FD3F          ; Pattern_Syntax # Pe       ORNATE RIGHT PARENTHESIS
+FD3E          ; Pattern_Syntax # Pe       ORNATE LEFT PARENTHESIS
+FD3F          ; Pattern_Syntax # Ps       ORNATE RIGHT PARENTHESIS
 FE45..FE46    ; Pattern_Syntax # Po   [2] SESAME DOT..WHITE SESAME DOT
 
 # Total code points: 2760
--- a/jdk/make/data/unicodedata/Scripts.txt	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/make/data/unicodedata/Scripts.txt	Wed Jul 05 20:42:36 2017 +0200
@@ -1,8 +1,8 @@
-# Scripts-6.2.0.txt
-# Date: 2012-06-04, 17:21:29 GMT [MD]
+# Scripts-7.0.0.txt
+# Date: 2014-05-15, 00:11:35 GMT [MD]
 #
 # Unicode Character Database
-# Copyright (c) 1991-2012 Unicode, Inc.
+# Copyright (c) 1991-2014 Unicode, Inc.
 # For terms of use, see http://www.unicode.org/terms_of_use.html
 # For documentation, see http://www.unicode.org/reports/tr44/
 
@@ -83,8 +83,10 @@
 0385          ; Common # Sk       GREEK DIALYTIKA TONOS
 0387          ; Common # Po       GREEK ANO TELEIA
 0589          ; Common # Po       ARMENIAN FULL STOP
+0605          ; Common # Cf       ARABIC NUMBER MARK ABOVE
 060C          ; Common # Po       ARABIC COMMA
 061B          ; Common # Po       ARABIC SEMICOLON
+061C          ; Common # Cf       ARABIC LETTER MARK
 061F          ; Common # Po       ARABIC QUESTION MARK
 0640          ; Common # Lm       ARABIC TATWEEL
 0660..0669    ; Common # Nd  [10] ARABIC-INDIC DIGIT ZERO..ARABIC-INDIC DIGIT NINE
@@ -136,7 +138,7 @@
 2055..205E    ; Common # Po  [10] FLOWER PUNCTUATION MARK..VERTICAL FOUR DOTS
 205F          ; Common # Zs       MEDIUM MATHEMATICAL SPACE
 2060..2064    ; Common # Cf   [5] WORD JOINER..INVISIBLE PLUS
-206A..206F    ; Common # Cf   [6] INHIBIT SYMMETRIC SWAPPING..NOMINAL DIGIT SHAPES
+2066..206F    ; Common # Cf  [10] LEFT-TO-RIGHT ISOLATE..NOMINAL DIGIT SHAPES
 2070          ; Common # No       SUPERSCRIPT ZERO
 2074..2079    ; Common # No   [6] SUPERSCRIPT FOUR..SUPERSCRIPT NINE
 207A..207C    ; Common # Sm   [3] SUPERSCRIPT PLUS SIGN..SUPERSCRIPT EQUALS SIGN
@@ -146,7 +148,7 @@
 208A..208C    ; Common # Sm   [3] SUBSCRIPT PLUS SIGN..SUBSCRIPT EQUALS SIGN
 208D          ; Common # Ps       SUBSCRIPT LEFT PARENTHESIS
 208E          ; Common # Pe       SUBSCRIPT RIGHT PARENTHESIS
-20A0..20BA    ; Common # Sc  [27] EURO-CURRENCY SIGN..TURKISH LIRA SIGN
+20A0..20BD    ; Common # Sc  [30] EURO-CURRENCY SIGN..RUBLE SIGN
 2100..2101    ; Common # So   [2] ACCOUNT OF..ADDRESSED TO THE SUBJECT
 2102          ; Common # L&       DOUBLE-STRUCK CAPITAL C
 2103..2106    ; Common # So   [4] DEGREE CELSIUS..CADA UNA
@@ -200,7 +202,10 @@
 21D5..21F3    ; Common # So  [31] UP DOWN DOUBLE ARROW..UP DOWN WHITE ARROW
 21F4..22FF    ; Common # Sm [268] RIGHT ARROW WITH SMALL CIRCLE..Z NOTATION BAG MEMBERSHIP
 2300..2307    ; Common # So   [8] DIAMETER SIGN..WAVY LINE
-2308..230B    ; Common # Sm   [4] LEFT CEILING..RIGHT FLOOR
+2308          ; Common # Ps       LEFT CEILING
+2309          ; Common # Pe       RIGHT CEILING
+230A          ; Common # Ps       LEFT FLOOR
+230B          ; Common # Pe       RIGHT FLOOR
 230C..231F    ; Common # So  [20] BOTTOM RIGHT CROP..BOTTOM RIGHT CORNER
 2320..2321    ; Common # Sm   [2] TOP HALF INTEGRAL..BOTTOM HALF INTEGRAL
 2322..2328    ; Common # So   [7] FROWN..KEYBOARD
@@ -212,7 +217,7 @@
 239B..23B3    ; Common # Sm  [25] LEFT PARENTHESIS UPPER HOOK..SUMMATION BOTTOM
 23B4..23DB    ; Common # So  [40] TOP SQUARE BRACKET..FUSE
 23DC..23E1    ; Common # Sm   [6] TOP PARENTHESIS..BOTTOM TORTOISE SHELL BRACKET
-23E2..23F3    ; Common # So  [18] WHITE TRAPEZIUM..HOURGLASS WITH FLOWING SAND
+23E2..23FA    ; Common # So  [25] WHITE TRAPEZIUM..BLACK CIRCLE FOR RECORD
 2400..2426    ; Common # So  [39] SYMBOL FOR NULL..SYMBOL FOR SUBSTITUTE FORM TWO
 2440..244A    ; Common # So  [11] OCR HOOK..OCR DOUBLE BACKSLASH
 2460..249B    ; Common # No  [60] CIRCLED DIGIT ONE..NUMBER TWENTY FULL STOP
@@ -226,8 +231,7 @@
 25F8..25FF    ; Common # Sm   [8] UPPER LEFT TRIANGLE..LOWER RIGHT TRIANGLE
 2600..266E    ; Common # So [111] BLACK SUN WITH RAYS..MUSIC NATURAL SIGN
 266F          ; Common # Sm       MUSIC SHARP SIGN
-2670..26FF    ; Common # So [144] WEST SYRIAC CROSS..WHITE FLAG WITH HORIZONTAL MIDDLE BLACK STRIPE
-2701..2767    ; Common # So [103] UPPER BLADE SCISSORS..ROTATED FLORAL HEART BULLET
+2670..2767    ; Common # So [248] WEST SYRIAC CROSS..ROTATED FLORAL HEART BULLET
 2768          ; Common # Ps       MEDIUM LEFT PARENTHESIS ORNAMENT
 2769          ; Common # Pe       MEDIUM RIGHT PARENTHESIS ORNAMENT
 276A          ; Common # Ps       MEDIUM FLATTENED LEFT PARENTHESIS ORNAMENT
@@ -295,7 +299,11 @@
 2B30..2B44    ; Common # Sm  [21] LEFT ARROW WITH SMALL CIRCLE..RIGHTWARDS ARROW THROUGH SUPERSET
 2B45..2B46    ; Common # So   [2] LEFTWARDS QUADRUPLE ARROW..RIGHTWARDS QUADRUPLE ARROW
 2B47..2B4C    ; Common # Sm   [6] REVERSE TILDE OPERATOR ABOVE RIGHTWARDS ARROW..RIGHTWARDS ARROW ABOVE REVERSE TILDE OPERATOR
-2B50..2B59    ; Common # So  [10] WHITE MEDIUM STAR..HEAVY CIRCLED SALTIRE
+2B4D..2B73    ; Common # So  [39] DOWNWARDS TRIANGLE-HEADED ZIGZAG ARROW..DOWNWARDS TRIANGLE-HEADED ARROW TO BAR
+2B76..2B95    ; Common # So  [32] NORTH WEST TRIANGLE-HEADED ARROW TO BAR..RIGHTWARDS BLACK ARROW
+2B98..2BB9    ; Common # So  [34] THREE-D TOP-LIGHTED LEFTWARDS EQUILATERAL ARROWHEAD..UP ARROWHEAD IN A RECTANGLE BOX
+2BBD..2BC8    ; Common # So  [12] BALLOT BOX WITH LIGHT X..BLACK MEDIUM RIGHT-POINTING TRIANGLE CENTRED
+2BCA..2BD1    ; Common # So   [8] TOP HALF BLACK CIRCLE..UNCERTAINTY SIGN
 2E00..2E01    ; Common # Po   [2] RIGHT ANGLE SUBSTITUTION MARKER..RIGHT ANGLE DOTTED SUBSTITUTION MARKER
 2E02          ; Common # Pi       LEFT SUBSTITUTION BRACKET
 2E03          ; Common # Pf       RIGHT SUBSTITUTION BRACKET
@@ -329,6 +337,10 @@
 2E2F          ; Common # Lm       VERTICAL TILDE
 2E30..2E39    ; Common # Po  [10] RING POINT..TOP HALF SECTION SIGN
 2E3A..2E3B    ; Common # Pd   [2] TWO-EM DASH..THREE-EM DASH
+2E3C..2E3F    ; Common # Po   [4] STENOGRAPHIC FULL STOP..CAPITULUM
+2E40          ; Common # Pd       DOUBLE HYPHEN
+2E41          ; Common # Po       REVERSED COMMA
+2E42          ; Common # Ps       DOUBLE LOW-REVERSED-9 QUOTATION MARK
 2FF0..2FFB    ; Common # So  [12] IDEOGRAPHIC DESCRIPTION CHARACTER LEFT TO RIGHT..IDEOGRAPHIC DESCRIPTION CHARACTER OVERLAID
 3000          ; Common # Zs       IDEOGRAPHIC SPACE
 3001..3003    ; Common # Po   [3] IDEOGRAPHIC COMMA..DITTO MARK
@@ -392,9 +404,11 @@
 A836..A837    ; Common # So   [2] NORTH INDIC QUARTER MARK..NORTH INDIC PLACEHOLDER MARK
 A838          ; Common # Sc       NORTH INDIC RUPEE MARK
 A839          ; Common # So       NORTH INDIC QUANTITY MARK
-FD3E          ; Common # Ps       ORNATE LEFT PARENTHESIS
-FD3F          ; Common # Pe       ORNATE RIGHT PARENTHESIS
-FDFD          ; Common # So       ARABIC LIGATURE BISMILLAH AR-RAHMAN AR-RAHEEM
+A92E          ; Common # Po       KAYAH LI SIGN CWI
+A9CF          ; Common # Lm       JAVANESE PANGRANGKEP
+AB5B          ; Common # Sk       MODIFIER BREVE WITH INVERTED BREVE
+FD3E          ; Common # Pe       ORNATE LEFT PARENTHESIS
+FD3F          ; Common # Ps       ORNATE RIGHT PARENTHESIS
 FE10..FE16    ; Common # Po   [7] PRESENTATION FORM FOR VERTICAL COMMA..PRESENTATION FORM FOR VERTICAL QUESTION MARK
 FE17          ; Common # Ps       PRESENTATION FORM FOR VERTICAL LEFT WHITE LENTICULAR BRACKET
 FE18          ; Common # Pe       PRESENTATION FORM FOR VERTICAL RIGHT WHITE LENTICULAR BRAKCET
@@ -487,6 +501,8 @@
 10137..1013F  ; Common # So   [9] AEGEAN WEIGHT BASE UNIT..AEGEAN MEASURE THIRD SUBUNIT
 10190..1019B  ; Common # So  [12] ROMAN SEXTANS SIGN..ROMAN CENTURIAL SIGN
 101D0..101FC  ; Common # So  [45] PHAISTOS DISC SIGN PEDESTRIAN..PHAISTOS DISC SIGN WAVY BAND
+102E1..102FB  ; Common # No  [27] COPTIC EPACT DIGIT ONE..COPTIC EPACT NUMBER NINE HUNDRED
+1BCA0..1BCA3  ; Common # Cf   [4] SHORTHAND FORMAT LETTER OVERLAP..SHORTHAND FORMAT UP STEP
 1D000..1D0F5  ; Common # So [246] BYZANTINE MUSICAL SYMBOL PSILI..BYZANTINE MUSICAL SYMBOL GORGON NEO KATO
 1D100..1D126  ; Common # So  [39] MUSICAL SYMBOL SINGLE BARLINE..MUSICAL SYMBOL DRUM CLEF-2
 1D129..1D164  ; Common # So  [60] MUSICAL SYMBOL MULTIPLE MEASURE REST..MUSICAL SYMBOL ONE HUNDRED TWENTY-EIGHTH NOTE
@@ -543,10 +559,10 @@
 1F000..1F02B  ; Common # So  [44] MAHJONG TILE EAST WIND..MAHJONG TILE BACK
 1F030..1F093  ; Common # So [100] DOMINO TILE HORIZONTAL BACK..DOMINO TILE VERTICAL-06-06
 1F0A0..1F0AE  ; Common # So  [15] PLAYING CARD BACK..PLAYING CARD KING OF SPADES
-1F0B1..1F0BE  ; Common # So  [14] PLAYING CARD ACE OF HEARTS..PLAYING CARD KING OF HEARTS
+1F0B1..1F0BF  ; Common # So  [15] PLAYING CARD ACE OF HEARTS..PLAYING CARD RED JOKER
 1F0C1..1F0CF  ; Common # So  [15] PLAYING CARD ACE OF DIAMONDS..PLAYING CARD BLACK JOKER
-1F0D1..1F0DF  ; Common # So  [15] PLAYING CARD ACE OF CLUBS..PLAYING CARD WHITE JOKER
-1F100..1F10A  ; Common # No  [11] DIGIT ZERO FULL STOP..DIGIT NINE COMMA
+1F0D1..1F0F5  ; Common # So  [37] PLAYING CARD ACE OF CLUBS..PLAYING CARD TRUMP-21
+1F100..1F10C  ; Common # No  [13] DIGIT ZERO FULL STOP..DINGBAT NEGATIVE CIRCLED SANS-SERIF DIGIT ZERO
 1F110..1F12E  ; Common # So  [31] PARENTHESIZED LATIN CAPITAL LETTER A..CIRCLED WZ
 1F130..1F16B  ; Common # So  [60] SQUARED LATIN CAPITAL LETTER A..RAISED MD SIGN
 1F170..1F19A  ; Common # So  [43] NEGATIVE SQUARED LATIN CAPITAL LETTER A..SQUARED VS
@@ -555,28 +571,29 @@
 1F210..1F23A  ; Common # So  [43] SQUARED CJK UNIFIED IDEOGRAPH-624B..SQUARED CJK UNIFIED IDEOGRAPH-55B6
 1F240..1F248  ; Common # So   [9] TORTOISE SHELL BRACKETED CJK UNIFIED IDEOGRAPH-672C..TORTOISE SHELL BRACKETED CJK UNIFIED IDEOGRAPH-6557
 1F250..1F251  ; Common # So   [2] CIRCLED IDEOGRAPH ADVANTAGE..CIRCLED IDEOGRAPH ACCEPT
-1F300..1F320  ; Common # So  [33] CYCLONE..SHOOTING STAR
-1F330..1F335  ; Common # So   [6] CHESTNUT..CACTUS
-1F337..1F37C  ; Common # So  [70] TULIP..BABY BOTTLE
-1F380..1F393  ; Common # So  [20] RIBBON..GRADUATION CAP
-1F3A0..1F3C4  ; Common # So  [37] CAROUSEL HORSE..SURFER
-1F3C6..1F3CA  ; Common # So   [5] TROPHY..SWIMMER
-1F3E0..1F3F0  ; Common # So  [17] HOUSE BUILDING..EUROPEAN CASTLE
-1F400..1F43E  ; Common # So  [63] RAT..PAW PRINTS
-1F440         ; Common # So       EYES
-1F442..1F4F7  ; Common # So [182] EAR..CAMERA
-1F4F9..1F4FC  ; Common # So   [4] VIDEO CAMERA..VIDEOCASSETTE
-1F500..1F53D  ; Common # So  [62] TWISTED RIGHTWARDS ARROWS..DOWN-POINTING SMALL RED TRIANGLE
-1F540..1F543  ; Common # So   [4] CIRCLED CROSS POMMEE..NOTCHED LEFT SEMICIRCLE WITH THREE DOTS
-1F550..1F567  ; Common # So  [24] CLOCK FACE ONE OCLOCK..CLOCK FACE TWELVE-THIRTY
-1F5FB..1F640  ; Common # So  [70] MOUNT FUJI..WEARY CAT FACE
-1F645..1F64F  ; Common # So  [11] FACE WITH NO GOOD GESTURE..PERSON WITH FOLDED HANDS
-1F680..1F6C5  ; Common # So  [70] ROCKET..LEFT LUGGAGE
+1F300..1F32C  ; Common # So  [45] CYCLONE..WIND BLOWING FACE
+1F330..1F37D  ; Common # So  [78] CHESTNUT..FORK AND KNIFE WITH PLATE
+1F380..1F3CE  ; Common # So  [79] RIBBON..RACING CAR
+1F3D4..1F3F7  ; Common # So  [36] SNOW CAPPED MOUNTAIN..LABEL
+1F400..1F4FE  ; Common # So [255] RAT..PORTABLE STEREO
+1F500..1F54A  ; Common # So  [75] TWISTED RIGHTWARDS ARROWS..DOVE OF PEACE
+1F550..1F579  ; Common # So  [42] CLOCK FACE ONE OCLOCK..JOYSTICK
+1F57B..1F5A3  ; Common # So  [41] LEFT HAND TELEPHONE RECEIVER..BLACK DOWN POINTING BACKHAND INDEX
+1F5A5..1F642  ; Common # So [158] DESKTOP COMPUTER..SLIGHTLY SMILING FACE
+1F645..1F6CF  ; Common # So [139] FACE WITH NO GOOD GESTURE..BED
+1F6E0..1F6EC  ; Common # So  [13] HAMMER AND WRENCH..AIRPLANE ARRIVING
+1F6F0..1F6F3  ; Common # So   [4] SATELLITE..PASSENGER SHIP
 1F700..1F773  ; Common # So [116] ALCHEMICAL SYMBOL FOR QUINTESSENCE..ALCHEMICAL SYMBOL FOR HALF OUNCE
+1F780..1F7D4  ; Common # So  [85] BLACK LEFT-POINTING ISOSCELES RIGHT TRIANGLE..HEAVY TWELVE POINTED PINWHEEL STAR
+1F800..1F80B  ; Common # So  [12] LEFTWARDS ARROW WITH SMALL TRIANGLE ARROWHEAD..DOWNWARDS ARROW WITH LARGE TRIANGLE ARROWHEAD
+1F810..1F847  ; Common # So  [56] LEFTWARDS ARROW WITH SMALL EQUILATERAL ARROWHEAD..DOWNWARDS HEAVY ARROW
+1F850..1F859  ; Common # So  [10] LEFTWARDS SANS-SERIF ARROW..UP DOWN SANS-SERIF ARROW
+1F860..1F887  ; Common # So  [40] WIDE-HEADED LEFTWARDS LIGHT BARB ARROW..WIDE-HEADED SOUTH WEST VERY HEAVY BARB ARROW
+1F890..1F8AD  ; Common # So  [30] LEFTWARDS TRIANGLE ARROWHEAD..WHITE ARROW SHAFT WIDTH TWO THIRDS
 E0001         ; Common # Cf       LANGUAGE TAG
 E0020..E007F  ; Common # Cf  [96] TAG SPACE..CANCEL TAG
 
-# Total code points: 6413
+# Total code points: 7129
 
 # ================================================
 
@@ -618,16 +635,20 @@
 A770          ; Latin # Lm       MODIFIER LETTER US
 A771..A787    ; Latin # L&  [23] LATIN SMALL LETTER DUM..LATIN SMALL LETTER INSULAR T
 A78B..A78E    ; Latin # L&   [4] LATIN CAPITAL LETTER SALTILLO..LATIN SMALL LETTER L WITH RETROFLEX HOOK AND BELT
-A790..A793    ; Latin # L&   [4] LATIN CAPITAL LETTER N WITH DESCENDER..LATIN SMALL LETTER C WITH BAR
-A7A0..A7AA    ; Latin # L&  [11] LATIN CAPITAL LETTER G WITH OBLIQUE STROKE..LATIN CAPITAL LETTER H WITH HOOK
+A790..A7AD    ; Latin # L&  [30] LATIN CAPITAL LETTER N WITH DESCENDER..LATIN CAPITAL LETTER L WITH BELT
+A7B0..A7B1    ; Latin # L&   [2] LATIN CAPITAL LETTER TURNED K..LATIN CAPITAL LETTER TURNED T
+A7F7          ; Latin # Lo       LATIN EPIGRAPHIC LETTER SIDEWAYS I
 A7F8..A7F9    ; Latin # Lm   [2] MODIFIER LETTER CAPITAL H WITH STROKE..MODIFIER LETTER SMALL LIGATURE OE
 A7FA          ; Latin # L&       LATIN LETTER SMALL CAPITAL TURNED M
 A7FB..A7FF    ; Latin # Lo   [5] LATIN EPIGRAPHIC LETTER REVERSED F..LATIN EPIGRAPHIC LETTER ARCHAIC M
+AB30..AB5A    ; Latin # L&  [43] LATIN SMALL LETTER BARRED ALPHA..LATIN SMALL LETTER Y WITH SHORT RIGHT LEG
+AB5C..AB5F    ; Latin # Lm   [4] MODIFIER LETTER SMALL HENG..MODIFIER LETTER SMALL U WITH LEFT HOOK
+AB64          ; Latin # L&       LATIN SMALL LETTER INVERTED ALPHA
 FB00..FB06    ; Latin # L&   [7] LATIN SMALL LIGATURE FF..LATIN SMALL LIGATURE ST
 FF21..FF3A    ; Latin # L&  [26] FULLWIDTH LATIN CAPITAL LETTER A..FULLWIDTH LATIN CAPITAL LETTER Z
 FF41..FF5A    ; Latin # L&  [26] FULLWIDTH LATIN SMALL LETTER A..FULLWIDTH LATIN SMALL LETTER Z
 
-# Total code points: 1272
+# Total code points: 1338
 
 # ================================================
 
@@ -636,6 +657,7 @@
 0376..0377    ; Greek # L&   [2] GREEK CAPITAL LETTER PAMPHYLIAN DIGAMMA..GREEK SMALL LETTER PAMPHYLIAN DIGAMMA
 037A          ; Greek # Lm       GREEK YPOGEGRAMMENI
 037B..037D    ; Greek # L&   [3] GREEK SMALL REVERSED LUNATE SIGMA SYMBOL..GREEK SMALL REVERSED DOTTED LUNATE SIGMA SYMBOL
+037F          ; Greek # L&       GREEK CAPITAL LETTER YOT
 0384          ; Greek # Sk       GREEK TONOS
 0386          ; Greek # L&       GREEK CAPITAL LETTER ALPHA WITH TONOS
 0388..038A    ; Greek # L&   [3] GREEK CAPITAL LETTER EPSILON WITH TONOS..GREEK CAPITAL LETTER IOTA WITH TONOS
@@ -675,15 +697,18 @@
 1FF6..1FFC    ; Greek # L&   [7] GREEK SMALL LETTER OMEGA WITH PERISPOMENI..GREEK CAPITAL LETTER OMEGA WITH PROSGEGRAMMENI
 1FFD..1FFE    ; Greek # Sk   [2] GREEK OXIA..GREEK DASIA
 2126          ; Greek # L&       OHM SIGN
+AB65          ; Greek # L&       GREEK LETTER SMALL CAPITAL OMEGA
 10140..10174  ; Greek # Nl  [53] GREEK ACROPHONIC ATTIC ONE QUARTER..GREEK ACROPHONIC STRATIAN FIFTY MNAS
 10175..10178  ; Greek # No   [4] GREEK ONE HALF SIGN..GREEK THREE QUARTERS SIGN
 10179..10189  ; Greek # So  [17] GREEK YEAR SIGN..GREEK TRYBLION BASE SIGN
-1018A         ; Greek # No       GREEK ZERO SIGN
+1018A..1018B  ; Greek # No   [2] GREEK ZERO SIGN..GREEK ONE QUARTER SIGN
+1018C         ; Greek # So       GREEK SINUSOID SIGN
+101A0         ; Greek # So       GREEK SYMBOL TAU RHO
 1D200..1D241  ; Greek # So  [66] GREEK VOCAL NOTATION SYMBOL-1..GREEK INSTRUMENTAL NOTATION SYMBOL-54
 1D242..1D244  ; Greek # Mn   [3] COMBINING GREEK MUSICAL TRISEME..COMBINING GREEK MUSICAL PENTASEME
 1D245         ; Greek # So       GREEK MUSICAL LEIMMA
 
-# Total code points: 511
+# Total code points: 516
 
 # ================================================
 
@@ -692,7 +717,7 @@
 0483..0484    ; Cyrillic # Mn   [2] COMBINING CYRILLIC TITLO..COMBINING CYRILLIC PALATALIZATION
 0487          ; Cyrillic # Mn       COMBINING CYRILLIC POKRYTIE
 0488..0489    ; Cyrillic # Me   [2] COMBINING CYRILLIC HUNDRED THOUSANDS SIGN..COMBINING CYRILLIC MILLIONS SIGN
-048A..0527    ; Cyrillic # L& [158] CYRILLIC CAPITAL LETTER SHORT I WITH TAIL..CYRILLIC SMALL LETTER SHHA WITH DESCENDER
+048A..052F    ; Cyrillic # L& [166] CYRILLIC CAPITAL LETTER SHORT I WITH TAIL..CYRILLIC SMALL LETTER EL WITH DESCENDER
 1D2B          ; Cyrillic # L&       CYRILLIC LETTER SMALL CAPITAL EL
 1D78          ; Cyrillic # Lm       MODIFIER LETTER CYRILLIC EN
 2DE0..2DFF    ; Cyrillic # Mn  [32] COMBINING CYRILLIC LETTER BE..COMBINING CYRILLIC LETTER IOTIFIED BIG YUS
@@ -704,10 +729,11 @@
 A674..A67D    ; Cyrillic # Mn  [10] COMBINING CYRILLIC LETTER UKRAINIAN IE..COMBINING CYRILLIC PAYEROK
 A67E          ; Cyrillic # Po       CYRILLIC KAVYKA
 A67F          ; Cyrillic # Lm       CYRILLIC PAYEROK
-A680..A697    ; Cyrillic # L&  [24] CYRILLIC CAPITAL LETTER DWE..CYRILLIC SMALL LETTER SHWE
+A680..A69B    ; Cyrillic # L&  [28] CYRILLIC CAPITAL LETTER DWE..CYRILLIC SMALL LETTER CROSSED O
+A69C..A69D    ; Cyrillic # Lm   [2] MODIFIER LETTER CYRILLIC HARD SIGN..MODIFIER LETTER CYRILLIC SOFT SIGN
 A69F          ; Cyrillic # Mn       COMBINING CYRILLIC LETTER IOTIFIED E
 
-# Total code points: 417
+# Total code points: 431
 
 # ================================================
 
@@ -716,10 +742,11 @@
 055A..055F    ; Armenian # Po   [6] ARMENIAN APOSTROPHE..ARMENIAN ABBREVIATION MARK
 0561..0587    ; Armenian # L&  [39] ARMENIAN SMALL LETTER AYB..ARMENIAN SMALL LIGATURE ECH YIWN
 058A          ; Armenian # Pd       ARMENIAN HYPHEN
+058D..058E    ; Armenian # So   [2] RIGHT-FACING ARMENIAN ETERNITY SIGN..LEFT-FACING ARMENIAN ETERNITY SIGN
 058F          ; Armenian # Sc       ARMENIAN DRAM SIGN
 FB13..FB17    ; Armenian # L&   [5] ARMENIAN SMALL LIGATURE MEN NOW..ARMENIAN SMALL LIGATURE MEN XEH
 
-# Total code points: 91
+# Total code points: 93
 
 # ================================================
 
@@ -779,9 +806,8 @@
 06FD..06FE    ; Arabic # So   [2] ARABIC SIGN SINDHI AMPERSAND..ARABIC SIGN SINDHI POSTPOSITION MEN
 06FF          ; Arabic # Lo       ARABIC LETTER HEH WITH INVERTED V
 0750..077F    ; Arabic # Lo  [48] ARABIC LETTER BEH WITH THREE DOTS HORIZONTALLY BELOW..ARABIC LETTER KAF WITH TWO DOTS ABOVE
-08A0          ; Arabic # Lo       ARABIC LETTER BEH WITH SMALL V BELOW
-08A2..08AC    ; Arabic # Lo  [11] ARABIC LETTER JEEM WITH TWO DOTS ABOVE..ARABIC LETTER ROHINGYA YEH
-08E4..08FE    ; Arabic # Mn  [27] ARABIC CURLY FATHA..ARABIC DAMMA WITH DOT
+08A0..08B2    ; Arabic # Lo  [19] ARABIC LETTER BEH WITH SMALL V BELOW..ARABIC LETTER ZAIN WITH INVERTED V ABOVE
+08E4..08FF    ; Arabic # Mn  [28] ARABIC CURLY FATHA..ARABIC MARK SIDEWAYS NOON GHUNNA
 FB50..FBB1    ; Arabic # Lo  [98] ARABIC LETTER ALEF WASLA ISOLATED FORM..ARABIC LETTER YEH BARREE WITH HAMZA ABOVE FINAL FORM
 FBB2..FBC1    ; Arabic # Sk  [16] ARABIC SYMBOL DOT ABOVE..ARABIC SYMBOL SMALL TAH BELOW
 FBD3..FD3D    ; Arabic # Lo [363] ARABIC LETTER NG ISOLATED FORM..ARABIC LIGATURE ALEF WITH FATHATAN ISOLATED FORM
@@ -789,6 +815,7 @@
 FD92..FDC7    ; Arabic # Lo  [54] ARABIC LIGATURE MEEM WITH JEEM WITH KHAH INITIAL FORM..ARABIC LIGATURE NOON WITH JEEM WITH YEH FINAL FORM
 FDF0..FDFB    ; Arabic # Lo  [12] ARABIC LIGATURE SALLA USED AS KORANIC STOP SIGN ISOLATED FORM..ARABIC LIGATURE JALLAJALALOUHOU
 FDFC          ; Arabic # Sc       RIAL SIGN
+FDFD          ; Arabic # So       ARABIC LIGATURE BISMILLAH AR-RAHMAN AR-RAHEEM
 FE70..FE74    ; Arabic # Lo   [5] ARABIC FATHATAN ISOLATED FORM..ARABIC KASRATAN ISOLATED FORM
 FE76..FEFC    ; Arabic # Lo [135] ARABIC FATHA ISOLATED FORM..ARABIC LIGATURE LAM WITH ALEF FINAL FORM
 10E60..10E7E  ; Arabic # No  [31] RUMI DIGIT ONE..RUMI FRACTION TWO THIRDS
@@ -827,7 +854,7 @@
 1EEAB..1EEBB  ; Arabic # Lo  [17] ARABIC MATHEMATICAL DOUBLE-STRUCK LAM..ARABIC MATHEMATICAL DOUBLE-STRUCK GHAIN
 1EEF0..1EEF1  ; Arabic # Sm   [2] ARABIC MATHEMATICAL OPERATOR MEEM WITH HAH WITH TATWEEL..ARABIC MATHEMATICAL OPERATOR HAH WITH DAL
 
-# Total code points: 1235
+# Total code points: 1244
 
 # ================================================
 
@@ -870,17 +897,17 @@
 0966..096F    ; Devanagari # Nd  [10] DEVANAGARI DIGIT ZERO..DEVANAGARI DIGIT NINE
 0970          ; Devanagari # Po       DEVANAGARI ABBREVIATION SIGN
 0971          ; Devanagari # Lm       DEVANAGARI SIGN HIGH SPACING DOT
-0972..0977    ; Devanagari # Lo   [6] DEVANAGARI LETTER CANDRA A..DEVANAGARI LETTER UUE
-0979..097F    ; Devanagari # Lo   [7] DEVANAGARI LETTER ZHA..DEVANAGARI LETTER BBA
+0972..097F    ; Devanagari # Lo  [14] DEVANAGARI LETTER CANDRA A..DEVANAGARI LETTER BBA
 A8E0..A8F1    ; Devanagari # Mn  [18] COMBINING DEVANAGARI DIGIT ZERO..COMBINING DEVANAGARI SIGN AVAGRAHA
 A8F2..A8F7    ; Devanagari # Lo   [6] DEVANAGARI SIGN SPACING CANDRABINDU..DEVANAGARI SIGN CANDRABINDU AVAGRAHA
 A8F8..A8FA    ; Devanagari # Po   [3] DEVANAGARI SIGN PUSHPIKA..DEVANAGARI CARET
 A8FB          ; Devanagari # Lo       DEVANAGARI HEADSTROKE
 
-# Total code points: 151
+# Total code points: 152
 
 # ================================================
 
+0980          ; Bengali # Lo       BENGALI ANJI
 0981          ; Bengali # Mn       BENGALI SIGN CANDRABINDU
 0982..0983    ; Bengali # Mc   [2] BENGALI SIGN ANUSVARA..BENGALI SIGN VISARGA
 0985..098C    ; Bengali # Lo   [8] BENGALI LETTER A..BENGALI LETTER VOCALIC L
@@ -908,7 +935,7 @@
 09FA          ; Bengali # So       BENGALI ISSHAR
 09FB          ; Bengali # Sc       BENGALI GANDA MARK
 
-# Total code points: 92
+# Total code points: 93
 
 # ================================================
 
@@ -1025,12 +1052,12 @@
 
 # ================================================
 
+0C00          ; Telugu # Mn       TELUGU SIGN COMBINING CANDRABINDU ABOVE
 0C01..0C03    ; Telugu # Mc   [3] TELUGU SIGN CANDRABINDU..TELUGU SIGN VISARGA
 0C05..0C0C    ; Telugu # Lo   [8] TELUGU LETTER A..TELUGU LETTER VOCALIC L
 0C0E..0C10    ; Telugu # Lo   [3] TELUGU LETTER E..TELUGU LETTER AI
 0C12..0C28    ; Telugu # Lo  [23] TELUGU LETTER O..TELUGU LETTER NA
-0C2A..0C33    ; Telugu # Lo  [10] TELUGU LETTER PA..TELUGU LETTER LLA
-0C35..0C39    ; Telugu # Lo   [5] TELUGU LETTER VA..TELUGU LETTER HA
+0C2A..0C39    ; Telugu # Lo  [16] TELUGU LETTER PA..TELUGU LETTER HA
 0C3D          ; Telugu # Lo       TELUGU SIGN AVAGRAHA
 0C3E..0C40    ; Telugu # Mn   [3] TELUGU VOWEL SIGN AA..TELUGU VOWEL SIGN II
 0C41..0C44    ; Telugu # Mc   [4] TELUGU VOWEL SIGN U..TELUGU VOWEL SIGN VOCALIC RR
@@ -1044,10 +1071,11 @@
 0C78..0C7E    ; Telugu # No   [7] TELUGU FRACTION DIGIT ZERO FOR ODD POWERS OF FOUR..TELUGU FRACTION DIGIT THREE FOR EVEN POWERS OF FOUR
 0C7F          ; Telugu # So       TELUGU SIGN TUUMU
 
-# Total code points: 93
+# Total code points: 95
 
 # ================================================
 
+0C81          ; Kannada # Mn       KANNADA SIGN CANDRABINDU
 0C82..0C83    ; Kannada # Mc   [2] KANNADA SIGN ANUSVARA..KANNADA SIGN VISARGA
 0C85..0C8C    ; Kannada # Lo   [8] KANNADA LETTER A..KANNADA LETTER VOCALIC L
 0C8E..0C90    ; Kannada # Lo   [3] KANNADA LETTER E..KANNADA LETTER AI
@@ -1070,10 +1098,11 @@
 0CE6..0CEF    ; Kannada # Nd  [10] KANNADA DIGIT ZERO..KANNADA DIGIT NINE
 0CF1..0CF2    ; Kannada # Lo   [2] KANNADA SIGN JIHVAMULIYA..KANNADA SIGN UPADHMANIYA
 
-# Total code points: 86
+# Total code points: 87
 
 # ================================================
 
+0D01          ; Malayalam # Mn       MALAYALAM SIGN CANDRABINDU
 0D02..0D03    ; Malayalam # Mc   [2] MALAYALAM SIGN ANUSVARA..MALAYALAM SIGN VISARGA
 0D05..0D0C    ; Malayalam # Lo   [8] MALAYALAM LETTER A..MALAYALAM LETTER VOCALIC L
 0D0E..0D10    ; Malayalam # Lo   [3] MALAYALAM LETTER E..MALAYALAM LETTER AI
@@ -1093,7 +1122,7 @@
 0D79          ; Malayalam # So       MALAYALAM DATE MARK
 0D7A..0D7F    ; Malayalam # Lo   [6] MALAYALAM LETTER CHILLU NN..MALAYALAM LETTER CHILLU K
 
-# Total code points: 98
+# Total code points: 99
 
 # ================================================
 
@@ -1108,10 +1137,12 @@
 0DD2..0DD4    ; Sinhala # Mn   [3] SINHALA VOWEL SIGN KETTI IS-PILLA..SINHALA VOWEL SIGN KETTI PAA-PILLA
 0DD6          ; Sinhala # Mn       SINHALA VOWEL SIGN DIGA PAA-PILLA
 0DD8..0DDF    ; Sinhala # Mc   [8] SINHALA VOWEL SIGN GAETTA-PILLA..SINHALA VOWEL SIGN GAYANUKITTA
+0DE6..0DEF    ; Sinhala # Nd  [10] SINHALA LITH DIGIT ZERO..SINHALA LITH DIGIT NINE
 0DF2..0DF3    ; Sinhala # Mc   [2] SINHALA VOWEL SIGN DIGA GAETTA-PILLA..SINHALA VOWEL SIGN DIGA GAYANUKITTA
 0DF4          ; Sinhala # Po       SINHALA PUNCTUATION KUNDDALIYA
+111E1..111F4  ; Sinhala # No  [20] SINHALA ARCHAIC DIGIT ONE..SINHALA ARCHAIC NUMBER ONE THOUSAND
 
-# Total code points: 80
+# Total code points: 110
 
 # ================================================
 
@@ -1234,14 +1265,23 @@
 109A..109C    ; Myanmar # Mc   [3] MYANMAR SIGN KHAMTI TONE-1..MYANMAR VOWEL SIGN AITON A
 109D          ; Myanmar # Mn       MYANMAR VOWEL SIGN AITON AI
 109E..109F    ; Myanmar # So   [2] MYANMAR SYMBOL SHAN ONE..MYANMAR SYMBOL SHAN EXCLAMATION
+A9E0..A9E4    ; Myanmar # Lo   [5] MYANMAR LETTER SHAN GHA..MYANMAR LETTER SHAN BHA
+A9E5          ; Myanmar # Mn       MYANMAR SIGN SHAN SAW
+A9E6          ; Myanmar # Lm       MYANMAR MODIFIER LETTER SHAN REDUPLICATION
+A9E7..A9EF    ; Myanmar # Lo   [9] MYANMAR LETTER TAI LAING NYA..MYANMAR LETTER TAI LAING NNA
+A9F0..A9F9    ; Myanmar # Nd  [10] MYANMAR TAI LAING DIGIT ZERO..MYANMAR TAI LAING DIGIT NINE
+A9FA..A9FE    ; Myanmar # Lo   [5] MYANMAR LETTER TAI LAING LLA..MYANMAR LETTER TAI LAING BHA
 AA60..AA6F    ; Myanmar # Lo  [16] MYANMAR LETTER KHAMTI GA..MYANMAR LETTER KHAMTI FA
 AA70          ; Myanmar # Lm       MYANMAR MODIFIER LETTER KHAMTI REDUPLICATION
 AA71..AA76    ; Myanmar # Lo   [6] MYANMAR LETTER KHAMTI XA..MYANMAR LOGOGRAM KHAMTI HM
 AA77..AA79    ; Myanmar # So   [3] MYANMAR SYMBOL AITON EXCLAMATION..MYANMAR SYMBOL AITON TWO
 AA7A          ; Myanmar # Lo       MYANMAR LETTER AITON RA
 AA7B          ; Myanmar # Mc       MYANMAR SIGN PAO KAREN TONE
+AA7C          ; Myanmar # Mn       MYANMAR SIGN TAI LAING TONE-2
+AA7D          ; Myanmar # Mc       MYANMAR SIGN TAI LAING TONE-5
+AA7E..AA7F    ; Myanmar # Lo   [2] MYANMAR LETTER SHWE PALAUNG CHA..MYANMAR LETTER SHWE PALAUNG SHA
 
-# Total code points: 188
+# Total code points: 223
 
 # ================================================
 
@@ -1345,8 +1385,9 @@
 
 16A0..16EA    ; Runic # Lo  [75] RUNIC LETTER FEHU FEOH FE F..RUNIC LETTER X
 16EE..16F0    ; Runic # Nl   [3] RUNIC ARLAUG SYMBOL..RUNIC BELGTHOR SYMBOL
+16F1..16F8    ; Runic # Lo   [8] RUNIC LETTER K..RUNIC LETTER FRANKS CASKET AESC
 
-# Total code points: 78
+# Total code points: 86
 
 # ================================================
 
@@ -1377,7 +1418,7 @@
 1806          ; Mongolian # Pd       MONGOLIAN TODO SOFT HYPHEN
 1807..180A    ; Mongolian # Po   [4] MONGOLIAN SIBE SYLLABLE BOUNDARY MARKER..MONGOLIAN NIRUGU
 180B..180D    ; Mongolian # Mn   [3] MONGOLIAN FREE VARIATION SELECTOR ONE..MONGOLIAN FREE VARIATION SELECTOR THREE
-180E          ; Mongolian # Zs       MONGOLIAN VOWEL SEPARATOR
+180E          ; Mongolian # Cf       MONGOLIAN VOWEL SEPARATOR
 1810..1819    ; Mongolian # Nd  [10] MONGOLIAN DIGIT ZERO..MONGOLIAN DIGIT NINE
 1820..1842    ; Mongolian # Lo  [35] MONGOLIAN LETTER A..MONGOLIAN LETTER CHI
 1843          ; Mongolian # Lm       MONGOLIAN LETTER TODO LONG VOWEL SIGN
@@ -1452,10 +1493,10 @@
 
 # ================================================
 
-10300..1031E  ; Old_Italic # Lo  [31] OLD ITALIC LETTER A..OLD ITALIC LETTER UU
+10300..1031F  ; Old_Italic # Lo  [32] OLD ITALIC LETTER A..OLD ITALIC LETTER ESS
 10320..10323  ; Old_Italic # No   [4] OLD ITALIC NUMERAL ONE..OLD ITALIC NUMERAL FIFTY
 
-# Total code points: 35
+# Total code points: 36
 
 # ================================================
 
@@ -1479,12 +1520,15 @@
 064B..0655    ; Inherited # Mn  [11] ARABIC FATHATAN..ARABIC HAMZA BELOW
 0670          ; Inherited # Mn       ARABIC LETTER SUPERSCRIPT ALEF
 0951..0952    ; Inherited # Mn   [2] DEVANAGARI STRESS SIGN UDATTA..DEVANAGARI STRESS SIGN ANUDATTA
+1AB0..1ABD    ; Inherited # Mn  [14] COMBINING DOUBLED CIRCUMFLEX ACCENT..COMBINING PARENTHESES BELOW
+1ABE          ; Inherited # Me       COMBINING PARENTHESES OVERLAY
 1CD0..1CD2    ; Inherited # Mn   [3] VEDIC TONE KARSHANA..VEDIC TONE PRENKHA
 1CD4..1CE0    ; Inherited # Mn  [13] VEDIC SIGN YAJURVEDIC MIDLINE SVARITA..VEDIC TONE RIGVEDIC KASHMIRI INDEPENDENT SVARITA
 1CE2..1CE8    ; Inherited # Mn   [7] VEDIC SIGN VISARGA SVARITA..VEDIC SIGN VISARGA ANUDATTA WITH TAIL
 1CED          ; Inherited # Mn       VEDIC SIGN TIRYAK
 1CF4          ; Inherited # Mn       VEDIC TONE CANDRA ABOVE
-1DC0..1DE6    ; Inherited # Mn  [39] COMBINING DOTTED GRAVE ACCENT..COMBINING LATIN SMALL LETTER Z
+1CF8..1CF9    ; Inherited # Mn   [2] VEDIC TONE RING ABOVE..VEDIC TONE DOUBLE RING ABOVE
+1DC0..1DF5    ; Inherited # Mn  [54] COMBINING DOTTED GRAVE ACCENT..COMBINING UP TACK ABOVE
 1DFC..1DFF    ; Inherited # Mn   [4] COMBINING DOUBLE INVERTED BREVE BELOW..COMBINING RIGHT ARROWHEAD AND DOWN ARROWHEAD BELOW
 200C..200D    ; Inherited # Cf   [2] ZERO WIDTH NON-JOINER..ZERO WIDTH JOINER
 20D0..20DC    ; Inherited # Mn  [13] COMBINING LEFT HARPOON ABOVE..COMBINING FOUR DOTS ABOVE
@@ -1495,15 +1539,16 @@
 302A..302D    ; Inherited # Mn   [4] IDEOGRAPHIC LEVEL TONE MARK..IDEOGRAPHIC ENTERING TONE MARK
 3099..309A    ; Inherited # Mn   [2] COMBINING KATAKANA-HIRAGANA VOICED SOUND MARK..COMBINING KATAKANA-HIRAGANA SEMI-VOICED SOUND MARK
 FE00..FE0F    ; Inherited # Mn  [16] VARIATION SELECTOR-1..VARIATION SELECTOR-16
-FE20..FE26    ; Inherited # Mn   [7] COMBINING LIGATURE LEFT HALF..COMBINING CONJOINING MACRON
+FE20..FE2D    ; Inherited # Mn  [14] COMBINING LIGATURE LEFT HALF..COMBINING CONJOINING MACRON BELOW
 101FD         ; Inherited # Mn       PHAISTOS DISC SIGN COMBINING OBLIQUE STROKE
+102E0         ; Inherited # Mn       COPTIC EPACT THOUSANDS MARK
 1D167..1D169  ; Inherited # Mn   [3] MUSICAL SYMBOL COMBINING TREMOLO-1..MUSICAL SYMBOL COMBINING TREMOLO-3
 1D17B..1D182  ; Inherited # Mn   [8] MUSICAL SYMBOL COMBINING ACCENT..MUSICAL SYMBOL COMBINING LOURE
 1D185..1D18B  ; Inherited # Mn   [7] MUSICAL SYMBOL COMBINING DOIT..MUSICAL SYMBOL COMBINING TRIPLE TONGUE
 1D1AA..1D1AD  ; Inherited # Mn   [4] MUSICAL SYMBOL COMBINING DOWN BOW..MUSICAL SYMBOL COMBINING SNAP PIZZICATO
 E0100..E01EF  ; Inherited # Mn [240] VARIATION SELECTOR-17..VARIATION SELECTOR-256
 
-# Total code points: 523
+# Total code points: 563
 
 # ================================================
 
@@ -1537,7 +1582,7 @@
 
 # ================================================
 
-1900..191C    ; Limbu # Lo  [29] LIMBU VOWEL-CARRIER LETTER..LIMBU LETTER HA
+1900..191E    ; Limbu # Lo  [31] LIMBU VOWEL-CARRIER LETTER..LIMBU LETTER TRA
 1920..1922    ; Limbu # Mn   [3] LIMBU VOWEL SIGN A..LIMBU VOWEL SIGN U
 1923..1926    ; Limbu # Mc   [4] LIMBU VOWEL SIGN EE..LIMBU VOWEL SIGN AU
 1927..1928    ; Limbu # Mn   [2] LIMBU VOWEL SIGN E..LIMBU VOWEL SIGN O
@@ -1550,7 +1595,7 @@
 1944..1945    ; Limbu # Po   [2] LIMBU EXCLAMATION MARK..LIMBU QUESTION MARK
 1946..194F    ; Limbu # Nd  [10] LIMBU DIGIT ZERO..LIMBU DIGIT NINE
 
-# Total code points: 66
+# Total code points: 68
 
 # ================================================
 
@@ -1612,7 +1657,8 @@
 
 1A00..1A16    ; Buginese # Lo  [23] BUGINESE LETTER KA..BUGINESE LETTER HA
 1A17..1A18    ; Buginese # Mn   [2] BUGINESE VOWEL SIGN I..BUGINESE VOWEL SIGN U
-1A19..1A1B    ; Buginese # Mc   [3] BUGINESE VOWEL SIGN E..BUGINESE VOWEL SIGN AE
+1A19..1A1A    ; Buginese # Mc   [2] BUGINESE VOWEL SIGN E..BUGINESE VOWEL SIGN O
+1A1B          ; Buginese # Mn       BUGINESE VOWEL SIGN AE
 1A1E..1A1F    ; Buginese # Po   [2] BUGINESE PALLAWA..BUGINESE END OF SECTION
 
 # Total code points: 30
@@ -1724,11 +1770,11 @@
 
 # ================================================
 
-12000..1236E  ; Cuneiform # Lo [879] CUNEIFORM SIGN A..CUNEIFORM SIGN ZUM
-12400..12462  ; Cuneiform # Nl  [99] CUNEIFORM NUMERIC SIGN TWO ASH..CUNEIFORM NUMERIC SIGN OLD ASSYRIAN ONE QUARTER
-12470..12473  ; Cuneiform # Po   [4] CUNEIFORM PUNCTUATION SIGN OLD ASSYRIAN WORD DIVIDER..CUNEIFORM PUNCTUATION SIGN DIAGONAL TRICOLON
+12000..12398  ; Cuneiform # Lo [921] CUNEIFORM SIGN A..CUNEIFORM SIGN UM TIMES ME
+12400..1246E  ; Cuneiform # Nl [111] CUNEIFORM NUMERIC SIGN TWO ASH..CUNEIFORM NUMERIC SIGN NINE U VARIANT FORM
+12470..12474  ; Cuneiform # Po   [5] CUNEIFORM PUNCTUATION SIGN OLD ASSYRIAN WORD DIVIDER..CUNEIFORM PUNCTUATION SIGN DIAGONAL QUADCOLON
 
-# Total code points: 982
+# Total code points: 1037
 
 # ================================================
 
@@ -1767,8 +1813,7 @@
 1BA6..1BA7    ; Sundanese # Mc   [2] SUNDANESE VOWEL SIGN PANAELAENG..SUNDANESE VOWEL SIGN PANOLONG
 1BA8..1BA9    ; Sundanese # Mn   [2] SUNDANESE VOWEL SIGN PAMEPET..SUNDANESE VOWEL SIGN PANEULEUNG
 1BAA          ; Sundanese # Mc       SUNDANESE SIGN PAMAAEH
-1BAB          ; Sundanese # Mn       SUNDANESE SIGN VIRAMA
-1BAC..1BAD    ; Sundanese # Mc   [2] SUNDANESE CONSONANT SIGN PASANGAN MA..SUNDANESE CONSONANT SIGN PASANGAN WA
+1BAB..1BAD    ; Sundanese # Mn   [3] SUNDANESE SIGN VIRAMA..SUNDANESE CONSONANT SIGN PASANGAN WA
 1BAE..1BAF    ; Sundanese # Lo   [2] SUNDANESE LETTER KHA..SUNDANESE LETTER SYA
 1BB0..1BB9    ; Sundanese # Nd  [10] SUNDANESE DIGIT ZERO..SUNDANESE DIGIT NINE
 1BBA..1BBF    ; Sundanese # Lo   [6] SUNDANESE AVAGRAHA..SUNDANESE LETTER FINAL M
@@ -1825,9 +1870,9 @@
 A900..A909    ; Kayah_Li # Nd  [10] KAYAH LI DIGIT ZERO..KAYAH LI DIGIT NINE
 A90A..A925    ; Kayah_Li # Lo  [28] KAYAH LI LETTER KA..KAYAH LI LETTER OO
 A926..A92D    ; Kayah_Li # Mn   [8] KAYAH LI VOWEL UE..KAYAH LI TONE CALYA PLOPHU
-A92E..A92F    ; Kayah_Li # Po   [2] KAYAH LI SIGN CWI..KAYAH LI SIGN SHYA
+A92F          ; Kayah_Li # Po       KAYAH LI SIGN SHYA
 
-# Total code points: 48
+# Total code points: 47
 
 # ================================================
 
@@ -1974,11 +2019,10 @@
 A9BC          ; Javanese # Mn       JAVANESE VOWEL SIGN PEPET
 A9BD..A9C0    ; Javanese # Mc   [4] JAVANESE CONSONANT SIGN KERET..JAVANESE PANGKON
 A9C1..A9CD    ; Javanese # Po  [13] JAVANESE LEFT RERENGGAN..JAVANESE TURNED PADA PISELEH
-A9CF          ; Javanese # Lm       JAVANESE PANGRANGKEP
 A9D0..A9D9    ; Javanese # Nd  [10] JAVANESE DIGIT ZERO..JAVANESE DIGIT NINE
 A9DE..A9DF    ; Javanese # Po   [2] JAVANESE PADA TIRTA TUMETES..JAVANESE PADA ISEN-ISEN
 
-# Total code points: 91
+# Total code points: 90
 
 # ================================================
 
@@ -2080,8 +2124,9 @@
 11047..1104D  ; Brahmi # Po   [7] BRAHMI DANDA..BRAHMI PUNCTUATION LOTUS
 11052..11065  ; Brahmi # No  [20] BRAHMI NUMBER ONE..BRAHMI NUMBER ONE THOUSAND
 11066..1106F  ; Brahmi # Nd  [10] BRAHMI DIGIT ZERO..BRAHMI DIGIT NINE
+1107F         ; Brahmi # Mn       BRAHMI NUMBER JOINER
 
-# Total code points: 108
+# Total code points: 109
 
 # ================================================
 
@@ -2136,9 +2181,11 @@
 111BF..111C0  ; Sharada # Mc   [2] SHARADA VOWEL SIGN AU..SHARADA SIGN VIRAMA
 111C1..111C4  ; Sharada # Lo   [4] SHARADA SIGN AVAGRAHA..SHARADA OM
 111C5..111C8  ; Sharada # Po   [4] SHARADA DANDA..SHARADA SEPARATOR
+111CD         ; Sharada # Po       SHARADA SUTRA MARK
 111D0..111D9  ; Sharada # Nd  [10] SHARADA DIGIT ZERO..SHARADA DIGIT NINE
+111DA         ; Sharada # Lo       SHARADA EKAM
 
-# Total code points: 83
+# Total code points: 85
 
 # ================================================
 
@@ -2161,4 +2208,244 @@
 
 # Total code points: 66
 
+# ================================================
+
+10530..10563  ; Caucasian_Albanian # Lo  [52] CAUCASIAN ALBANIAN LETTER ALT..CAUCASIAN ALBANIAN LETTER KIW
+1056F         ; Caucasian_Albanian # Po       CAUCASIAN ALBANIAN CITATION MARK
+
+# Total code points: 53
+
+# ================================================
+
+16AD0..16AED  ; Bassa_Vah # Lo  [30] BASSA VAH LETTER ENNI..BASSA VAH LETTER I
+16AF0..16AF4  ; Bassa_Vah # Mn   [5] BASSA VAH COMBINING HIGH TONE..BASSA VAH COMBINING HIGH-LOW TONE
+16AF5         ; Bassa_Vah # Po       BASSA VAH FULL STOP
+
+# Total code points: 36
+
+# ================================================
+
+1BC00..1BC6A  ; Duployan # Lo [107] DUPLOYAN LETTER H..DUPLOYAN LETTER VOCALIC M
+1BC70..1BC7C  ; Duployan # Lo  [13] DUPLOYAN AFFIX LEFT HORIZONTAL SECANT..DUPLOYAN AFFIX ATTACHED TANGENT HOOK
+1BC80..1BC88  ; Duployan # Lo   [9] DUPLOYAN AFFIX HIGH ACUTE..DUPLOYAN AFFIX HIGH VERTICAL
+1BC90..1BC99  ; Duployan # Lo  [10] DUPLOYAN AFFIX LOW ACUTE..DUPLOYAN AFFIX LOW ARROW
+1BC9C         ; Duployan # So       DUPLOYAN SIGN O WITH CROSS
+1BC9D..1BC9E  ; Duployan # Mn   [2] DUPLOYAN THICK LETTER SELECTOR..DUPLOYAN DOUBLE MARK
+1BC9F         ; Duployan # Po       DUPLOYAN PUNCTUATION CHINOOK FULL STOP
+
+# Total code points: 143
+
+# ================================================
+
+10500..10527  ; Elbasan # Lo  [40] ELBASAN LETTER A..ELBASAN LETTER KHE
+
+# Total code points: 40
+
+# ================================================
+
+11301         ; Grantha # Mn       GRANTHA SIGN CANDRABINDU
+11302..11303  ; Grantha # Mc   [2] GRANTHA SIGN ANUSVARA..GRANTHA SIGN VISARGA
+11305..1130C  ; Grantha # Lo   [8] GRANTHA LETTER A..GRANTHA LETTER VOCALIC L
+1130F..11310  ; Grantha # Lo   [2] GRANTHA LETTER EE..GRANTHA LETTER AI
+11313..11328  ; Grantha # Lo  [22] GRANTHA LETTER OO..GRANTHA LETTER NA
+1132A..11330  ; Grantha # Lo   [7] GRANTHA LETTER PA..GRANTHA LETTER RA
+11332..11333  ; Grantha # Lo   [2] GRANTHA LETTER LA..GRANTHA LETTER LLA
+11335..11339  ; Grantha # Lo   [5] GRANTHA LETTER VA..GRANTHA LETTER HA
+1133C         ; Grantha # Mn       GRANTHA SIGN NUKTA
+1133D         ; Grantha # Lo       GRANTHA SIGN AVAGRAHA
+1133E..1133F  ; Grantha # Mc   [2] GRANTHA VOWEL SIGN AA..GRANTHA VOWEL SIGN I
+11340         ; Grantha # Mn       GRANTHA VOWEL SIGN II
+11341..11344  ; Grantha # Mc   [4] GRANTHA VOWEL SIGN U..GRANTHA VOWEL SIGN VOCALIC RR
+11347..11348  ; Grantha # Mc   [2] GRANTHA VOWEL SIGN EE..GRANTHA VOWEL SIGN AI
+1134B..1134D  ; Grantha # Mc   [3] GRANTHA VOWEL SIGN OO..GRANTHA SIGN VIRAMA
+11357         ; Grantha # Mc       GRANTHA AU LENGTH MARK
+1135D..11361  ; Grantha # Lo   [5] GRANTHA SIGN PLUTA..GRANTHA LETTER VOCALIC LL
+11362..11363  ; Grantha # Mc   [2] GRANTHA VOWEL SIGN VOCALIC L..GRANTHA VOWEL SIGN VOCALIC LL
+11366..1136C  ; Grantha # Mn   [7] COMBINING GRANTHA DIGIT ZERO..COMBINING GRANTHA DIGIT SIX
+11370..11374  ; Grantha # Mn   [5] COMBINING GRANTHA LETTER A..COMBINING GRANTHA LETTER PA
+
+# Total code points: 83
+
+# ================================================
+
+16B00..16B2F  ; Pahawh_Hmong # Lo  [48] PAHAWH HMONG VOWEL KEEB..PAHAWH HMONG CONSONANT CAU
+16B30..16B36  ; Pahawh_Hmong # Mn   [7] PAHAWH HMONG MARK CIM TUB..PAHAWH HMONG MARK CIM TAUM
+16B37..16B3B  ; Pahawh_Hmong # Po   [5] PAHAWH HMONG SIGN VOS THOM..PAHAWH HMONG SIGN VOS FEEM
+16B3C..16B3F  ; Pahawh_Hmong # So   [4] PAHAWH HMONG SIGN XYEEM NTXIV..PAHAWH HMONG SIGN XYEEM FAIB
+16B40..16B43  ; Pahawh_Hmong # Lm   [4] PAHAWH HMONG SIGN VOS SEEV..PAHAWH HMONG SIGN IB YAM
+16B44         ; Pahawh_Hmong # Po       PAHAWH HMONG SIGN XAUS
+16B45         ; Pahawh_Hmong # So       PAHAWH HMONG SIGN CIM TSOV ROG
+16B50..16B59  ; Pahawh_Hmong # Nd  [10] PAHAWH HMONG DIGIT ZERO..PAHAWH HMONG DIGIT NINE
+16B5B..16B61  ; Pahawh_Hmong # No   [7] PAHAWH HMONG NUMBER TENS..PAHAWH HMONG NUMBER TRILLIONS
+16B63..16B77  ; Pahawh_Hmong # Lo  [21] PAHAWH HMONG SIGN VOS LUB..PAHAWH HMONG SIGN CIM NRES TOS
+16B7D..16B8F  ; Pahawh_Hmong # Lo  [19] PAHAWH HMONG CLAN SIGN TSHEEJ..PAHAWH HMONG CLAN SIGN VWJ
+
+# Total code points: 127
+
+# ================================================
+
+11200..11211  ; Khojki # Lo  [18] KHOJKI LETTER A..KHOJKI LETTER JJA
+11213..1122B  ; Khojki # Lo  [25] KHOJKI LETTER NYA..KHOJKI LETTER LLA
+1122C..1122E  ; Khojki # Mc   [3] KHOJKI VOWEL SIGN AA..KHOJKI VOWEL SIGN II
+1122F..11231  ; Khojki # Mn   [3] KHOJKI VOWEL SIGN U..KHOJKI VOWEL SIGN AI
+11232..11233  ; Khojki # Mc   [2] KHOJKI VOWEL SIGN O..KHOJKI VOWEL SIGN AU
+11234         ; Khojki # Mn       KHOJKI SIGN ANUSVARA
+11235         ; Khojki # Mc       KHOJKI SIGN VIRAMA
+11236..11237  ; Khojki # Mn   [2] KHOJKI SIGN NUKTA..KHOJKI SIGN SHADDA
+11238..1123D  ; Khojki # Po   [6] KHOJKI DANDA..KHOJKI ABBREVIATION SIGN
+
+# Total code points: 61
+
+# ================================================
+
+10600..10736  ; Linear_A # Lo [311] LINEAR A SIGN AB001..LINEAR A SIGN A664
+10740..10755  ; Linear_A # Lo  [22] LINEAR A SIGN A701 A..LINEAR A SIGN A732 JE
+10760..10767  ; Linear_A # Lo   [8] LINEAR A SIGN A800..LINEAR A SIGN A807
+
+# Total code points: 341
+
+# ================================================
+
+11150..11172  ; Mahajani # Lo  [35] MAHAJANI LETTER A..MAHAJANI LETTER RRA
+11173         ; Mahajani # Mn       MAHAJANI SIGN NUKTA
+11174..11175  ; Mahajani # Po   [2] MAHAJANI ABBREVIATION SIGN..MAHAJANI SECTION MARK
+11176         ; Mahajani # Lo       MAHAJANI LIGATURE SHRI
+
+# Total code points: 39
+
+# ================================================
+
+10AC0..10AC7  ; Manichaean # Lo   [8] MANICHAEAN LETTER ALEPH..MANICHAEAN LETTER WAW
+10AC8         ; Manichaean # So       MANICHAEAN SIGN UD
+10AC9..10AE4  ; Manichaean # Lo  [28] MANICHAEAN LETTER ZAYIN..MANICHAEAN LETTER TAW
+10AE5..10AE6  ; Manichaean # Mn   [2] MANICHAEAN ABBREVIATION MARK ABOVE..MANICHAEAN ABBREVIATION MARK BELOW
+10AEB..10AEF  ; Manichaean # No   [5] MANICHAEAN NUMBER ONE..MANICHAEAN NUMBER ONE HUNDRED
+10AF0..10AF6  ; Manichaean # Po   [7] MANICHAEAN PUNCTUATION STAR..MANICHAEAN PUNCTUATION LINE FILLER
+
+# Total code points: 51
+
+# ================================================
+
+1E800..1E8C4  ; Mende_Kikakui # Lo [197] MENDE KIKAKUI SYLLABLE M001 KI..MENDE KIKAKUI SYLLABLE M060 NYON
+1E8C7..1E8CF  ; Mende_Kikakui # No   [9] MENDE KIKAKUI DIGIT ONE..MENDE KIKAKUI DIGIT NINE
+1E8D0..1E8D6  ; Mende_Kikakui # Mn   [7] MENDE KIKAKUI COMBINING NUMBER TEENS..MENDE KIKAKUI COMBINING NUMBER MILLIONS
+
+# Total code points: 213
+
+# ================================================
+
+11600..1162F  ; Modi # Lo  [48] MODI LETTER A..MODI LETTER LLA
+11630..11632  ; Modi # Mc   [3] MODI VOWEL SIGN AA..MODI VOWEL SIGN II
+11633..1163A  ; Modi # Mn   [8] MODI VOWEL SIGN U..MODI VOWEL SIGN AI
+1163B..1163C  ; Modi # Mc   [2] MODI VOWEL SIGN O..MODI VOWEL SIGN AU
+1163D         ; Modi # Mn       MODI SIGN ANUSVARA
+1163E         ; Modi # Mc       MODI SIGN VISARGA
+1163F..11640  ; Modi # Mn   [2] MODI SIGN VIRAMA..MODI SIGN ARDHACANDRA
+11641..11643  ; Modi # Po   [3] MODI DANDA..MODI ABBREVIATION SIGN
+11644         ; Modi # Lo       MODI SIGN HUVA
+11650..11659  ; Modi # Nd  [10] MODI DIGIT ZERO..MODI DIGIT NINE
+
+# Total code points: 79
+
+# ================================================
+
+16A40..16A5E  ; Mro # Lo  [31] MRO LETTER TA..MRO LETTER TEK
+16A60..16A69  ; Mro # Nd  [10] MRO DIGIT ZERO..MRO DIGIT NINE
+16A6E..16A6F  ; Mro # Po   [2] MRO DANDA..MRO DOUBLE DANDA
+
+# Total code points: 43
+
+# ================================================
+
+10A80..10A9C  ; Old_North_Arabian # Lo  [29] OLD NORTH ARABIAN LETTER HEH..OLD NORTH ARABIAN LETTER ZAH
+10A9D..10A9F  ; Old_North_Arabian # No   [3] OLD NORTH ARABIAN NUMBER ONE..OLD NORTH ARABIAN NUMBER TWENTY
+
+# Total code points: 32
+
+# ================================================
+
+10880..1089E  ; Nabataean # Lo  [31] NABATAEAN LETTER FINAL ALEPH..NABATAEAN LETTER TAW
+108A7..108AF  ; Nabataean # No   [9] NABATAEAN NUMBER ONE..NABATAEAN NUMBER ONE HUNDRED
+
+# Total code points: 40
+
+# ================================================
+
+10860..10876  ; Palmyrene # Lo  [23] PALMYRENE LETTER ALEPH..PALMYRENE LETTER TAW
+10877..10878  ; Palmyrene # So   [2] PALMYRENE LEFT-POINTING FLEURON..PALMYRENE RIGHT-POINTING FLEURON
+10879..1087F  ; Palmyrene # No   [7] PALMYRENE NUMBER ONE..PALMYRENE NUMBER TWENTY
+
+# Total code points: 32
+
+# ================================================
+
+11AC0..11AF8  ; Pau_Cin_Hau # Lo  [57] PAU CIN HAU LETTER PA..PAU CIN HAU GLOTTAL STOP FINAL
+
+# Total code points: 57
+
+# ================================================
+
+10350..10375  ; Old_Permic # Lo  [38] OLD PERMIC LETTER AN..OLD PERMIC LETTER IA
+10376..1037A  ; Old_Permic # Mn   [5] COMBINING OLD PERMIC LETTER AN..COMBINING OLD PERMIC LETTER SII
+
+# Total code points: 43
+
+# ================================================
+
+10B80..10B91  ; Psalter_Pahlavi # Lo  [18] PSALTER PAHLAVI LETTER ALEPH..PSALTER PAHLAVI LETTER TAW
+10B99..10B9C  ; Psalter_Pahlavi # Po   [4] PSALTER PAHLAVI SECTION MARK..PSALTER PAHLAVI FOUR DOTS WITH DOT
+10BA9..10BAF  ; Psalter_Pahlavi # No   [7] PSALTER PAHLAVI NUMBER ONE..PSALTER PAHLAVI NUMBER ONE HUNDRED
+
+# Total code points: 29
+
+# ================================================
+
+11580..115AE  ; Siddham # Lo  [47] SIDDHAM LETTER A..SIDDHAM LETTER HA
+115AF..115B1  ; Siddham # Mc   [3] SIDDHAM VOWEL SIGN AA..SIDDHAM VOWEL SIGN II
+115B2..115B5  ; Siddham # Mn   [4] SIDDHAM VOWEL SIGN U..SIDDHAM VOWEL SIGN VOCALIC RR
+115B8..115BB  ; Siddham # Mc   [4] SIDDHAM VOWEL SIGN E..SIDDHAM VOWEL SIGN AU
+115BC..115BD  ; Siddham # Mn   [2] SIDDHAM SIGN CANDRABINDU..SIDDHAM SIGN ANUSVARA
+115BE         ; Siddham # Mc       SIDDHAM SIGN VISARGA
+115BF..115C0  ; Siddham # Mn   [2] SIDDHAM SIGN VIRAMA..SIDDHAM SIGN NUKTA
+115C1..115C9  ; Siddham # Po   [9] SIDDHAM SIGN SIDDHAM..SIDDHAM END OF TEXT MARK
+
+# Total code points: 72
+
+# ================================================
+
+112B0..112DE  ; Khudawadi # Lo  [47] KHUDAWADI LETTER A..KHUDAWADI LETTER HA
+112DF         ; Khudawadi # Mn       KHUDAWADI SIGN ANUSVARA
+112E0..112E2  ; Khudawadi # Mc   [3] KHUDAWADI VOWEL SIGN AA..KHUDAWADI VOWEL SIGN II
+112E3..112EA  ; Khudawadi # Mn   [8] KHUDAWADI VOWEL SIGN U..KHUDAWADI SIGN VIRAMA
+112F0..112F9  ; Khudawadi # Nd  [10] KHUDAWADI DIGIT ZERO..KHUDAWADI DIGIT NINE
+
+# Total code points: 69
+
+# ================================================
+
+11480..114AF  ; Tirhuta # Lo  [48] TIRHUTA ANJI..TIRHUTA LETTER HA
+114B0..114B2  ; Tirhuta # Mc   [3] TIRHUTA VOWEL SIGN AA..TIRHUTA VOWEL SIGN II
+114B3..114B8  ; Tirhuta # Mn   [6] TIRHUTA VOWEL SIGN U..TIRHUTA VOWEL SIGN VOCALIC LL
+114B9         ; Tirhuta # Mc       TIRHUTA VOWEL SIGN E
+114BA         ; Tirhuta # Mn       TIRHUTA VOWEL SIGN SHORT E
+114BB..114BE  ; Tirhuta # Mc   [4] TIRHUTA VOWEL SIGN AI..TIRHUTA VOWEL SIGN AU
+114BF..114C0  ; Tirhuta # Mn   [2] TIRHUTA SIGN CANDRABINDU..TIRHUTA SIGN ANUSVARA
+114C1         ; Tirhuta # Mc       TIRHUTA SIGN VISARGA
+114C2..114C3  ; Tirhuta # Mn   [2] TIRHUTA SIGN VIRAMA..TIRHUTA SIGN NUKTA
+114C4..114C5  ; Tirhuta # Lo   [2] TIRHUTA SIGN AVAGRAHA..TIRHUTA GVANG
+114C6         ; Tirhuta # Po       TIRHUTA ABBREVIATION SIGN
+114C7         ; Tirhuta # Lo       TIRHUTA OM
+114D0..114D9  ; Tirhuta # Nd  [10] TIRHUTA DIGIT ZERO..TIRHUTA DIGIT NINE
+
+# Total code points: 82
+
+# ================================================
+
+118A0..118DF  ; Warang_Citi # L&  [64] WARANG CITI CAPITAL LETTER NGAA..WARANG CITI SMALL LETTER VIYO
+118E0..118E9  ; Warang_Citi # Nd  [10] WARANG CITI DIGIT ZERO..WARANG CITI DIGIT NINE
+118EA..118F2  ; Warang_Citi # No   [9] WARANG CITI NUMBER TEN..WARANG CITI NUMBER NINETY
+118FF         ; Warang_Citi # Lo       WARANG CITI OM
+
+# Total code points: 84
+
 # EOF
--- a/jdk/make/data/unicodedata/SpecialCasing.txt	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/make/data/unicodedata/SpecialCasing.txt	Wed Jul 05 20:42:36 2017 +0200
@@ -1,18 +1,25 @@
-# SpecialCasing-6.2.0.txt
-# Date: 2012-05-23, 20:35:15 GMT [MD]
+# SpecialCasing-7.0.0.txt
+# Date: 2014-03-18, 07:18:02 GMT [MD]
 #
 # Unicode Character Database
-# Copyright (c) 1991-2012 Unicode, Inc.
+# Copyright (c) 1991-2014 Unicode, Inc.
 # For terms of use, see http://www.unicode.org/terms_of_use.html
 # For documentation, see http://www.unicode.org/reports/tr44/
 #
-# Special Casing Properties
+# Special Casing
 #
-# This file is a supplement to the UnicodeData file.
-# It contains additional information about the casing of Unicode characters.
-# (For compatibility, the UnicodeData.txt file only contains case mappings for
-# characters where they are 1-1, and independent of context and language.
-# For more information, see the discussion of Case Mappings in the Unicode Standard.
+# This file is a supplement to the UnicodeData.txt file. It does not define any
+# properties, but rather provides additional information about the casing of
+# Unicode characters, for situations when casing incurs a change in string length
+# or is dependent on context or locale. For compatibility, the UnicodeData.txt
+# file only contains simple case mappings for characters where they are one-to-one
+# and independent of context and language. The data in this file, combined with
+# the simple case mappings in UnicodeData.txt, defines the full case mappings
+# Lowercase_Mapping (lc), Titlecase_Mapping (tc), and Uppercase_Mapping (uc).
+#
+# Note that the preferred mechanism for defining tailored casing operations is
+# the Unicode Common Locale Data Repository (CLDR). For more information, see the
+# discussion of case mappings and case algorithms in the Unicode Standard.
 #
 # All code points not listed in this file that do not have a simple case mappings
 # in UnicodeData.txt map to themselves.
@@ -21,16 +28,17 @@
 # ================================================================================
 # The entries in this file are in the following machine-readable format:
 #
-# <code>; <lower> ; <title> ; <upper> ; (<condition_list> ;)? # <comment>
+# <code>; <lower>; <title>; <upper>; (<condition_list>;)? # <comment>
 #
-# <code>, <lower>, <title>, and <upper> provide character values in hex. If there is more
-# than one character, they are separated by spaces. Other than as used to separate 
-# elements, spaces are to be ignored.
+# <code>, <lower>, <title>, and <upper> provide the respective full case mappings
+# of <code>, expressed as character values in hex. If there is more than one character,
+# they are separated by spaces. Other than as used to separate elements, spaces are
+# to be ignored.
 #
 # The <condition_list> is optional. Where present, it consists of one or more language IDs
-# or contexts, separated by spaces. In these conditions:
+# or casing contexts, separated by spaces. In these conditions:
 # - A condition list overrides the normal behavior if all of the listed conditions are true.
-# - The context is always the context of the characters in the original string,
+# - The casing context is always the context of the characters in the original string,
 #   NOT in the resulting string.
 # - Case distinctions in the condition list are not significant.
 # - Conditions preceded by "Not_" represent the negation of the condition.
@@ -38,18 +46,14 @@
 #
 # A language ID is defined by BCP 47, with '-' and '_' treated equivalently.
 #
-# A context for a character C is defined by Section 3.13 Default Case 
-# Operations, of The Unicode Standard, Version 5.0.
-# (This is identical to the context defined by Unicode 4.1.0,
-#  as specified in http://www.unicode.org/versions/Unicode4.1.0/)
+# A casing context for a character is defined by Section 3.13 Default Case Algorithms
+# of The Unicode Standard.
 #
 # Parsers of this file must be prepared to deal with future additions to this format:
 #  * Additional contexts
 #  * Additional fields
 # ================================================================================
 
-# @missing: 0000..10FFFF; <slc>; <stc>; <suc>;
-
 # ================================================================================
 # Unconditional mappings
 # ================================================================================
@@ -114,7 +118,7 @@
 #  This process can be achieved by first transforming the text to NFC before casing.
 #  E.g. <alpha><iota_subscript><acute> is uppercased to <ALPHA><acute><IOTA>
 
-# The following cases are already in the UnicodeData file, so are only commented here.
+# The following cases are already in the UnicodeData.txt file, so are only commented here.
 
 # 0345; 0345; 0345; 0399; # COMBINING GREEK YPOGEGRAMMENI
 
@@ -205,7 +209,7 @@
 
 03A3; 03C2; 03A3; 03A3; Final_Sigma; # GREEK CAPITAL LETTER SIGMA
 
-# Note: the following cases for non-final are already in the UnicodeData file.
+# Note: the following cases for non-final are already in the UnicodeData.txt file.
 
 # 03A3; 03C3; 03A3; 03A3; # GREEK CAPITAL LETTER SIGMA
 # 03C3; 03C3; 03A3; 03A3; # GREEK SMALL LETTER SIGMA
@@ -268,7 +272,7 @@
 0069; 0069; 0130; 0130; tr; # LATIN SMALL LETTER I
 0069; 0069; 0130; 0130; az; # LATIN SMALL LETTER I
 
-# Note: the following case is already in the UnicodeData file.
+# Note: the following case is already in the UnicodeData.txt file.
 
 # 0131; 0131; 0049; 0049; tr; # LATIN SMALL LETTER DOTLESS I
 
--- a/jdk/make/data/unicodedata/UnicodeData.txt	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/make/data/unicodedata/UnicodeData.txt	Wed Jul 05 20:42:36 2017 +0200
@@ -602,12 +602,12 @@
 0259;LATIN SMALL LETTER SCHWA;Ll;0;L;;;;;N;;;018F;;018F
 025A;LATIN SMALL LETTER SCHWA WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER SCHWA HOOK;;;;
 025B;LATIN SMALL LETTER OPEN E;Ll;0;L;;;;;N;LATIN SMALL LETTER EPSILON;;0190;;0190
-025C;LATIN SMALL LETTER REVERSED OPEN E;Ll;0;L;;;;;N;LATIN SMALL LETTER REVERSED EPSILON;;;;
+025C;LATIN SMALL LETTER REVERSED OPEN E;Ll;0;L;;;;;N;LATIN SMALL LETTER REVERSED EPSILON;;A7AB;;A7AB
 025D;LATIN SMALL LETTER REVERSED OPEN E WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER REVERSED EPSILON HOOK;;;;
 025E;LATIN SMALL LETTER CLOSED REVERSED OPEN E;Ll;0;L;;;;;N;LATIN SMALL LETTER CLOSED REVERSED EPSILON;;;;
 025F;LATIN SMALL LETTER DOTLESS J WITH STROKE;Ll;0;L;;;;;N;LATIN SMALL LETTER DOTLESS J BAR;;;;
 0260;LATIN SMALL LETTER G WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER G HOOK;;0193;;0193
-0261;LATIN SMALL LETTER SCRIPT G;Ll;0;L;;;;;N;;;;;
+0261;LATIN SMALL LETTER SCRIPT G;Ll;0;L;;;;;N;;;A7AC;;A7AC
 0262;LATIN LETTER SMALL CAPITAL G;Ll;0;L;;;;;N;;;;;
 0263;LATIN SMALL LETTER GAMMA;Ll;0;L;;;;;N;;;0194;;0194
 0264;LATIN SMALL LETTER RAMS HORN;Ll;0;L;;;;;N;LATIN SMALL LETTER BABY GAMMA;;;;
@@ -618,7 +618,7 @@
 0269;LATIN SMALL LETTER IOTA;Ll;0;L;;;;;N;;;0196;;0196
 026A;LATIN LETTER SMALL CAPITAL I;Ll;0;L;;;;;N;;;;;
 026B;LATIN SMALL LETTER L WITH MIDDLE TILDE;Ll;0;L;;;;;N;;;2C62;;2C62
-026C;LATIN SMALL LETTER L WITH BELT;Ll;0;L;;;;;N;LATIN SMALL LETTER L BELT;;;;
+026C;LATIN SMALL LETTER L WITH BELT;Ll;0;L;;;;;N;LATIN SMALL LETTER L BELT;;A7AD;;A7AD
 026D;LATIN SMALL LETTER L WITH RETROFLEX HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER L RETROFLEX HOOK;;;;
 026E;LATIN SMALL LETTER LEZH;Ll;0;L;;;;;N;LATIN SMALL LETTER L YOGH;;;;
 026F;LATIN SMALL LETTER TURNED M;Ll;0;L;;;;;N;;;019C;;019C
@@ -645,7 +645,7 @@
 0284;LATIN SMALL LETTER DOTLESS J WITH STROKE AND HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER DOTLESS J BAR HOOK;;;;
 0285;LATIN SMALL LETTER SQUAT REVERSED ESH;Ll;0;L;;;;;N;;;;;
 0286;LATIN SMALL LETTER ESH WITH CURL;Ll;0;L;;;;;N;LATIN SMALL LETTER ESH CURL;;;;
-0287;LATIN SMALL LETTER TURNED T;Ll;0;L;;;;;N;;;;;
+0287;LATIN SMALL LETTER TURNED T;Ll;0;L;;;;;N;;;A7B1;;A7B1
 0288;LATIN SMALL LETTER T WITH RETROFLEX HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER T RETROFLEX HOOK;;01AE;;01AE
 0289;LATIN SMALL LETTER U BAR;Ll;0;L;;;;;N;;;0244;;0244
 028A;LATIN SMALL LETTER UPSILON;Ll;0;L;;;;;N;;;01B1;;01B1
@@ -668,7 +668,7 @@
 029B;LATIN LETTER SMALL CAPITAL G WITH HOOK;Ll;0;L;;;;;N;LATIN LETTER SMALL CAPITAL G HOOK;;;;
 029C;LATIN LETTER SMALL CAPITAL H;Ll;0;L;;;;;N;;;;;
 029D;LATIN SMALL LETTER J WITH CROSSED-TAIL;Ll;0;L;;;;;N;LATIN SMALL LETTER CROSSED-TAIL J;;;;
-029E;LATIN SMALL LETTER TURNED K;Ll;0;L;;;;;N;;;;;
+029E;LATIN SMALL LETTER TURNED K;Ll;0;L;;;;;N;;;A7B0;;A7B0
 029F;LATIN LETTER SMALL CAPITAL L;Ll;0;L;;;;;N;;;;;
 02A0;LATIN SMALL LETTER Q WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER Q HOOK;;;;
 02A1;LATIN LETTER GLOTTAL STOP WITH STROKE;Ll;0;L;;;;;N;LATIN LETTER GLOTTAL STOP BAR;;;;
@@ -891,6 +891,7 @@
 037C;GREEK SMALL DOTTED LUNATE SIGMA SYMBOL;Ll;0;L;;;;;N;;;03FE;;03FE
 037D;GREEK SMALL REVERSED DOTTED LUNATE SIGMA SYMBOL;Ll;0;L;;;;;N;;;03FF;;03FF
 037E;GREEK QUESTION MARK;Po;0;ON;003B;;;;N;;;;;
+037F;GREEK CAPITAL LETTER YOT;Lu;0;L;;;;;N;;;;03F3;
 0384;GREEK TONOS;Sk;0;ON;<compat> 0020 0301;;;;N;GREEK SPACING TONOS;;;;
 0385;GREEK DIALYTIKA TONOS;Sk;0;ON;00A8 0301;;;;N;GREEK SPACING DIAERESIS TONOS;;;;
 0386;GREEK CAPITAL LETTER ALPHA WITH TONOS;Lu;0;L;0391 0301;;;;N;GREEK CAPITAL LETTER ALPHA TONOS;;;03AC;
@@ -999,7 +1000,7 @@
 03F0;GREEK KAPPA SYMBOL;Ll;0;L;<compat> 03BA;;;;N;GREEK SMALL LETTER SCRIPT KAPPA;;039A;;039A
 03F1;GREEK RHO SYMBOL;Ll;0;L;<compat> 03C1;;;;N;GREEK SMALL LETTER TAILED RHO;;03A1;;03A1
 03F2;GREEK LUNATE SIGMA SYMBOL;Ll;0;L;<compat> 03C2;;;;N;GREEK SMALL LETTER LUNATE SIGMA;;03F9;;03F9
-03F3;GREEK LETTER YOT;Ll;0;L;;;;;N;;;;;
+03F3;GREEK LETTER YOT;Ll;0;L;;;;;N;;;037F;;037F
 03F4;GREEK CAPITAL THETA SYMBOL;Lu;0;L;<compat> 0398;;;;N;;;;03B8;
 03F5;GREEK LUNATE EPSILON SYMBOL;Ll;0;L;<compat> 03B5;;;;N;;;0395;;0395
 03F6;GREEK REVERSED LUNATE EPSILON SYMBOL;Sm;0;ON;;;;;N;;;;;
@@ -1308,6 +1309,14 @@
 0525;CYRILLIC SMALL LETTER PE WITH DESCENDER;Ll;0;L;;;;;N;;;0524;;0524
 0526;CYRILLIC CAPITAL LETTER SHHA WITH DESCENDER;Lu;0;L;;;;;N;;;;0527;
 0527;CYRILLIC SMALL LETTER SHHA WITH DESCENDER;Ll;0;L;;;;;N;;;0526;;0526
+0528;CYRILLIC CAPITAL LETTER EN WITH LEFT HOOK;Lu;0;L;;;;;N;;;;0529;
+0529;CYRILLIC SMALL LETTER EN WITH LEFT HOOK;Ll;0;L;;;;;N;;;0528;;0528
+052A;CYRILLIC CAPITAL LETTER DZZHE;Lu;0;L;;;;;N;;;;052B;
+052B;CYRILLIC SMALL LETTER DZZHE;Ll;0;L;;;;;N;;;052A;;052A
+052C;CYRILLIC CAPITAL LETTER DCHE;Lu;0;L;;;;;N;;;;052D;
+052D;CYRILLIC SMALL LETTER DCHE;Ll;0;L;;;;;N;;;052C;;052C
+052E;CYRILLIC CAPITAL LETTER EL WITH DESCENDER;Lu;0;L;;;;;N;;;;052F;
+052F;CYRILLIC SMALL LETTER EL WITH DESCENDER;Ll;0;L;;;;;N;;;052E;;052E
 0531;ARMENIAN CAPITAL LETTER AYB;Lu;0;L;;;;;N;;;;0561;
 0532;ARMENIAN CAPITAL LETTER BEN;Lu;0;L;;;;;N;;;;0562;
 0533;ARMENIAN CAPITAL LETTER GIM;Lu;0;L;;;;;N;;;;0563;
@@ -1394,6 +1403,8 @@
 0587;ARMENIAN SMALL LIGATURE ECH YIWN;Ll;0;L;<compat> 0565 0582;;;;N;;;;;
 0589;ARMENIAN FULL STOP;Po;0;L;;;;;N;ARMENIAN PERIOD;;;;
 058A;ARMENIAN HYPHEN;Pd;0;ON;;;;;N;;;;;
+058D;RIGHT-FACING ARMENIAN ETERNITY SIGN;So;0;ON;;;;;N;;;;;
+058E;LEFT-FACING ARMENIAN ETERNITY SIGN;So;0;ON;;;;;N;;;;;
 058F;ARMENIAN DRAM SIGN;Sc;0;ET;;;;;N;;;;;
 0591;HEBREW ACCENT ETNAHTA;Mn;220;NSM;;;;;N;;;;;
 0592;HEBREW ACCENT SEGOL;Mn;230;NSM;;;;;N;;;;;
@@ -1487,6 +1498,7 @@
 0602;ARABIC FOOTNOTE MARKER;Cf;0;AN;;;;;N;;;;;
 0603;ARABIC SIGN SAFHA;Cf;0;AN;;;;;N;;;;;
 0604;ARABIC SIGN SAMVAT;Cf;0;AN;;;;;N;;;;;
+0605;ARABIC NUMBER MARK ABOVE;Cf;0;AN;;;;;N;;;;;
 0606;ARABIC-INDIC CUBE ROOT;Sm;0;ON;;;;;N;;;;;
 0607;ARABIC-INDIC FOURTH ROOT;Sm;0;ON;;;;;N;;;;;
 0608;ARABIC RAY;Sm;0;AL;;;;;N;;;;;
@@ -1509,6 +1521,7 @@
 0619;ARABIC SMALL DAMMA;Mn;31;NSM;;;;;N;;;;;
 061A;ARABIC SMALL KASRA;Mn;32;NSM;;;;;N;;;;;
 061B;ARABIC SEMICOLON;Po;0;AL;;;;;N;;;;;
+061C;ARABIC LETTER MARK;Cf;0;AL;;;;;N;;;;;
 061E;ARABIC TRIPLE DOT PUNCTUATION MARK;Po;0;AL;;;;;N;;;;;
 061F;ARABIC QUESTION MARK;Po;0;AL;;;;;N;;;;;
 0620;ARABIC LETTER KASHMIRI YEH;Lo;0;AL;;;;;N;;;;;
@@ -2060,6 +2073,7 @@
 085B;MANDAIC GEMINATION MARK;Mn;220;NSM;;;;;N;;;;;
 085E;MANDAIC PUNCTUATION;Po;0;R;;;;;N;;;;;
 08A0;ARABIC LETTER BEH WITH SMALL V BELOW;Lo;0;AL;;;;;N;;;;;
+08A1;ARABIC LETTER BEH WITH HAMZA ABOVE;Lo;0;AL;;;;;N;;;;;
 08A2;ARABIC LETTER JEEM WITH TWO DOTS ABOVE;Lo;0;AL;;;;;N;;;;;
 08A3;ARABIC LETTER TAH WITH TWO DOTS ABOVE;Lo;0;AL;;;;;N;;;;;
 08A4;ARABIC LETTER FEH WITH DOT BELOW AND THREE DOTS ABOVE;Lo;0;AL;;;;;N;;;;;
@@ -2071,6 +2085,12 @@
 08AA;ARABIC LETTER REH WITH LOOP;Lo;0;AL;;;;;N;;;;;
 08AB;ARABIC LETTER WAW WITH DOT WITHIN;Lo;0;AL;;;;;N;;;;;
 08AC;ARABIC LETTER ROHINGYA YEH;Lo;0;AL;;;;;N;;;;;
+08AD;ARABIC LETTER LOW ALEF;Lo;0;AL;;;;;N;;;;;
+08AE;ARABIC LETTER DAL WITH THREE DOTS BELOW;Lo;0;AL;;;;;N;;;;;
+08AF;ARABIC LETTER SAD WITH THREE DOTS BELOW;Lo;0;AL;;;;;N;;;;;
+08B0;ARABIC LETTER GAF WITH INVERTED STROKE;Lo;0;AL;;;;;N;;;;;
+08B1;ARABIC LETTER STRAIGHT WAW;Lo;0;AL;;;;;N;;;;;
+08B2;ARABIC LETTER ZAIN WITH INVERTED V ABOVE;Lo;0;AL;;;;;N;;;;;
 08E4;ARABIC CURLY FATHA;Mn;230;NSM;;;;;N;;;;;
 08E5;ARABIC CURLY DAMMA;Mn;230;NSM;;;;;N;;;;;
 08E6;ARABIC CURLY KASRA;Mn;220;NSM;;;;;N;;;;;
@@ -2098,6 +2118,7 @@
 08FC;ARABIC DOUBLE RIGHT ARROWHEAD ABOVE WITH DOT;Mn;230;NSM;;;;;N;;;;;
 08FD;ARABIC RIGHT ARROWHEAD ABOVE WITH DOT;Mn;230;NSM;;;;;N;;;;;
 08FE;ARABIC DAMMA WITH DOT;Mn;230;NSM;;;;;N;;;;;
+08FF;ARABIC MARK SIDEWAYS NOON GHUNNA;Mn;230;NSM;;;;;N;;;;;
 0900;DEVANAGARI SIGN INVERTED CANDRABINDU;Mn;0;NSM;;;;;N;;;;;
 0901;DEVANAGARI SIGN CANDRABINDU;Mn;0;NSM;;;;;N;;;;;
 0902;DEVANAGARI SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;;
@@ -2218,6 +2239,7 @@
 0975;DEVANAGARI LETTER AW;Lo;0;L;;;;;N;;;;;
 0976;DEVANAGARI LETTER UE;Lo;0;L;;;;;N;;;;;
 0977;DEVANAGARI LETTER UUE;Lo;0;L;;;;;N;;;;;
+0978;DEVANAGARI LETTER MARWARI DDA;Lo;0;L;;;;;N;;;;;
 0979;DEVANAGARI LETTER ZHA;Lo;0;L;;;;;N;;;;;
 097A;DEVANAGARI LETTER HEAVY YA;Lo;0;L;;;;;N;;;;;
 097B;DEVANAGARI LETTER GGA;Lo;0;L;;;;;N;;;;;
@@ -2225,6 +2247,7 @@
 097D;DEVANAGARI LETTER GLOTTAL STOP;Lo;0;L;;;;;N;;;;;
 097E;DEVANAGARI LETTER DDDA;Lo;0;L;;;;;N;;;;;
 097F;DEVANAGARI LETTER BBA;Lo;0;L;;;;;N;;;;;
+0980;BENGALI ANJI;Lo;0;L;;;;;N;;;;;
 0981;BENGALI SIGN CANDRABINDU;Mn;0;NSM;;;;;N;;;;;
 0982;BENGALI SIGN ANUSVARA;Mc;0;L;;;;;N;;;;;
 0983;BENGALI SIGN VISARGA;Mc;0;L;;;;;N;;;;;
@@ -2642,6 +2665,7 @@
 0BF8;TAMIL AS ABOVE SIGN;So;0;ON;;;;;N;;;;;
 0BF9;TAMIL RUPEE SIGN;Sc;0;ET;;;;;N;;;;;
 0BFA;TAMIL NUMBER SIGN;So;0;ON;;;;;N;;;;;
+0C00;TELUGU SIGN COMBINING CANDRABINDU ABOVE;Mn;0;NSM;;;;;N;;;;;
 0C01;TELUGU SIGN CANDRABINDU;Mc;0;L;;;;;N;;;;;
 0C02;TELUGU SIGN ANUSVARA;Mc;0;L;;;;;N;;;;;
 0C03;TELUGU SIGN VISARGA;Mc;0;L;;;;;N;;;;;
@@ -2689,6 +2713,7 @@
 0C31;TELUGU LETTER RRA;Lo;0;L;;;;;N;;;;;
 0C32;TELUGU LETTER LA;Lo;0;L;;;;;N;;;;;
 0C33;TELUGU LETTER LLA;Lo;0;L;;;;;N;;;;;
+0C34;TELUGU LETTER LLLA;Lo;0;L;;;;;N;;;;;
 0C35;TELUGU LETTER VA;Lo;0;L;;;;;N;;;;;
 0C36;TELUGU LETTER SHA;Lo;0;L;;;;;N;;;;;
 0C37;TELUGU LETTER SSA;Lo;0;L;;;;;N;;;;;
@@ -2735,6 +2760,7 @@
 0C7D;TELUGU FRACTION DIGIT TWO FOR EVEN POWERS OF FOUR;No;0;ON;;;;2;N;;;;;
 0C7E;TELUGU FRACTION DIGIT THREE FOR EVEN POWERS OF FOUR;No;0;ON;;;;3;N;;;;;
 0C7F;TELUGU SIGN TUUMU;So;0;L;;;;;N;;;;;
+0C81;KANNADA SIGN CANDRABINDU;Mn;0;NSM;;;;;N;;;;;
 0C82;KANNADA SIGN ANUSVARA;Mc;0;L;;;;;N;;;;;
 0C83;KANNADA SIGN VISARGA;Mc;0;L;;;;;N;;;;;
 0C85;KANNADA LETTER A;Lo;0;L;;;;;N;;;;;
@@ -2821,6 +2847,7 @@
 0CEF;KANNADA DIGIT NINE;Nd;0;L;;9;9;9;N;;;;;
 0CF1;KANNADA SIGN JIHVAMULIYA;Lo;0;L;;;;;N;;;;;
 0CF2;KANNADA SIGN UPADHMANIYA;Lo;0;L;;;;;N;;;;;
+0D01;MALAYALAM SIGN CANDRABINDU;Mn;0;NSM;;;;;N;;;;;
 0D02;MALAYALAM SIGN ANUSVARA;Mc;0;L;;;;;N;;;;;
 0D03;MALAYALAM SIGN VISARGA;Mc;0;L;;;;;N;;;;;
 0D05;MALAYALAM LETTER A;Lo;0;L;;;;;N;;;;;
@@ -2996,6 +3023,16 @@
 0DDD;SINHALA VOWEL SIGN KOMBUVA HAA DIGA AELA-PILLA;Mc;0;L;0DDC 0DCA;;;;N;;;;;
 0DDE;SINHALA VOWEL SIGN KOMBUVA HAA GAYANUKITTA;Mc;0;L;0DD9 0DDF;;;;N;;;;;
 0DDF;SINHALA VOWEL SIGN GAYANUKITTA;Mc;0;L;;;;;N;;;;;
+0DE6;SINHALA LITH DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;;
+0DE7;SINHALA LITH DIGIT ONE;Nd;0;L;;1;1;1;N;;;;;
+0DE8;SINHALA LITH DIGIT TWO;Nd;0;L;;2;2;2;N;;;;;
+0DE9;SINHALA LITH DIGIT THREE;Nd;0;L;;3;3;3;N;;;;;
+0DEA;SINHALA LITH DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;;
+0DEB;SINHALA LITH DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;;
+0DEC;SINHALA LITH DIGIT SIX;Nd;0;L;;6;6;6;N;;;;;
+0DED;SINHALA LITH DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;;
+0DEE;SINHALA LITH DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;;
+0DEF;SINHALA LITH DIGIT NINE;Nd;0;L;;9;9;9;N;;;;;
 0DF2;SINHALA VOWEL SIGN DIGA GAETTA-PILLA;Mc;0;L;;;;;N;;;;;
 0DF3;SINHALA VOWEL SIGN DIGA GAYANUKITTA;Mc;0;L;;;;;N;;;;;
 0DF4;SINHALA PUNCTUATION KUNDDALIYA;Po;0;L;;;;;N;;;;;
@@ -5087,6 +5124,14 @@
 16EE;RUNIC ARLAUG SYMBOL;Nl;0;L;;;;17;N;;;;;
 16EF;RUNIC TVIMADUR SYMBOL;Nl;0;L;;;;18;N;;;;;
 16F0;RUNIC BELGTHOR SYMBOL;Nl;0;L;;;;19;N;;;;;
+16F1;RUNIC LETTER K;Lo;0;L;;;;;N;;;;;
+16F2;RUNIC LETTER SH;Lo;0;L;;;;;N;;;;;
+16F3;RUNIC LETTER OO;Lo;0;L;;;;;N;;;;;
+16F4;RUNIC LETTER FRANKS CASKET OS;Lo;0;L;;;;;N;;;;;
+16F5;RUNIC LETTER FRANKS CASKET IS;Lo;0;L;;;;;N;;;;;
+16F6;RUNIC LETTER FRANKS CASKET EH;Lo;0;L;;;;;N;;;;;
+16F7;RUNIC LETTER FRANKS CASKET AC;Lo;0;L;;;;;N;;;;;
+16F8;RUNIC LETTER FRANKS CASKET AESC;Lo;0;L;;;;;N;;;;;
 1700;TAGALOG LETTER A;Lo;0;L;;;;;N;;;;;
 1701;TAGALOG LETTER I;Lo;0;L;;;;;N;;;;;
 1702;TAGALOG LETTER U;Lo;0;L;;;;;N;;;;;
@@ -5296,7 +5341,7 @@
 180B;MONGOLIAN FREE VARIATION SELECTOR ONE;Mn;0;NSM;;;;;N;;;;;
 180C;MONGOLIAN FREE VARIATION SELECTOR TWO;Mn;0;NSM;;;;;N;;;;;
 180D;MONGOLIAN FREE VARIATION SELECTOR THREE;Mn;0;NSM;;;;;N;;;;;
-180E;MONGOLIAN VOWEL SEPARATOR;Zs;0;WS;;;;;N;;;;;
+180E;MONGOLIAN VOWEL SEPARATOR;Cf;0;BN;;;;;N;;;;;
 1810;MONGOLIAN DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;;
 1811;MONGOLIAN DIGIT ONE;Nd;0;L;;1;1;1;N;;;;;
 1812;MONGOLIAN DIGIT TWO;Nd;0;L;;2;2;2;N;;;;;
@@ -5537,6 +5582,8 @@
 191A;LIMBU LETTER SSA;Lo;0;L;;;;;N;;;;;
 191B;LIMBU LETTER SA;Lo;0;L;;;;;N;;;;;
 191C;LIMBU LETTER HA;Lo;0;L;;;;;N;;;;;
+191D;LIMBU LETTER GYAN;Lo;0;L;;;;;N;;;;;
+191E;LIMBU LETTER TRA;Lo;0;L;;;;;N;;;;;
 1920;LIMBU VOWEL SIGN A;Mn;0;NSM;;;;;N;;;;;
 1921;LIMBU VOWEL SIGN I;Mn;0;NSM;;;;;N;;;;;
 1922;LIMBU VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;;
@@ -5751,7 +5798,7 @@
 1A18;BUGINESE VOWEL SIGN U;Mn;220;NSM;;;;;N;;;;;
 1A19;BUGINESE VOWEL SIGN E;Mc;0;L;;;;;N;;;;;
 1A1A;BUGINESE VOWEL SIGN O;Mc;0;L;;;;;N;;;;;
-1A1B;BUGINESE VOWEL SIGN AE;Mc;0;L;;;;;N;;;;;
+1A1B;BUGINESE VOWEL SIGN AE;Mn;0;NSM;;;;;N;;;;;
 1A1E;BUGINESE PALLAWA;Po;0;L;;;;;N;;;;;
 1A1F;BUGINESE END OF SECTION;Po;0;L;;;;;N;;;;;
 1A20;TAI THAM LETTER HIGH KA;Lo;0;L;;;;;N;;;;;
@@ -5881,6 +5928,21 @@
 1AAB;TAI THAM SIGN SATKAANKUU;Po;0;L;;;;;N;;;;;
 1AAC;TAI THAM SIGN HANG;Po;0;L;;;;;N;;;;;
 1AAD;TAI THAM SIGN CAANG;Po;0;L;;;;;N;;;;;
+1AB0;COMBINING DOUBLED CIRCUMFLEX ACCENT;Mn;230;NSM;;;;;N;;;;;
+1AB1;COMBINING DIAERESIS-RING;Mn;230;NSM;;;;;N;;;;;
+1AB2;COMBINING INFINITY;Mn;230;NSM;;;;;N;;;;;
+1AB3;COMBINING DOWNWARDS ARROW;Mn;230;NSM;;;;;N;;;;;
+1AB4;COMBINING TRIPLE DOT;Mn;230;NSM;;;;;N;;;;;
+1AB5;COMBINING X-X BELOW;Mn;220;NSM;;;;;N;;;;;
+1AB6;COMBINING WIGGLY LINE BELOW;Mn;220;NSM;;;;;N;;;;;
+1AB7;COMBINING OPEN MARK BELOW;Mn;220;NSM;;;;;N;;;;;
+1AB8;COMBINING DOUBLE OPEN MARK BELOW;Mn;220;NSM;;;;;N;;;;;
+1AB9;COMBINING LIGHT CENTRALIZATION STROKE BELOW;Mn;220;NSM;;;;;N;;;;;
+1ABA;COMBINING STRONG CENTRALIZATION STROKE BELOW;Mn;220;NSM;;;;;N;;;;;
+1ABB;COMBINING PARENTHESES ABOVE;Mn;230;NSM;;;;;N;;;;;
+1ABC;COMBINING DOUBLE PARENTHESES ABOVE;Mn;230;NSM;;;;;N;;;;;
+1ABD;COMBINING PARENTHESES BELOW;Mn;220;NSM;;;;;N;;;;;
+1ABE;COMBINING PARENTHESES OVERLAY;Me;0;NSM;;;;;N;;;;;
 1B00;BALINESE SIGN ULU RICEM;Mn;0;NSM;;;;;N;;;;;
 1B01;BALINESE SIGN ULU CANDRA;Mn;0;NSM;;;;;N;;;;;
 1B02;BALINESE SIGN CECEK;Mn;0;NSM;;;;;N;;;;;
@@ -6046,8 +6108,8 @@
 1BA9;SUNDANESE VOWEL SIGN PANEULEUNG;Mn;0;NSM;;;;;N;;;;;
 1BAA;SUNDANESE SIGN PAMAAEH;Mc;9;L;;;;;N;;;;;
 1BAB;SUNDANESE SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;;
-1BAC;SUNDANESE CONSONANT SIGN PASANGAN MA;Mc;0;L;;;;;N;;;;;
-1BAD;SUNDANESE CONSONANT SIGN PASANGAN WA;Mc;0;L;;;;;N;;;;;
+1BAC;SUNDANESE CONSONANT SIGN PASANGAN MA;Mn;0;NSM;;;;;N;;;;;
+1BAD;SUNDANESE CONSONANT SIGN PASANGAN WA;Mn;0;NSM;;;;;N;;;;;
 1BAE;SUNDANESE LETTER KHA;Lo;0;L;;;;;N;;;;;
 1BAF;SUNDANESE LETTER SYA;Lo;0;L;;;;;N;;;;;
 1BB0;SUNDANESE DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;;
@@ -6291,6 +6353,8 @@
 1CF4;VEDIC TONE CANDRA ABOVE;Mn;230;NSM;;;;;N;;;;;
 1CF5;VEDIC SIGN JIHVAMULIYA;Lo;0;L;;;;;N;;;;;
 1CF6;VEDIC SIGN UPADHMANIYA;Lo;0;L;;;;;N;;;;;
+1CF8;VEDIC TONE RING ABOVE;Mn;230;NSM;;;;;N;;;;;
+1CF9;VEDIC TONE DOUBLE RING ABOVE;Mn;230;NSM;;;;;N;;;;;
 1D00;LATIN LETTER SMALL CAPITAL A;Ll;0;L;;;;;N;;;;;
 1D01;LATIN LETTER SMALL CAPITAL AE;Ll;0;L;;;;;N;;;;;
 1D02;LATIN SMALL LETTER TURNED AE;Ll;0;L;;;;;N;;;;;
@@ -6522,6 +6586,21 @@
 1DE4;COMBINING LATIN SMALL LETTER S;Mn;230;NSM;;;;;N;;;;;
 1DE5;COMBINING LATIN SMALL LETTER LONG S;Mn;230;NSM;;;;;N;;;;;
 1DE6;COMBINING LATIN SMALL LETTER Z;Mn;230;NSM;;;;;N;;;;;
+1DE7;COMBINING LATIN SMALL LETTER ALPHA;Mn;230;NSM;;;;;N;;;;;
+1DE8;COMBINING LATIN SMALL LETTER B;Mn;230;NSM;;;;;N;;;;;
+1DE9;COMBINING LATIN SMALL LETTER BETA;Mn;230;NSM;;;;;N;;;;;
+1DEA;COMBINING LATIN SMALL LETTER SCHWA;Mn;230;NSM;;;;;N;;;;;
+1DEB;COMBINING LATIN SMALL LETTER F;Mn;230;NSM;;;;;N;;;;;
+1DEC;COMBINING LATIN SMALL LETTER L WITH DOUBLE MIDDLE TILDE;Mn;230;NSM;;;;;N;;;;;
+1DED;COMBINING LATIN SMALL LETTER O WITH LIGHT CENTRALIZATION STROKE;Mn;230;NSM;;;;;N;;;;;
+1DEE;COMBINING LATIN SMALL LETTER P;Mn;230;NSM;;;;;N;;;;;
+1DEF;COMBINING LATIN SMALL LETTER ESH;Mn;230;NSM;;;;;N;;;;;
+1DF0;COMBINING LATIN SMALL LETTER U WITH LIGHT CENTRALIZATION STROKE;Mn;230;NSM;;;;;N;;;;;
+1DF1;COMBINING LATIN SMALL LETTER W;Mn;230;NSM;;;;;N;;;;;
+1DF2;COMBINING LATIN SMALL LETTER A WITH DIAERESIS;Mn;230;NSM;;;;;N;;;;;
+1DF3;COMBINING LATIN SMALL LETTER O WITH DIAERESIS;Mn;230;NSM;;;;;N;;;;;
+1DF4;COMBINING LATIN SMALL LETTER U WITH DIAERESIS;Mn;230;NSM;;;;;N;;;;;
+1DF5;COMBINING UP TACK ABOVE;Mn;230;NSM;;;;;N;;;;;
 1DFC;COMBINING DOUBLE INVERTED BREVE BELOW;Mn;233;NSM;;;;;N;;;;;
 1DFD;COMBINING ALMOST EQUAL TO BELOW;Mn;220;NSM;;;;;N;;;;;
 1DFE;COMBINING LEFT ARROWHEAD ABOVE;Mn;230;NSM;;;;;N;;;;;
@@ -7116,6 +7195,10 @@
 2062;INVISIBLE TIMES;Cf;0;BN;;;;;N;;;;;
 2063;INVISIBLE SEPARATOR;Cf;0;BN;;;;;N;;;;;
 2064;INVISIBLE PLUS;Cf;0;BN;;;;;N;;;;;
+2066;LEFT-TO-RIGHT ISOLATE;Cf;0;LRI;;;;;N;;;;;
+2067;RIGHT-TO-LEFT ISOLATE;Cf;0;RLI;;;;;N;;;;;
+2068;FIRST STRONG ISOLATE;Cf;0;FSI;;;;;N;;;;;
+2069;POP DIRECTIONAL ISOLATE;Cf;0;PDI;;;;;N;;;;;
 206A;INHIBIT SYMMETRIC SWAPPING;Cf;0;BN;;;;;N;;;;;
 206B;ACTIVATE SYMMETRIC SWAPPING;Cf;0;BN;;;;;N;;;;;
 206C;INHIBIT ARABIC FORM SHAPING;Cf;0;BN;;;;;N;;;;;
@@ -7191,6 +7274,9 @@
 20B8;TENGE SIGN;Sc;0;ET;;;;;N;;;;;
 20B9;INDIAN RUPEE SIGN;Sc;0;ET;;;;;N;;;;;
 20BA;TURKISH LIRA SIGN;Sc;0;ET;;;;;N;;;;;
+20BB;NORDIC MARK SIGN;Sc;0;ET;;;;;N;;;;;
+20BC;MANAT SIGN;Sc;0;ET;;;;;N;;;;;
+20BD;RUBLE SIGN;Sc;0;ET;;;;;N;;;;;
 20D0;COMBINING LEFT HARPOON ABOVE;Mn;230;NSM;;;;;N;NON-SPACING LEFT HARPOON ABOVE;;;;
 20D1;COMBINING RIGHT HARPOON ABOVE;Mn;230;NSM;;;;;N;NON-SPACING RIGHT HARPOON ABOVE;;;;
 20D2;COMBINING LONG VERTICAL LINE OVERLAY;Mn;1;NSM;;;;;N;NON-SPACING LONG VERTICAL BAR OVERLAY;;;;
@@ -7738,10 +7824,10 @@
 2305;PROJECTIVE;So;0;ON;;;;;N;;;;;
 2306;PERSPECTIVE;So;0;ON;;;;;N;;;;;
 2307;WAVY LINE;So;0;ON;;;;;N;;;;;
-2308;LEFT CEILING;Sm;0;ON;;;;;Y;;;;;
-2309;RIGHT CEILING;Sm;0;ON;;;;;Y;;;;;
-230A;LEFT FLOOR;Sm;0;ON;;;;;Y;;;;;
-230B;RIGHT FLOOR;Sm;0;ON;;;;;Y;;;;;
+2308;LEFT CEILING;Ps;0;ON;;;;;Y;;;;;
+2309;RIGHT CEILING;Pe;0;ON;;;;;Y;;;;;
+230A;LEFT FLOOR;Ps;0;ON;;;;;Y;;;;;
+230B;RIGHT FLOOR;Pe;0;ON;;;;;Y;;;;;
 230C;BOTTOM RIGHT CROP;So;0;ON;;;;;N;;;;;
 230D;BOTTOM LEFT CROP;So;0;ON;;;;;N;;;;;
 230E;TOP RIGHT CROP;So;0;ON;;;;;N;;;;;
@@ -7974,6 +8060,13 @@
 23F1;STOPWATCH;So;0;ON;;;;;N;;;;;
 23F2;TIMER CLOCK;So;0;ON;;;;;N;;;;;
 23F3;HOURGLASS WITH FLOWING SAND;So;0;ON;;;;;N;;;;;
+23F4;BLACK MEDIUM LEFT-POINTING TRIANGLE;So;0;ON;;;;;N;;;;;
+23F5;BLACK MEDIUM RIGHT-POINTING TRIANGLE;So;0;ON;;;;;N;;;;;
+23F6;BLACK MEDIUM UP-POINTING TRIANGLE;So;0;ON;;;;;N;;;;;
+23F7;BLACK MEDIUM DOWN-POINTING TRIANGLE;So;0;ON;;;;;N;;;;;
+23F8;DOUBLE VERTICAL BAR;So;0;ON;;;;;N;;;;;
+23F9;BLACK SQUARE FOR STOP;So;0;ON;;;;;N;;;;;
+23FA;BLACK CIRCLE FOR RECORD;So;0;ON;;;;;N;;;;;
 2400;SYMBOL FOR NULL;So;0;ON;;;;;N;GRAPHIC FOR NULL;;;;
 2401;SYMBOL FOR START OF HEADING;So;0;ON;;;;;N;GRAPHIC FOR START OF HEADING;;;;
 2402;SYMBOL FOR START OF TEXT;So;0;ON;;;;;N;GRAPHIC FOR START OF TEXT;;;;
@@ -8696,6 +8789,7 @@
 26FD;FUEL PUMP;So;0;ON;;;;;N;;;;;
 26FE;CUP ON BLACK SQUARE;So;0;ON;;;;;N;;;;;
 26FF;WHITE FLAG WITH HORIZONTAL MIDDLE BLACK STRIPE;So;0;ON;;;;;N;;;;;
+2700;BLACK SAFETY SCISSORS;So;0;ON;;;;;N;;;;;
 2701;UPPER BLADE SCISSORS;So;0;ON;;;;;N;;;;;
 2702;BLACK SCISSORS;So;0;ON;;;;;N;;;;;
 2703;LOWER BLADE SCISSORS;So;0;ON;;;;;N;;;;;
@@ -9796,6 +9890,9 @@
 2B4A;LEFTWARDS ARROW ABOVE ALMOST EQUAL TO;Sm;0;ON;;;;;N;;;;;
 2B4B;LEFTWARDS ARROW ABOVE REVERSE TILDE OPERATOR;Sm;0;ON;;;;;N;;;;;
 2B4C;RIGHTWARDS ARROW ABOVE REVERSE TILDE OPERATOR;Sm;0;ON;;;;;N;;;;;
+2B4D;DOWNWARDS TRIANGLE-HEADED ZIGZAG ARROW;So;0;ON;;;;;N;;;;;
+2B4E;SHORT SLANTED NORTH ARROW;So;0;ON;;;;;N;;;;;
+2B4F;SHORT BACKSLANTED SOUTH ARROW;So;0;ON;;;;;N;;;;;
 2B50;WHITE MEDIUM STAR;So;0;ON;;;;;N;;;;;
 2B51;BLACK SMALL STAR;So;0;ON;;;;;N;;;;;
 2B52;WHITE SMALL STAR;So;0;ON;;;;;N;;;;;
@@ -9806,6 +9903,118 @@
 2B57;HEAVY CIRCLE WITH CIRCLE INSIDE;So;0;ON;;;;;N;;;;;
 2B58;HEAVY CIRCLE;So;0;ON;;;;;N;;;;;
 2B59;HEAVY CIRCLED SALTIRE;So;0;ON;;;;;N;;;;;
+2B5A;SLANTED NORTH ARROW WITH HOOKED HEAD;So;0;ON;;;;;N;;;;;
+2B5B;BACKSLANTED SOUTH ARROW WITH HOOKED TAIL;So;0;ON;;;;;N;;;;;
+2B5C;SLANTED NORTH ARROW WITH HORIZONTAL TAIL;So;0;ON;;;;;N;;;;;
+2B5D;BACKSLANTED SOUTH ARROW WITH HORIZONTAL TAIL;So;0;ON;;;;;N;;;;;
+2B5E;BENT ARROW POINTING DOWNWARDS THEN NORTH EAST;So;0;ON;;;;;N;;;;;
+2B5F;SHORT BENT ARROW POINTING DOWNWARDS THEN NORTH EAST;So;0;ON;;;;;N;;;;;
+2B60;LEFTWARDS TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;;
+2B61;UPWARDS TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;;
+2B62;RIGHTWARDS TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;;
+2B63;DOWNWARDS TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;;
+2B64;LEFT RIGHT TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;;
+2B65;UP DOWN TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;;
+2B66;NORTH WEST TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;;
+2B67;NORTH EAST TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;;
+2B68;SOUTH EAST TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;;
+2B69;SOUTH WEST TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;;
+2B6A;LEFTWARDS TRIANGLE-HEADED DASHED ARROW;So;0;ON;;;;;N;;;;;
+2B6B;UPWARDS TRIANGLE-HEADED DASHED ARROW;So;0;ON;;;;;N;;;;;
+2B6C;RIGHTWARDS TRIANGLE-HEADED DASHED ARROW;So;0;ON;;;;;N;;;;;
+2B6D;DOWNWARDS TRIANGLE-HEADED DASHED ARROW;So;0;ON;;;;;N;;;;;
+2B6E;CLOCKWISE TRIANGLE-HEADED OPEN CIRCLE ARROW;So;0;ON;;;;;N;;;;;
+2B6F;ANTICLOCKWISE TRIANGLE-HEADED OPEN CIRCLE ARROW;So;0;ON;;;;;N;;;;;
+2B70;LEFTWARDS TRIANGLE-HEADED ARROW TO BAR;So;0;ON;;;;;N;;;;;
+2B71;UPWARDS TRIANGLE-HEADED ARROW TO BAR;So;0;ON;;;;;N;;;;;
+2B72;RIGHTWARDS TRIANGLE-HEADED ARROW TO BAR;So;0;ON;;;;;N;;;;;
+2B73;DOWNWARDS TRIANGLE-HEADED ARROW TO BAR;So;0;ON;;;;;N;;;;;
+2B76;NORTH WEST TRIANGLE-HEADED ARROW TO BAR;So;0;ON;;;;;N;;;;;
+2B77;NORTH EAST TRIANGLE-HEADED ARROW TO BAR;So;0;ON;;;;;N;;;;;
+2B78;SOUTH EAST TRIANGLE-HEADED ARROW TO BAR;So;0;ON;;;;;N;;;;;
+2B79;SOUTH WEST TRIANGLE-HEADED ARROW TO BAR;So;0;ON;;;;;N;;;;;
+2B7A;LEFTWARDS TRIANGLE-HEADED ARROW WITH DOUBLE HORIZONTAL STROKE;So;0;ON;;;;;N;;;;;
+2B7B;UPWARDS TRIANGLE-HEADED ARROW WITH DOUBLE HORIZONTAL STROKE;So;0;ON;;;;;N;;;;;
+2B7C;RIGHTWARDS TRIANGLE-HEADED ARROW WITH DOUBLE HORIZONTAL STROKE;So;0;ON;;;;;N;;;;;
+2B7D;DOWNWARDS TRIANGLE-HEADED ARROW WITH DOUBLE HORIZONTAL STROKE;So;0;ON;;;;;N;;;;;
+2B7E;HORIZONTAL TAB KEY;So;0;ON;;;;;N;;;;;
+2B7F;VERTICAL TAB KEY;So;0;ON;;;;;N;;;;;
+2B80;LEFTWARDS TRIANGLE-HEADED ARROW OVER RIGHTWARDS TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;;
+2B81;UPWARDS TRIANGLE-HEADED ARROW LEFTWARDS OF DOWNWARDS TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;;
+2B82;RIGHTWARDS TRIANGLE-HEADED ARROW OVER LEFTWARDS TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;;
+2B83;DOWNWARDS TRIANGLE-HEADED ARROW LEFTWARDS OF UPWARDS TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;;
+2B84;LEFTWARDS TRIANGLE-HEADED PAIRED ARROWS;So;0;ON;;;;;N;;;;;
+2B85;UPWARDS TRIANGLE-HEADED PAIRED ARROWS;So;0;ON;;;;;N;;;;;
+2B86;RIGHTWARDS TRIANGLE-HEADED PAIRED ARROWS;So;0;ON;;;;;N;;;;;
+2B87;DOWNWARDS TRIANGLE-HEADED PAIRED ARROWS;So;0;ON;;;;;N;;;;;
+2B88;LEFTWARDS BLACK CIRCLED WHITE ARROW;So;0;ON;;;;;N;;;;;
+2B89;UPWARDS BLACK CIRCLED WHITE ARROW;So;0;ON;;;;;N;;;;;
+2B8A;RIGHTWARDS BLACK CIRCLED WHITE ARROW;So;0;ON;;;;;N;;;;;
+2B8B;DOWNWARDS BLACK CIRCLED WHITE ARROW;So;0;ON;;;;;N;;;;;
+2B8C;ANTICLOCKWISE TRIANGLE-HEADED RIGHT U-SHAPED ARROW;So;0;ON;;;;;N;;;;;
+2B8D;ANTICLOCKWISE TRIANGLE-HEADED BOTTOM U-SHAPED ARROW;So;0;ON;;;;;N;;;;;
+2B8E;ANTICLOCKWISE TRIANGLE-HEADED LEFT U-SHAPED ARROW;So;0;ON;;;;;N;;;;;
+2B8F;ANTICLOCKWISE TRIANGLE-HEADED TOP U-SHAPED ARROW;So;0;ON;;;;;N;;;;;
+2B90;RETURN LEFT;So;0;ON;;;;;N;;;;;
+2B91;RETURN RIGHT;So;0;ON;;;;;N;;;;;
+2B92;NEWLINE LEFT;So;0;ON;;;;;N;;;;;
+2B93;NEWLINE RIGHT;So;0;ON;;;;;N;;;;;
+2B94;FOUR CORNER ARROWS CIRCLING ANTICLOCKWISE;So;0;ON;;;;;N;;;;;
+2B95;RIGHTWARDS BLACK ARROW;So;0;ON;;;;;N;;;;;
+2B98;THREE-D TOP-LIGHTED LEFTWARDS EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+2B99;THREE-D RIGHT-LIGHTED UPWARDS EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+2B9A;THREE-D TOP-LIGHTED RIGHTWARDS EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+2B9B;THREE-D LEFT-LIGHTED DOWNWARDS EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+2B9C;BLACK LEFTWARDS EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+2B9D;BLACK UPWARDS EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+2B9E;BLACK RIGHTWARDS EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+2B9F;BLACK DOWNWARDS EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+2BA0;DOWNWARDS TRIANGLE-HEADED ARROW WITH LONG TIP LEFTWARDS;So;0;ON;;;;;N;;;;;
+2BA1;DOWNWARDS TRIANGLE-HEADED ARROW WITH LONG TIP RIGHTWARDS;So;0;ON;;;;;N;;;;;
+2BA2;UPWARDS TRIANGLE-HEADED ARROW WITH LONG TIP LEFTWARDS;So;0;ON;;;;;N;;;;;
+2BA3;UPWARDS TRIANGLE-HEADED ARROW WITH LONG TIP RIGHTWARDS;So;0;ON;;;;;N;;;;;
+2BA4;LEFTWARDS TRIANGLE-HEADED ARROW WITH LONG TIP UPWARDS;So;0;ON;;;;;N;;;;;
+2BA5;RIGHTWARDS TRIANGLE-HEADED ARROW WITH LONG TIP UPWARDS;So;0;ON;;;;;N;;;;;
+2BA6;LEFTWARDS TRIANGLE-HEADED ARROW WITH LONG TIP DOWNWARDS;So;0;ON;;;;;N;;;;;
+2BA7;RIGHTWARDS TRIANGLE-HEADED ARROW WITH LONG TIP DOWNWARDS;So;0;ON;;;;;N;;;;;
+2BA8;BLACK CURVED DOWNWARDS AND LEFTWARDS ARROW;So;0;ON;;;;;N;;;;;
+2BA9;BLACK CURVED DOWNWARDS AND RIGHTWARDS ARROW;So;0;ON;;;;;N;;;;;
+2BAA;BLACK CURVED UPWARDS AND LEFTWARDS ARROW;So;0;ON;;;;;N;;;;;
+2BAB;BLACK CURVED UPWARDS AND RIGHTWARDS ARROW;So;0;ON;;;;;N;;;;;
+2BAC;BLACK CURVED LEFTWARDS AND UPWARDS ARROW;So;0;ON;;;;;N;;;;;
+2BAD;BLACK CURVED RIGHTWARDS AND UPWARDS ARROW;So;0;ON;;;;;N;;;;;
+2BAE;BLACK CURVED LEFTWARDS AND DOWNWARDS ARROW;So;0;ON;;;;;N;;;;;
+2BAF;BLACK CURVED RIGHTWARDS AND DOWNWARDS ARROW;So;0;ON;;;;;N;;;;;
+2BB0;RIBBON ARROW DOWN LEFT;So;0;ON;;;;;N;;;;;
+2BB1;RIBBON ARROW DOWN RIGHT;So;0;ON;;;;;N;;;;;
+2BB2;RIBBON ARROW UP LEFT;So;0;ON;;;;;N;;;;;
+2BB3;RIBBON ARROW UP RIGHT;So;0;ON;;;;;N;;;;;
+2BB4;RIBBON ARROW LEFT UP;So;0;ON;;;;;N;;;;;
+2BB5;RIBBON ARROW RIGHT UP;So;0;ON;;;;;N;;;;;
+2BB6;RIBBON ARROW LEFT DOWN;So;0;ON;;;;;N;;;;;
+2BB7;RIBBON ARROW RIGHT DOWN;So;0;ON;;;;;N;;;;;
+2BB8;UPWARDS WHITE ARROW FROM BAR WITH HORIZONTAL BAR;So;0;ON;;;;;N;;;;;
+2BB9;UP ARROWHEAD IN A RECTANGLE BOX;So;0;ON;;;;;N;;;;;
+2BBD;BALLOT BOX WITH LIGHT X;So;0;ON;;;;;N;;;;;
+2BBE;CIRCLED X;So;0;ON;;;;;N;;;;;
+2BBF;CIRCLED BOLD X;So;0;ON;;;;;N;;;;;
+2BC0;BLACK SQUARE CENTRED;So;0;ON;;;;;N;;;;;
+2BC1;BLACK DIAMOND CENTRED;So;0;ON;;;;;N;;;;;
+2BC2;TURNED BLACK PENTAGON;So;0;ON;;;;;N;;;;;
+2BC3;HORIZONTAL BLACK OCTAGON;So;0;ON;;;;;N;;;;;
+2BC4;BLACK OCTAGON;So;0;ON;;;;;N;;;;;
+2BC5;BLACK MEDIUM UP-POINTING TRIANGLE CENTRED;So;0;ON;;;;;N;;;;;
+2BC6;BLACK MEDIUM DOWN-POINTING TRIANGLE CENTRED;So;0;ON;;;;;N;;;;;
+2BC7;BLACK MEDIUM LEFT-POINTING TRIANGLE CENTRED;So;0;ON;;;;;N;;;;;
+2BC8;BLACK MEDIUM RIGHT-POINTING TRIANGLE CENTRED;So;0;ON;;;;;N;;;;;
+2BCA;TOP HALF BLACK CIRCLE;So;0;ON;;;;;N;;;;;
+2BCB;BOTTOM HALF BLACK CIRCLE;So;0;ON;;;;;N;;;;;
+2BCC;LIGHT FOUR POINTED BLACK CUSP;So;0;ON;;;;;N;;;;;
+2BCD;ROTATED LIGHT FOUR POINTED BLACK CUSP;So;0;ON;;;;;N;;;;;
+2BCE;WHITE FOUR POINTED CUSP;So;0;ON;;;;;N;;;;;
+2BCF;ROTATED WHITE FOUR POINTED CUSP;So;0;ON;;;;;N;;;;;
+2BD0;SQUARE POSITION INDICATOR;So;0;ON;;;;;N;;;;;
+2BD1;UNCERTAINTY SIGN;So;0;ON;;;;;N;;;;;
 2C00;GLAGOLITIC CAPITAL LETTER AZU;Lu;0;L;;;;;N;;;;2C30;
 2C01;GLAGOLITIC CAPITAL LETTER BUKY;Lu;0;L;;;;;N;;;;2C31;
 2C02;GLAGOLITIC CAPITAL LETTER VEDE;Lu;0;L;;;;;N;;;;2C32;
@@ -10325,6 +10534,13 @@
 2E39;TOP HALF SECTION SIGN;Po;0;ON;;;;;N;;;;;
 2E3A;TWO-EM DASH;Pd;0;ON;;;;;N;;;;;
 2E3B;THREE-EM DASH;Pd;0;ON;;;;;N;;;;;
+2E3C;STENOGRAPHIC FULL STOP;Po;0;ON;;;;;N;;;;;
+2E3D;VERTICAL SIX DOTS;Po;0;ON;;;;;N;;;;;
+2E3E;WIGGLY VERTICAL LINE;Po;0;ON;;;;;N;;;;;
+2E3F;CAPITULUM;Po;0;ON;;;;;N;;;;;
+2E40;DOUBLE HYPHEN;Pd;0;ON;;;;;N;;;;;
+2E41;REVERSED COMMA;Po;0;ON;;;;;N;;;;;
+2E42;DOUBLE LOW-REVERSED-9 QUOTATION MARK;Ps;0;ON;;;;;N;;;;;
 2E80;CJK RADICAL REPEAT;So;0;ON;;;;;N;;;;;
 2E81;CJK RADICAL CLIFF;So;0;ON;;;;;N;;;;;
 2E82;CJK RADICAL SECOND ONE;So;0;ON;;;;;N;;;;;
@@ -13383,6 +13599,12 @@
 A695;CYRILLIC SMALL LETTER HWE;Ll;0;L;;;;;N;;;A694;;A694
 A696;CYRILLIC CAPITAL LETTER SHWE;Lu;0;L;;;;;N;;;;A697;
 A697;CYRILLIC SMALL LETTER SHWE;Ll;0;L;;;;;N;;;A696;;A696
+A698;CYRILLIC CAPITAL LETTER DOUBLE O;Lu;0;L;;;;;N;;;;A699;
+A699;CYRILLIC SMALL LETTER DOUBLE O;Ll;0;L;;;;;N;;;A698;;A698
+A69A;CYRILLIC CAPITAL LETTER CROSSED O;Lu;0;L;;;;;N;;;;A69B;
+A69B;CYRILLIC SMALL LETTER CROSSED O;Ll;0;L;;;;;N;;;A69A;;A69A
+A69C;MODIFIER LETTER CYRILLIC HARD SIGN;Lm;0;L;<super> 044A;;;;N;;;;;
+A69D;MODIFIER LETTER CYRILLIC SOFT SIGN;Lm;0;L;<super> 044C;;;;N;;;;;
 A69F;COMBINING CYRILLIC LETTER IOTIFIED E;Mn;230;NSM;;;;;N;;;;;
 A6A0;BAMUM LETTER A;Lo;0;L;;;;;N;;;;;
 A6A1;BAMUM LETTER KA;Lo;0;L;;;;;N;;;;;
@@ -13619,6 +13841,18 @@
 A791;LATIN SMALL LETTER N WITH DESCENDER;Ll;0;L;;;;;N;;;A790;;A790
 A792;LATIN CAPITAL LETTER C WITH BAR;Lu;0;L;;;;;N;;;;A793;
 A793;LATIN SMALL LETTER C WITH BAR;Ll;0;L;;;;;N;;;A792;;A792
+A794;LATIN SMALL LETTER C WITH PALATAL HOOK;Ll;0;L;;;;;N;;;;;
+A795;LATIN SMALL LETTER H WITH PALATAL HOOK;Ll;0;L;;;;;N;;;;;
+A796;LATIN CAPITAL LETTER B WITH FLOURISH;Lu;0;L;;;;;N;;;;A797;
+A797;LATIN SMALL LETTER B WITH FLOURISH;Ll;0;L;;;;;N;;;A796;;A796
+A798;LATIN CAPITAL LETTER F WITH STROKE;Lu;0;L;;;;;N;;;;A799;
+A799;LATIN SMALL LETTER F WITH STROKE;Ll;0;L;;;;;N;;;A798;;A798
+A79A;LATIN CAPITAL LETTER VOLAPUK AE;Lu;0;L;;;;;N;;;;A79B;
+A79B;LATIN SMALL LETTER VOLAPUK AE;Ll;0;L;;;;;N;;;A79A;;A79A
+A79C;LATIN CAPITAL LETTER VOLAPUK OE;Lu;0;L;;;;;N;;;;A79D;
+A79D;LATIN SMALL LETTER VOLAPUK OE;Ll;0;L;;;;;N;;;A79C;;A79C
+A79E;LATIN CAPITAL LETTER VOLAPUK UE;Lu;0;L;;;;;N;;;;A79F;
+A79F;LATIN SMALL LETTER VOLAPUK UE;Ll;0;L;;;;;N;;;A79E;;A79E
 A7A0;LATIN CAPITAL LETTER G WITH OBLIQUE STROKE;Lu;0;L;;;;;N;;;;A7A1;
 A7A1;LATIN SMALL LETTER G WITH OBLIQUE STROKE;Ll;0;L;;;;;N;;;A7A0;;A7A0
 A7A2;LATIN CAPITAL LETTER K WITH OBLIQUE STROKE;Lu;0;L;;;;;N;;;;A7A3;
@@ -13630,6 +13864,12 @@
 A7A8;LATIN CAPITAL LETTER S WITH OBLIQUE STROKE;Lu;0;L;;;;;N;;;;A7A9;
 A7A9;LATIN SMALL LETTER S WITH OBLIQUE STROKE;Ll;0;L;;;;;N;;;A7A8;;A7A8
 A7AA;LATIN CAPITAL LETTER H WITH HOOK;Lu;0;L;;;;;N;;;;0266;
+A7AB;LATIN CAPITAL LETTER REVERSED OPEN E;Lu;0;L;;;;;N;;;;025C;
+A7AC;LATIN CAPITAL LETTER SCRIPT G;Lu;0;L;;;;;N;;;;0261;
+A7AD;LATIN CAPITAL LETTER L WITH BELT;Lu;0;L;;;;;N;;;;026C;
+A7B0;LATIN CAPITAL LETTER TURNED K;Lu;0;L;;;;;N;;;;029E;
+A7B1;LATIN CAPITAL LETTER TURNED T;Lu;0;L;;;;;N;;;;0287;
+A7F7;LATIN EPIGRAPHIC LETTER SIDEWAYS I;Lo;0;L;;;;;N;;;;;
 A7F8;MODIFIER LETTER CAPITAL H WITH STROKE;Lm;0;L;<super> 0126;;;;N;;;;;
 A7F9;MODIFIER LETTER SMALL LIGATURE OE;Lm;0;L;<super> 0153;;;;N;;;;;
 A7FA;LATIN LETTER SMALL CAPITAL TURNED M;Ll;0;L;;;;;N;;;;;
@@ -14062,6 +14302,37 @@
 A9D9;JAVANESE DIGIT NINE;Nd;0;L;;9;9;9;N;;;;;
 A9DE;JAVANESE PADA TIRTA TUMETES;Po;0;L;;;;;N;;;;;
 A9DF;JAVANESE PADA ISEN-ISEN;Po;0;L;;;;;N;;;;;
+A9E0;MYANMAR LETTER SHAN GHA;Lo;0;L;;;;;N;;;;;
+A9E1;MYANMAR LETTER SHAN CHA;Lo;0;L;;;;;N;;;;;
+A9E2;MYANMAR LETTER SHAN JHA;Lo;0;L;;;;;N;;;;;
+A9E3;MYANMAR LETTER SHAN NNA;Lo;0;L;;;;;N;;;;;
+A9E4;MYANMAR LETTER SHAN BHA;Lo;0;L;;;;;N;;;;;
+A9E5;MYANMAR SIGN SHAN SAW;Mn;0;NSM;;;;;N;;;;;
+A9E6;MYANMAR MODIFIER LETTER SHAN REDUPLICATION;Lm;0;L;;;;;N;;;;;
+A9E7;MYANMAR LETTER TAI LAING NYA;Lo;0;L;;;;;N;;;;;
+A9E8;MYANMAR LETTER TAI LAING FA;Lo;0;L;;;;;N;;;;;
+A9E9;MYANMAR LETTER TAI LAING GA;Lo;0;L;;;;;N;;;;;
+A9EA;MYANMAR LETTER TAI LAING GHA;Lo;0;L;;;;;N;;;;;
+A9EB;MYANMAR LETTER TAI LAING JA;Lo;0;L;;;;;N;;;;;
+A9EC;MYANMAR LETTER TAI LAING JHA;Lo;0;L;;;;;N;;;;;
+A9ED;MYANMAR LETTER TAI LAING DDA;Lo;0;L;;;;;N;;;;;
+A9EE;MYANMAR LETTER TAI LAING DDHA;Lo;0;L;;;;;N;;;;;
+A9EF;MYANMAR LETTER TAI LAING NNA;Lo;0;L;;;;;N;;;;;
+A9F0;MYANMAR TAI LAING DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;;
+A9F1;MYANMAR TAI LAING DIGIT ONE;Nd;0;L;;1;1;1;N;;;;;
+A9F2;MYANMAR TAI LAING DIGIT TWO;Nd;0;L;;2;2;2;N;;;;;
+A9F3;MYANMAR TAI LAING DIGIT THREE;Nd;0;L;;3;3;3;N;;;;;
+A9F4;MYANMAR TAI LAING DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;;
+A9F5;MYANMAR TAI LAING DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;;
+A9F6;MYANMAR TAI LAING DIGIT SIX;Nd;0;L;;6;6;6;N;;;;;
+A9F7;MYANMAR TAI LAING DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;;
+A9F8;MYANMAR TAI LAING DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;;
+A9F9;MYANMAR TAI LAING DIGIT NINE;Nd;0;L;;9;9;9;N;;;;;
+A9FA;MYANMAR LETTER TAI LAING LLA;Lo;0;L;;;;;N;;;;;
+A9FB;MYANMAR LETTER TAI LAING DA;Lo;0;L;;;;;N;;;;;
+A9FC;MYANMAR LETTER TAI LAING DHA;Lo;0;L;;;;;N;;;;;
+A9FD;MYANMAR LETTER TAI LAING BA;Lo;0;L;;;;;N;;;;;
+A9FE;MYANMAR LETTER TAI LAING BHA;Lo;0;L;;;;;N;;;;;
 AA00;CHAM LETTER A;Lo;0;L;;;;;N;;;;;
 AA01;CHAM LETTER I;Lo;0;L;;;;;N;;;;;
 AA02;CHAM LETTER U;Lo;0;L;;;;;N;;;;;
@@ -14173,6 +14444,10 @@
 AA79;MYANMAR SYMBOL AITON TWO;So;0;L;;;;;N;;;;;
 AA7A;MYANMAR LETTER AITON RA;Lo;0;L;;;;;N;;;;;
 AA7B;MYANMAR SIGN PAO KAREN TONE;Mc;0;L;;;;;N;;;;;
+AA7C;MYANMAR SIGN TAI LAING TONE-2;Mn;0;NSM;;;;;N;;;;;
+AA7D;MYANMAR SIGN TAI LAING TONE-5;Mc;0;L;;;;;N;;;;;
+AA7E;MYANMAR LETTER SHWE PALAUNG CHA;Lo;0;L;;;;;N;;;;;
+AA7F;MYANMAR LETTER SHWE PALAUNG SHA;Lo;0;L;;;;;N;;;;;
 AA80;TAI VIET LETTER LOW KO;Lo;0;L;;;;;N;;;;;
 AA81;TAI VIET LETTER HIGH KO;Lo;0;L;;;;;N;;;;;
 AA82;TAI VIET LETTER LOW KHO;Lo;0;L;;;;;N;;;;;
@@ -14300,6 +14575,56 @@
 AB2C;ETHIOPIC SYLLABLE BBEE;Lo;0;L;;;;;N;;;;;
 AB2D;ETHIOPIC SYLLABLE BBE;Lo;0;L;;;;;N;;;;;
 AB2E;ETHIOPIC SYLLABLE BBO;Lo;0;L;;;;;N;;;;;
+AB30;LATIN SMALL LETTER BARRED ALPHA;Ll;0;L;;;;;N;;;;;
+AB31;LATIN SMALL LETTER A REVERSED-SCHWA;Ll;0;L;;;;;N;;;;;
+AB32;LATIN SMALL LETTER BLACKLETTER E;Ll;0;L;;;;;N;;;;;
+AB33;LATIN SMALL LETTER BARRED E;Ll;0;L;;;;;N;;;;;
+AB34;LATIN SMALL LETTER E WITH FLOURISH;Ll;0;L;;;;;N;;;;;
+AB35;LATIN SMALL LETTER LENIS F;Ll;0;L;;;;;N;;;;;
+AB36;LATIN SMALL LETTER SCRIPT G WITH CROSSED-TAIL;Ll;0;L;;;;;N;;;;;
+AB37;LATIN SMALL LETTER L WITH INVERTED LAZY S;Ll;0;L;;;;;N;;;;;
+AB38;LATIN SMALL LETTER L WITH DOUBLE MIDDLE TILDE;Ll;0;L;;;;;N;;;;;
+AB39;LATIN SMALL LETTER L WITH MIDDLE RING;Ll;0;L;;;;;N;;;;;
+AB3A;LATIN SMALL LETTER M WITH CROSSED-TAIL;Ll;0;L;;;;;N;;;;;
+AB3B;LATIN SMALL LETTER N WITH CROSSED-TAIL;Ll;0;L;;;;;N;;;;;
+AB3C;LATIN SMALL LETTER ENG WITH CROSSED-TAIL;Ll;0;L;;;;;N;;;;;
+AB3D;LATIN SMALL LETTER BLACKLETTER O;Ll;0;L;;;;;N;;;;;
+AB3E;LATIN SMALL LETTER BLACKLETTER O WITH STROKE;Ll;0;L;;;;;N;;;;;
+AB3F;LATIN SMALL LETTER OPEN O WITH STROKE;Ll;0;L;;;;;N;;;;;
+AB40;LATIN SMALL LETTER INVERTED OE;Ll;0;L;;;;;N;;;;;
+AB41;LATIN SMALL LETTER TURNED OE WITH STROKE;Ll;0;L;;;;;N;;;;;
+AB42;LATIN SMALL LETTER TURNED OE WITH HORIZONTAL STROKE;Ll;0;L;;;;;N;;;;;
+AB43;LATIN SMALL LETTER TURNED O OPEN-O;Ll;0;L;;;;;N;;;;;
+AB44;LATIN SMALL LETTER TURNED O OPEN-O WITH STROKE;Ll;0;L;;;;;N;;;;;
+AB45;LATIN SMALL LETTER STIRRUP R;Ll;0;L;;;;;N;;;;;
+AB46;LATIN LETTER SMALL CAPITAL R WITH RIGHT LEG;Ll;0;L;;;;;N;;;;;
+AB47;LATIN SMALL LETTER R WITHOUT HANDLE;Ll;0;L;;;;;N;;;;;
+AB48;LATIN SMALL LETTER DOUBLE R;Ll;0;L;;;;;N;;;;;
+AB49;LATIN SMALL LETTER R WITH CROSSED-TAIL;Ll;0;L;;;;;N;;;;;
+AB4A;LATIN SMALL LETTER DOUBLE R WITH CROSSED-TAIL;Ll;0;L;;;;;N;;;;;
+AB4B;LATIN SMALL LETTER SCRIPT R;Ll;0;L;;;;;N;;;;;
+AB4C;LATIN SMALL LETTER SCRIPT R WITH RING;Ll;0;L;;;;;N;;;;;
+AB4D;LATIN SMALL LETTER BASELINE ESH;Ll;0;L;;;;;N;;;;;
+AB4E;LATIN SMALL LETTER U WITH SHORT RIGHT LEG;Ll;0;L;;;;;N;;;;;
+AB4F;LATIN SMALL LETTER U BAR WITH SHORT RIGHT LEG;Ll;0;L;;;;;N;;;;;
+AB50;LATIN SMALL LETTER UI;Ll;0;L;;;;;N;;;;;
+AB51;LATIN SMALL LETTER TURNED UI;Ll;0;L;;;;;N;;;;;
+AB52;LATIN SMALL LETTER U WITH LEFT HOOK;Ll;0;L;;;;;N;;;;;
+AB53;LATIN SMALL LETTER CHI;Ll;0;L;;;;;N;;;;;
+AB54;LATIN SMALL LETTER CHI WITH LOW RIGHT RING;Ll;0;L;;;;;N;;;;;
+AB55;LATIN SMALL LETTER CHI WITH LOW LEFT SERIF;Ll;0;L;;;;;N;;;;;
+AB56;LATIN SMALL LETTER X WITH LOW RIGHT RING;Ll;0;L;;;;;N;;;;;
+AB57;LATIN SMALL LETTER X WITH LONG LEFT LEG;Ll;0;L;;;;;N;;;;;
+AB58;LATIN SMALL LETTER X WITH LONG LEFT LEG AND LOW RIGHT RING;Ll;0;L;;;;;N;;;;;
+AB59;LATIN SMALL LETTER X WITH LONG LEFT LEG WITH SERIF;Ll;0;L;;;;;N;;;;;
+AB5A;LATIN SMALL LETTER Y WITH SHORT RIGHT LEG;Ll;0;L;;;;;N;;;;;
+AB5B;MODIFIER BREVE WITH INVERTED BREVE;Sk;0;L;;;;;N;;;;;
+AB5C;MODIFIER LETTER SMALL HENG;Lm;0;L;<super> A727;;;;N;;;;;
+AB5D;MODIFIER LETTER SMALL L WITH INVERTED LAZY S;Lm;0;L;<super> AB37;;;;N;;;;;
+AB5E;MODIFIER LETTER SMALL L WITH MIDDLE TILDE;Lm;0;L;<super> 026B;;;;N;;;;;
+AB5F;MODIFIER LETTER SMALL U WITH LEFT HOOK;Lm;0;L;<super> AB52;;;;N;;;;;
+AB64;LATIN SMALL LETTER INVERTED ALPHA;Ll;0;L;;;;;N;;;;;
+AB65;GREEK LETTER SMALL CAPITAL OMEGA;Ll;0;L;;;;;N;;;;;
 ABC0;MEETEI MAYEK LETTER KOK;Lo;0;L;;;;;N;;;;;
 ABC1;MEETEI MAYEK LETTER SAM;Lo;0;L;;;;;N;;;;;
 ABC2;MEETEI MAYEK LETTER LAI;Lo;0;L;;;;;N;;;;;
@@ -15445,8 +15770,8 @@
 FD3B;ARABIC LIGATURE ZAH WITH MEEM MEDIAL FORM;Lo;0;AL;<medial> 0638 0645;;;;N;;;;;
 FD3C;ARABIC LIGATURE ALEF WITH FATHATAN FINAL FORM;Lo;0;AL;<final> 0627 064B;;;;N;;;;;
 FD3D;ARABIC LIGATURE ALEF WITH FATHATAN ISOLATED FORM;Lo;0;AL;<isolated> 0627 064B;;;;N;;;;;
-FD3E;ORNATE LEFT PARENTHESIS;Ps;0;ON;;;;;N;;;;;
-FD3F;ORNATE RIGHT PARENTHESIS;Pe;0;ON;;;;;N;;;;;
+FD3E;ORNATE LEFT PARENTHESIS;Pe;0;ON;;;;;N;;;;;
+FD3F;ORNATE RIGHT PARENTHESIS;Ps;0;ON;;;;;N;;;;;
 FD50;ARABIC LIGATURE TEH WITH JEEM WITH MEEM INITIAL FORM;Lo;0;AL;<initial> 062A 062C 0645;;;;N;;;;;
 FD51;ARABIC LIGATURE TEH WITH HAH WITH JEEM FINAL FORM;Lo;0;AL;<final> 062A 062D 062C;;;;N;;;;;
 FD52;ARABIC LIGATURE TEH WITH HAH WITH JEEM INITIAL FORM;Lo;0;AL;<initial> 062A 062D 062C;;;;N;;;;;
@@ -15612,6 +15937,13 @@
 FE24;COMBINING MACRON LEFT HALF;Mn;230;NSM;;;;;N;;;;;
 FE25;COMBINING MACRON RIGHT HALF;Mn;230;NSM;;;;;N;;;;;
 FE26;COMBINING CONJOINING MACRON;Mn;230;NSM;;;;;N;;;;;
+FE27;COMBINING LIGATURE LEFT HALF BELOW;Mn;220;NSM;;;;;N;;;;;
+FE28;COMBINING LIGATURE RIGHT HALF BELOW;Mn;220;NSM;;;;;N;;;;;
+FE29;COMBINING TILDE LEFT HALF BELOW;Mn;220;NSM;;;;;N;;;;;
+FE2A;COMBINING TILDE RIGHT HALF BELOW;Mn;220;NSM;;;;;N;;;;;
+FE2B;COMBINING MACRON LEFT HALF BELOW;Mn;220;NSM;;;;;N;;;;;
+FE2C;COMBINING MACRON RIGHT HALF BELOW;Mn;220;NSM;;;;;N;;;;;
+FE2D;COMBINING CONJOINING MACRON BELOW;Mn;220;NSM;;;;;N;;;;;
 FE30;PRESENTATION FORM FOR VERTICAL TWO DOT LEADER;Po;0;ON;<vertical> 2025;;;;N;GLYPH FOR VERTICAL TWO DOT LEADER;;;;
 FE31;PRESENTATION FORM FOR VERTICAL EM DASH;Pd;0;ON;<vertical> 2014;;;;N;GLYPH FOR VERTICAL EM DASH;;;;
 FE32;PRESENTATION FORM FOR VERTICAL EN DASH;Pd;0;ON;<vertical> 2013;;;;N;GLYPH FOR VERTICAL EN DASH;;;;
@@ -16384,6 +16716,8 @@
 10188;GREEK GRAMMA SIGN;So;0;ON;;;;;N;;;;;
 10189;GREEK TRYBLION BASE SIGN;So;0;ON;;;;;N;;;;;
 1018A;GREEK ZERO SIGN;No;0;ON;;;;0;N;;;;;
+1018B;GREEK ONE QUARTER SIGN;No;0;ON;;;;1/4;N;;;;;
+1018C;GREEK SINUSOID SIGN;So;0;ON;;;;;N;;;;;
 10190;ROMAN SEXTANS SIGN;So;0;ON;;;;;N;;;;;
 10191;ROMAN UNCIA SIGN;So;0;ON;;;;;N;;;;;
 10192;ROMAN SEMUNCIA SIGN;So;0;ON;;;;;N;;;;;
@@ -16396,6 +16730,7 @@
 10199;ROMAN DUPONDIUS SIGN;So;0;ON;;;;;N;;;;;
 1019A;ROMAN AS SIGN;So;0;ON;;;;;N;;;;;
 1019B;ROMAN CENTURIAL SIGN;So;0;ON;;;;;N;;;;;
+101A0;GREEK SYMBOL TAU RHO;So;0;ON;;;;;N;;;;;
 101D0;PHAISTOS DISC SIGN PEDESTRIAN;So;0;L;;;;;N;;;;;
 101D1;PHAISTOS DISC SIGN PLUMED HEAD;So;0;L;;;;;N;;;;;
 101D2;PHAISTOS DISC SIGN TATTOOED HEAD;So;0;L;;;;;N;;;;;
@@ -16520,6 +16855,34 @@
 102CE;CARIAN LETTER LD2;Lo;0;L;;;;;N;;;;;
 102CF;CARIAN LETTER E2;Lo;0;L;;;;;N;;;;;
 102D0;CARIAN LETTER UUU3;Lo;0;L;;;;;N;;;;;
+102E0;COPTIC EPACT THOUSANDS MARK;Mn;220;NSM;;;;;N;;;;;
+102E1;COPTIC EPACT DIGIT ONE;No;0;EN;;;;1;N;;;;;
+102E2;COPTIC EPACT DIGIT TWO;No;0;EN;;;;2;N;;;;;
+102E3;COPTIC EPACT DIGIT THREE;No;0;EN;;;;3;N;;;;;
+102E4;COPTIC EPACT DIGIT FOUR;No;0;EN;;;;4;N;;;;;
+102E5;COPTIC EPACT DIGIT FIVE;No;0;EN;;;;5;N;;;;;
+102E6;COPTIC EPACT DIGIT SIX;No;0;EN;;;;6;N;;;;;
+102E7;COPTIC EPACT DIGIT SEVEN;No;0;EN;;;;7;N;;;;;
+102E8;COPTIC EPACT DIGIT EIGHT;No;0;EN;;;;8;N;;;;;
+102E9;COPTIC EPACT DIGIT NINE;No;0;EN;;;;9;N;;;;;
+102EA;COPTIC EPACT NUMBER TEN;No;0;EN;;;;10;N;;;;;
+102EB;COPTIC EPACT NUMBER TWENTY;No;0;EN;;;;20;N;;;;;
+102EC;COPTIC EPACT NUMBER THIRTY;No;0;EN;;;;30;N;;;;;
+102ED;COPTIC EPACT NUMBER FORTY;No;0;EN;;;;40;N;;;;;
+102EE;COPTIC EPACT NUMBER FIFTY;No;0;EN;;;;50;N;;;;;
+102EF;COPTIC EPACT NUMBER SIXTY;No;0;EN;;;;60;N;;;;;
+102F0;COPTIC EPACT NUMBER SEVENTY;No;0;EN;;;;70;N;;;;;
+102F1;COPTIC EPACT NUMBER EIGHTY;No;0;EN;;;;80;N;;;;;
+102F2;COPTIC EPACT NUMBER NINETY;No;0;EN;;;;90;N;;;;;
+102F3;COPTIC EPACT NUMBER ONE HUNDRED;No;0;EN;;;;100;N;;;;;
+102F4;COPTIC EPACT NUMBER TWO HUNDRED;No;0;EN;;;;200;N;;;;;
+102F5;COPTIC EPACT NUMBER THREE HUNDRED;No;0;EN;;;;300;N;;;;;
+102F6;COPTIC EPACT NUMBER FOUR HUNDRED;No;0;EN;;;;400;N;;;;;
+102F7;COPTIC EPACT NUMBER FIVE HUNDRED;No;0;EN;;;;500;N;;;;;
+102F8;COPTIC EPACT NUMBER SIX HUNDRED;No;0;EN;;;;600;N;;;;;
+102F9;COPTIC EPACT NUMBER SEVEN HUNDRED;No;0;EN;;;;700;N;;;;;
+102FA;COPTIC EPACT NUMBER EIGHT HUNDRED;No;0;EN;;;;800;N;;;;;
+102FB;COPTIC EPACT NUMBER NINE HUNDRED;No;0;EN;;;;900;N;;;;;
 10300;OLD ITALIC LETTER A;Lo;0;L;;;;;N;;;;;
 10301;OLD ITALIC LETTER BE;Lo;0;L;;;;;N;;;;;
 10302;OLD ITALIC LETTER KE;Lo;0;L;;;;;N;;;;;
@@ -16551,6 +16914,7 @@
 1031C;OLD ITALIC LETTER CHE;Lo;0;L;;;;;N;;;;;
 1031D;OLD ITALIC LETTER II;Lo;0;L;;;;;N;;;;;
 1031E;OLD ITALIC LETTER UU;Lo;0;L;;;;;N;;;;;
+1031F;OLD ITALIC LETTER ESS;Lo;0;L;;;;;N;;;;;
 10320;OLD ITALIC NUMERAL ONE;No;0;L;;;;1;N;;;;;
 10321;OLD ITALIC NUMERAL FIVE;No;0;L;;;;5;N;;;;;
 10322;OLD ITALIC NUMERAL TEN;No;0;L;;;;10;N;;;;;
@@ -16582,6 +16946,49 @@
 10348;GOTHIC LETTER HWAIR;Lo;0;L;;;;;N;;;;;
 10349;GOTHIC LETTER OTHAL;Lo;0;L;;;;;N;;;;;
 1034A;GOTHIC LETTER NINE HUNDRED;Nl;0;L;;;;900;N;;;;;
+10350;OLD PERMIC LETTER AN;Lo;0;L;;;;;N;;;;;
+10351;OLD PERMIC LETTER BUR;Lo;0;L;;;;;N;;;;;
+10352;OLD PERMIC LETTER GAI;Lo;0;L;;;;;N;;;;;
+10353;OLD PERMIC LETTER DOI;Lo;0;L;;;;;N;;;;;
+10354;OLD PERMIC LETTER E;Lo;0;L;;;;;N;;;;;
+10355;OLD PERMIC LETTER ZHOI;Lo;0;L;;;;;N;;;;;
+10356;OLD PERMIC LETTER DZHOI;Lo;0;L;;;;;N;;;;;
+10357;OLD PERMIC LETTER ZATA;Lo;0;L;;;;;N;;;;;
+10358;OLD PERMIC LETTER DZITA;Lo;0;L;;;;;N;;;;;
+10359;OLD PERMIC LETTER I;Lo;0;L;;;;;N;;;;;
+1035A;OLD PERMIC LETTER KOKE;Lo;0;L;;;;;N;;;;;
+1035B;OLD PERMIC LETTER LEI;Lo;0;L;;;;;N;;;;;
+1035C;OLD PERMIC LETTER MENOE;Lo;0;L;;;;;N;;;;;
+1035D;OLD PERMIC LETTER NENOE;Lo;0;L;;;;;N;;;;;
+1035E;OLD PERMIC LETTER VOOI;Lo;0;L;;;;;N;;;;;
+1035F;OLD PERMIC LETTER PEEI;Lo;0;L;;;;;N;;;;;
+10360;OLD PERMIC LETTER REI;Lo;0;L;;;;;N;;;;;
+10361;OLD PERMIC LETTER SII;Lo;0;L;;;;;N;;;;;
+10362;OLD PERMIC LETTER TAI;Lo;0;L;;;;;N;;;;;
+10363;OLD PERMIC LETTER U;Lo;0;L;;;;;N;;;;;
+10364;OLD PERMIC LETTER CHERY;Lo;0;L;;;;;N;;;;;
+10365;OLD PERMIC LETTER SHOOI;Lo;0;L;;;;;N;;;;;
+10366;OLD PERMIC LETTER SHCHOOI;Lo;0;L;;;;;N;;;;;
+10367;OLD PERMIC LETTER YRY;Lo;0;L;;;;;N;;;;;
+10368;OLD PERMIC LETTER YERU;Lo;0;L;;;;;N;;;;;
+10369;OLD PERMIC LETTER O;Lo;0;L;;;;;N;;;;;
+1036A;OLD PERMIC LETTER OO;Lo;0;L;;;;;N;;;;;
+1036B;OLD PERMIC LETTER EF;Lo;0;L;;;;;N;;;;;
+1036C;OLD PERMIC LETTER HA;Lo;0;L;;;;;N;;;;;
+1036D;OLD PERMIC LETTER TSIU;Lo;0;L;;;;;N;;;;;
+1036E;OLD PERMIC LETTER VER;Lo;0;L;;;;;N;;;;;
+1036F;OLD PERMIC LETTER YER;Lo;0;L;;;;;N;;;;;
+10370;OLD PERMIC LETTER YERI;Lo;0;L;;;;;N;;;;;
+10371;OLD PERMIC LETTER YAT;Lo;0;L;;;;;N;;;;;
+10372;OLD PERMIC LETTER IE;Lo;0;L;;;;;N;;;;;
+10373;OLD PERMIC LETTER YU;Lo;0;L;;;;;N;;;;;
+10374;OLD PERMIC LETTER YA;Lo;0;L;;;;;N;;;;;
+10375;OLD PERMIC LETTER IA;Lo;0;L;;;;;N;;;;;
+10376;COMBINING OLD PERMIC LETTER AN;Mn;230;NSM;;;;;N;;;;;
+10377;COMBINING OLD PERMIC LETTER DOI;Mn;230;NSM;;;;;N;;;;;
+10378;COMBINING OLD PERMIC LETTER ZATA;Mn;230;NSM;;;;;N;;;;;
+10379;COMBINING OLD PERMIC LETTER NENOE;Mn;230;NSM;;;;;N;;;;;
+1037A;COMBINING OLD PERMIC LETTER SII;Mn;230;NSM;;;;;N;;;;;
 10380;UGARITIC LETTER ALPA;Lo;0;L;;;;;N;;;;;
 10381;UGARITIC LETTER BETA;Lo;0;L;;;;;N;;;;;
 10382;UGARITIC LETTER GAMLA;Lo;0;L;;;;;N;;;;;
@@ -16831,6 +17238,440 @@
 104A7;OSMANYA DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;;
 104A8;OSMANYA DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;;
 104A9;OSMANYA DIGIT NINE;Nd;0;L;;9;9;9;N;;;;;
+10500;ELBASAN LETTER A;Lo;0;L;;;;;N;;;;;
+10501;ELBASAN LETTER BE;Lo;0;L;;;;;N;;;;;
+10502;ELBASAN LETTER CE;Lo;0;L;;;;;N;;;;;
+10503;ELBASAN LETTER CHE;Lo;0;L;;;;;N;;;;;
+10504;ELBASAN LETTER DE;Lo;0;L;;;;;N;;;;;
+10505;ELBASAN LETTER NDE;Lo;0;L;;;;;N;;;;;
+10506;ELBASAN LETTER DHE;Lo;0;L;;;;;N;;;;;
+10507;ELBASAN LETTER EI;Lo;0;L;;;;;N;;;;;
+10508;ELBASAN LETTER E;Lo;0;L;;;;;N;;;;;
+10509;ELBASAN LETTER FE;Lo;0;L;;;;;N;;;;;
+1050A;ELBASAN LETTER GE;Lo;0;L;;;;;N;;;;;
+1050B;ELBASAN LETTER GJE;Lo;0;L;;;;;N;;;;;
+1050C;ELBASAN LETTER HE;Lo;0;L;;;;;N;;;;;
+1050D;ELBASAN LETTER I;Lo;0;L;;;;;N;;;;;
+1050E;ELBASAN LETTER JE;Lo;0;L;;;;;N;;;;;
+1050F;ELBASAN LETTER KE;Lo;0;L;;;;;N;;;;;
+10510;ELBASAN LETTER LE;Lo;0;L;;;;;N;;;;;
+10511;ELBASAN LETTER LLE;Lo;0;L;;;;;N;;;;;
+10512;ELBASAN LETTER ME;Lo;0;L;;;;;N;;;;;
+10513;ELBASAN LETTER NE;Lo;0;L;;;;;N;;;;;
+10514;ELBASAN LETTER NA;Lo;0;L;;;;;N;;;;;
+10515;ELBASAN LETTER NJE;Lo;0;L;;;;;N;;;;;
+10516;ELBASAN LETTER O;Lo;0;L;;;;;N;;;;;
+10517;ELBASAN LETTER PE;Lo;0;L;;;;;N;;;;;
+10518;ELBASAN LETTER QE;Lo;0;L;;;;;N;;;;;
+10519;ELBASAN LETTER RE;Lo;0;L;;;;;N;;;;;
+1051A;ELBASAN LETTER RRE;Lo;0;L;;;;;N;;;;;
+1051B;ELBASAN LETTER SE;Lo;0;L;;;;;N;;;;;
+1051C;ELBASAN LETTER SHE;Lo;0;L;;;;;N;;;;;
+1051D;ELBASAN LETTER TE;Lo;0;L;;;;;N;;;;;
+1051E;ELBASAN LETTER THE;Lo;0;L;;;;;N;;;;;
+1051F;ELBASAN LETTER U;Lo;0;L;;;;;N;;;;;
+10520;ELBASAN LETTER VE;Lo;0;L;;;;;N;;;;;
+10521;ELBASAN LETTER XE;Lo;0;L;;;;;N;;;;;
+10522;ELBASAN LETTER Y;Lo;0;L;;;;;N;;;;;
+10523;ELBASAN LETTER ZE;Lo;0;L;;;;;N;;;;;
+10524;ELBASAN LETTER ZHE;Lo;0;L;;;;;N;;;;;
+10525;ELBASAN LETTER GHE;Lo;0;L;;;;;N;;;;;
+10526;ELBASAN LETTER GHAMMA;Lo;0;L;;;;;N;;;;;
+10527;ELBASAN LETTER KHE;Lo;0;L;;;;;N;;;;;
+10530;CAUCASIAN ALBANIAN LETTER ALT;Lo;0;L;;;;;N;;;;;
+10531;CAUCASIAN ALBANIAN LETTER BET;Lo;0;L;;;;;N;;;;;
+10532;CAUCASIAN ALBANIAN LETTER GIM;Lo;0;L;;;;;N;;;;;
+10533;CAUCASIAN ALBANIAN LETTER DAT;Lo;0;L;;;;;N;;;;;
+10534;CAUCASIAN ALBANIAN LETTER EB;Lo;0;L;;;;;N;;;;;
+10535;CAUCASIAN ALBANIAN LETTER ZARL;Lo;0;L;;;;;N;;;;;
+10536;CAUCASIAN ALBANIAN LETTER EYN;Lo;0;L;;;;;N;;;;;
+10537;CAUCASIAN ALBANIAN LETTER ZHIL;Lo;0;L;;;;;N;;;;;
+10538;CAUCASIAN ALBANIAN LETTER TAS;Lo;0;L;;;;;N;;;;;
+10539;CAUCASIAN ALBANIAN LETTER CHA;Lo;0;L;;;;;N;;;;;
+1053A;CAUCASIAN ALBANIAN LETTER YOWD;Lo;0;L;;;;;N;;;;;
+1053B;CAUCASIAN ALBANIAN LETTER ZHA;Lo;0;L;;;;;N;;;;;
+1053C;CAUCASIAN ALBANIAN LETTER IRB;Lo;0;L;;;;;N;;;;;
+1053D;CAUCASIAN ALBANIAN LETTER SHA;Lo;0;L;;;;;N;;;;;
+1053E;CAUCASIAN ALBANIAN LETTER LAN;Lo;0;L;;;;;N;;;;;
+1053F;CAUCASIAN ALBANIAN LETTER INYA;Lo;0;L;;;;;N;;;;;
+10540;CAUCASIAN ALBANIAN LETTER XEYN;Lo;0;L;;;;;N;;;;;
+10541;CAUCASIAN ALBANIAN LETTER DYAN;Lo;0;L;;;;;N;;;;;
+10542;CAUCASIAN ALBANIAN LETTER CAR;Lo;0;L;;;;;N;;;;;
+10543;CAUCASIAN ALBANIAN LETTER JHOX;Lo;0;L;;;;;N;;;;;
+10544;CAUCASIAN ALBANIAN LETTER KAR;Lo;0;L;;;;;N;;;;;
+10545;CAUCASIAN ALBANIAN LETTER LYIT;Lo;0;L;;;;;N;;;;;
+10546;CAUCASIAN ALBANIAN LETTER HEYT;Lo;0;L;;;;;N;;;;;
+10547;CAUCASIAN ALBANIAN LETTER QAY;Lo;0;L;;;;;N;;;;;
+10548;CAUCASIAN ALBANIAN LETTER AOR;Lo;0;L;;;;;N;;;;;
+10549;CAUCASIAN ALBANIAN LETTER CHOY;Lo;0;L;;;;;N;;;;;
+1054A;CAUCASIAN ALBANIAN LETTER CHI;Lo;0;L;;;;;N;;;;;
+1054B;CAUCASIAN ALBANIAN LETTER CYAY;Lo;0;L;;;;;N;;;;;
+1054C;CAUCASIAN ALBANIAN LETTER MAQ;Lo;0;L;;;;;N;;;;;
+1054D;CAUCASIAN ALBANIAN LETTER QAR;Lo;0;L;;;;;N;;;;;
+1054E;CAUCASIAN ALBANIAN LETTER NOWC;Lo;0;L;;;;;N;;;;;
+1054F;CAUCASIAN ALBANIAN LETTER DZYAY;Lo;0;L;;;;;N;;;;;
+10550;CAUCASIAN ALBANIAN LETTER SHAK;Lo;0;L;;;;;N;;;;;
+10551;CAUCASIAN ALBANIAN LETTER JAYN;Lo;0;L;;;;;N;;;;;
+10552;CAUCASIAN ALBANIAN LETTER ON;Lo;0;L;;;;;N;;;;;
+10553;CAUCASIAN ALBANIAN LETTER TYAY;Lo;0;L;;;;;N;;;;;
+10554;CAUCASIAN ALBANIAN LETTER FAM;Lo;0;L;;;;;N;;;;;
+10555;CAUCASIAN ALBANIAN LETTER DZAY;Lo;0;L;;;;;N;;;;;
+10556;CAUCASIAN ALBANIAN LETTER CHAT;Lo;0;L;;;;;N;;;;;
+10557;CAUCASIAN ALBANIAN LETTER PEN;Lo;0;L;;;;;N;;;;;
+10558;CAUCASIAN ALBANIAN LETTER GHEYS;Lo;0;L;;;;;N;;;;;
+10559;CAUCASIAN ALBANIAN LETTER RAT;Lo;0;L;;;;;N;;;;;
+1055A;CAUCASIAN ALBANIAN LETTER SEYK;Lo;0;L;;;;;N;;;;;
+1055B;CAUCASIAN ALBANIAN LETTER VEYZ;Lo;0;L;;;;;N;;;;;
+1055C;CAUCASIAN ALBANIAN LETTER TIWR;Lo;0;L;;;;;N;;;;;
+1055D;CAUCASIAN ALBANIAN LETTER SHOY;Lo;0;L;;;;;N;;;;;
+1055E;CAUCASIAN ALBANIAN LETTER IWN;Lo;0;L;;;;;N;;;;;
+1055F;CAUCASIAN ALBANIAN LETTER CYAW;Lo;0;L;;;;;N;;;;;
+10560;CAUCASIAN ALBANIAN LETTER CAYN;Lo;0;L;;;;;N;;;;;
+10561;CAUCASIAN ALBANIAN LETTER YAYD;Lo;0;L;;;;;N;;;;;
+10562;CAUCASIAN ALBANIAN LETTER PIWR;Lo;0;L;;;;;N;;;;;
+10563;CAUCASIAN ALBANIAN LETTER KIW;Lo;0;L;;;;;N;;;;;
+1056F;CAUCASIAN ALBANIAN CITATION MARK;Po;0;L;;;;;N;;;;;
+10600;LINEAR A SIGN AB001;Lo;0;L;;;;;N;;;;;
+10601;LINEAR A SIGN AB002;Lo;0;L;;;;;N;;;;;
+10602;LINEAR A SIGN AB003;Lo;0;L;;;;;N;;;;;
+10603;LINEAR A SIGN AB004;Lo;0;L;;;;;N;;;;;
+10604;LINEAR A SIGN AB005;Lo;0;L;;;;;N;;;;;
+10605;LINEAR A SIGN AB006;Lo;0;L;;;;;N;;;;;
+10606;LINEAR A SIGN AB007;Lo;0;L;;;;;N;;;;;
+10607;LINEAR A SIGN AB008;Lo;0;L;;;;;N;;;;;
+10608;LINEAR A SIGN AB009;Lo;0;L;;;;;N;;;;;
+10609;LINEAR A SIGN AB010;Lo;0;L;;;;;N;;;;;
+1060A;LINEAR A SIGN AB011;Lo;0;L;;;;;N;;;;;
+1060B;LINEAR A SIGN AB013;Lo;0;L;;;;;N;;;;;
+1060C;LINEAR A SIGN AB016;Lo;0;L;;;;;N;;;;;
+1060D;LINEAR A SIGN AB017;Lo;0;L;;;;;N;;;;;
+1060E;LINEAR A SIGN AB020;Lo;0;L;;;;;N;;;;;
+1060F;LINEAR A SIGN AB021;Lo;0;L;;;;;N;;;;;
+10610;LINEAR A SIGN AB021F;Lo;0;L;;;;;N;;;;;
+10611;LINEAR A SIGN AB021M;Lo;0;L;;;;;N;;;;;
+10612;LINEAR A SIGN AB022;Lo;0;L;;;;;N;;;;;
+10613;LINEAR A SIGN AB022F;Lo;0;L;;;;;N;;;;;
+10614;LINEAR A SIGN AB022M;Lo;0;L;;;;;N;;;;;
+10615;LINEAR A SIGN AB023;Lo;0;L;;;;;N;;;;;
+10616;LINEAR A SIGN AB023M;Lo;0;L;;;;;N;;;;;
+10617;LINEAR A SIGN AB024;Lo;0;L;;;;;N;;;;;
+10618;LINEAR A SIGN AB026;Lo;0;L;;;;;N;;;;;
+10619;LINEAR A SIGN AB027;Lo;0;L;;;;;N;;;;;
+1061A;LINEAR A SIGN AB028;Lo;0;L;;;;;N;;;;;
+1061B;LINEAR A SIGN A028B;Lo;0;L;;;;;N;;;;;
+1061C;LINEAR A SIGN AB029;Lo;0;L;;;;;N;;;;;
+1061D;LINEAR A SIGN AB030;Lo;0;L;;;;;N;;;;;
+1061E;LINEAR A SIGN AB031;Lo;0;L;;;;;N;;;;;
+1061F;LINEAR A SIGN AB034;Lo;0;L;;;;;N;;;;;
+10620;LINEAR A SIGN AB037;Lo;0;L;;;;;N;;;;;
+10621;LINEAR A SIGN AB038;Lo;0;L;;;;;N;;;;;
+10622;LINEAR A SIGN AB039;Lo;0;L;;;;;N;;;;;
+10623;LINEAR A SIGN AB040;Lo;0;L;;;;;N;;;;;
+10624;LINEAR A SIGN AB041;Lo;0;L;;;;;N;;;;;
+10625;LINEAR A SIGN AB044;Lo;0;L;;;;;N;;;;;
+10626;LINEAR A SIGN AB045;Lo;0;L;;;;;N;;;;;
+10627;LINEAR A SIGN AB046;Lo;0;L;;;;;N;;;;;
+10628;LINEAR A SIGN AB047;Lo;0;L;;;;;N;;;;;
+10629;LINEAR A SIGN AB048;Lo;0;L;;;;;N;;;;;
+1062A;LINEAR A SIGN AB049;Lo;0;L;;;;;N;;;;;
+1062B;LINEAR A SIGN AB050;Lo;0;L;;;;;N;;;;;
+1062C;LINEAR A SIGN AB051;Lo;0;L;;;;;N;;;;;
+1062D;LINEAR A SIGN AB053;Lo;0;L;;;;;N;;;;;
+1062E;LINEAR A SIGN AB054;Lo;0;L;;;;;N;;;;;
+1062F;LINEAR A SIGN AB055;Lo;0;L;;;;;N;;;;;
+10630;LINEAR A SIGN AB056;Lo;0;L;;;;;N;;;;;
+10631;LINEAR A SIGN AB057;Lo;0;L;;;;;N;;;;;
+10632;LINEAR A SIGN AB058;Lo;0;L;;;;;N;;;;;
+10633;LINEAR A SIGN AB059;Lo;0;L;;;;;N;;;;;
+10634;LINEAR A SIGN AB060;Lo;0;L;;;;;N;;;;;
+10635;LINEAR A SIGN AB061;Lo;0;L;;;;;N;;;;;
+10636;LINEAR A SIGN AB065;Lo;0;L;;;;;N;;;;;
+10637;LINEAR A SIGN AB066;Lo;0;L;;;;;N;;;;;
+10638;LINEAR A SIGN AB067;Lo;0;L;;;;;N;;;;;
+10639;LINEAR A SIGN AB069;Lo;0;L;;;;;N;;;;;
+1063A;LINEAR A SIGN AB070;Lo;0;L;;;;;N;;;;;
+1063B;LINEAR A SIGN AB073;Lo;0;L;;;;;N;;;;;
+1063C;LINEAR A SIGN AB074;Lo;0;L;;;;;N;;;;;
+1063D;LINEAR A SIGN AB076;Lo;0;L;;;;;N;;;;;
+1063E;LINEAR A SIGN AB077;Lo;0;L;;;;;N;;;;;
+1063F;LINEAR A SIGN AB078;Lo;0;L;;;;;N;;;;;
+10640;LINEAR A SIGN AB079;Lo;0;L;;;;;N;;;;;
+10641;LINEAR A SIGN AB080;Lo;0;L;;;;;N;;;;;
+10642;LINEAR A SIGN AB081;Lo;0;L;;;;;N;;;;;
+10643;LINEAR A SIGN AB082;Lo;0;L;;;;;N;;;;;
+10644;LINEAR A SIGN AB085;Lo;0;L;;;;;N;;;;;
+10645;LINEAR A SIGN AB086;Lo;0;L;;;;;N;;;;;
+10646;LINEAR A SIGN AB087;Lo;0;L;;;;;N;;;;;
+10647;LINEAR A SIGN A100-102;Lo;0;L;;;;;N;;;;;
+10648;LINEAR A SIGN AB118;Lo;0;L;;;;;N;;;;;
+10649;LINEAR A SIGN AB120;Lo;0;L;;;;;N;;;;;
+1064A;LINEAR A SIGN A120B;Lo;0;L;;;;;N;;;;;
+1064B;LINEAR A SIGN AB122;Lo;0;L;;;;;N;;;;;
+1064C;LINEAR A SIGN AB123;Lo;0;L;;;;;N;;;;;
+1064D;LINEAR A SIGN AB131A;Lo;0;L;;;;;N;;;;;
+1064E;LINEAR A SIGN AB131B;Lo;0;L;;;;;N;;;;;
+1064F;LINEAR A SIGN A131C;Lo;0;L;;;;;N;;;;;
+10650;LINEAR A SIGN AB164;Lo;0;L;;;;;N;;;;;
+10651;LINEAR A SIGN AB171;Lo;0;L;;;;;N;;;;;
+10652;LINEAR A SIGN AB180;Lo;0;L;;;;;N;;;;;
+10653;LINEAR A SIGN AB188;Lo;0;L;;;;;N;;;;;
+10654;LINEAR A SIGN AB191;Lo;0;L;;;;;N;;;;;
+10655;LINEAR A SIGN A301;Lo;0;L;;;;;N;;;;;
+10656;LINEAR A SIGN A302;Lo;0;L;;;;;N;;;;;
+10657;LINEAR A SIGN A303;Lo;0;L;;;;;N;;;;;
+10658;LINEAR A SIGN A304;Lo;0;L;;;;;N;;;;;
+10659;LINEAR A SIGN A305;Lo;0;L;;;;;N;;;;;
+1065A;LINEAR A SIGN A306;Lo;0;L;;;;;N;;;;;
+1065B;LINEAR A SIGN A307;Lo;0;L;;;;;N;;;;;
+1065C;LINEAR A SIGN A308;Lo;0;L;;;;;N;;;;;
+1065D;LINEAR A SIGN A309A;Lo;0;L;;;;;N;;;;;
+1065E;LINEAR A SIGN A309B;Lo;0;L;;;;;N;;;;;
+1065F;LINEAR A SIGN A309C;Lo;0;L;;;;;N;;;;;
+10660;LINEAR A SIGN A310;Lo;0;L;;;;;N;;;;;
+10661;LINEAR A SIGN A311;Lo;0;L;;;;;N;;;;;
+10662;LINEAR A SIGN A312;Lo;0;L;;;;;N;;;;;
+10663;LINEAR A SIGN A313A;Lo;0;L;;;;;N;;;;;
+10664;LINEAR A SIGN A313B;Lo;0;L;;;;;N;;;;;
+10665;LINEAR A SIGN A313C;Lo;0;L;;;;;N;;;;;
+10666;LINEAR A SIGN A314;Lo;0;L;;;;;N;;;;;
+10667;LINEAR A SIGN A315;Lo;0;L;;;;;N;;;;;
+10668;LINEAR A SIGN A316;Lo;0;L;;;;;N;;;;;
+10669;LINEAR A SIGN A317;Lo;0;L;;;;;N;;;;;
+1066A;LINEAR A SIGN A318;Lo;0;L;;;;;N;;;;;
+1066B;LINEAR A SIGN A319;Lo;0;L;;;;;N;;;;;
+1066C;LINEAR A SIGN A320;Lo;0;L;;;;;N;;;;;
+1066D;LINEAR A SIGN A321;Lo;0;L;;;;;N;;;;;
+1066E;LINEAR A SIGN A322;Lo;0;L;;;;;N;;;;;
+1066F;LINEAR A SIGN A323;Lo;0;L;;;;;N;;;;;
+10670;LINEAR A SIGN A324;Lo;0;L;;;;;N;;;;;
+10671;LINEAR A SIGN A325;Lo;0;L;;;;;N;;;;;
+10672;LINEAR A SIGN A326;Lo;0;L;;;;;N;;;;;
+10673;LINEAR A SIGN A327;Lo;0;L;;;;;N;;;;;
+10674;LINEAR A SIGN A328;Lo;0;L;;;;;N;;;;;
+10675;LINEAR A SIGN A329;Lo;0;L;;;;;N;;;;;
+10676;LINEAR A SIGN A330;Lo;0;L;;;;;N;;;;;
+10677;LINEAR A SIGN A331;Lo;0;L;;;;;N;;;;;
+10678;LINEAR A SIGN A332;Lo;0;L;;;;;N;;;;;
+10679;LINEAR A SIGN A333;Lo;0;L;;;;;N;;;;;
+1067A;LINEAR A SIGN A334;Lo;0;L;;;;;N;;;;;
+1067B;LINEAR A SIGN A335;Lo;0;L;;;;;N;;;;;
+1067C;LINEAR A SIGN A336;Lo;0;L;;;;;N;;;;;
+1067D;LINEAR A SIGN A337;Lo;0;L;;;;;N;;;;;
+1067E;LINEAR A SIGN A338;Lo;0;L;;;;;N;;;;;
+1067F;LINEAR A SIGN A339;Lo;0;L;;;;;N;;;;;
+10680;LINEAR A SIGN A340;Lo;0;L;;;;;N;;;;;
+10681;LINEAR A SIGN A341;Lo;0;L;;;;;N;;;;;
+10682;LINEAR A SIGN A342;Lo;0;L;;;;;N;;;;;
+10683;LINEAR A SIGN A343;Lo;0;L;;;;;N;;;;;
+10684;LINEAR A SIGN A344;Lo;0;L;;;;;N;;;;;
+10685;LINEAR A SIGN A345;Lo;0;L;;;;;N;;;;;
+10686;LINEAR A SIGN A346;Lo;0;L;;;;;N;;;;;
+10687;LINEAR A SIGN A347;Lo;0;L;;;;;N;;;;;
+10688;LINEAR A SIGN A348;Lo;0;L;;;;;N;;;;;
+10689;LINEAR A SIGN A349;Lo;0;L;;;;;N;;;;;
+1068A;LINEAR A SIGN A350;Lo;0;L;;;;;N;;;;;
+1068B;LINEAR A SIGN A351;Lo;0;L;;;;;N;;;;;
+1068C;LINEAR A SIGN A352;Lo;0;L;;;;;N;;;;;
+1068D;LINEAR A SIGN A353;Lo;0;L;;;;;N;;;;;
+1068E;LINEAR A SIGN A354;Lo;0;L;;;;;N;;;;;
+1068F;LINEAR A SIGN A355;Lo;0;L;;;;;N;;;;;
+10690;LINEAR A SIGN A356;Lo;0;L;;;;;N;;;;;
+10691;LINEAR A SIGN A357;Lo;0;L;;;;;N;;;;;
+10692;LINEAR A SIGN A358;Lo;0;L;;;;;N;;;;;
+10693;LINEAR A SIGN A359;Lo;0;L;;;;;N;;;;;
+10694;LINEAR A SIGN A360;Lo;0;L;;;;;N;;;;;
+10695;LINEAR A SIGN A361;Lo;0;L;;;;;N;;;;;
+10696;LINEAR A SIGN A362;Lo;0;L;;;;;N;;;;;
+10697;LINEAR A SIGN A363;Lo;0;L;;;;;N;;;;;
+10698;LINEAR A SIGN A364;Lo;0;L;;;;;N;;;;;
+10699;LINEAR A SIGN A365;Lo;0;L;;;;;N;;;;;
+1069A;LINEAR A SIGN A366;Lo;0;L;;;;;N;;;;;
+1069B;LINEAR A SIGN A367;Lo;0;L;;;;;N;;;;;
+1069C;LINEAR A SIGN A368;Lo;0;L;;;;;N;;;;;
+1069D;LINEAR A SIGN A369;Lo;0;L;;;;;N;;;;;
+1069E;LINEAR A SIGN A370;Lo;0;L;;;;;N;;;;;
+1069F;LINEAR A SIGN A371;Lo;0;L;;;;;N;;;;;
+106A0;LINEAR A SIGN A400-VAS;Lo;0;L;;;;;N;;;;;
+106A1;LINEAR A SIGN A401-VAS;Lo;0;L;;;;;N;;;;;
+106A2;LINEAR A SIGN A402-VAS;Lo;0;L;;;;;N;;;;;
+106A3;LINEAR A SIGN A403-VAS;Lo;0;L;;;;;N;;;;;
+106A4;LINEAR A SIGN A404-VAS;Lo;0;L;;;;;N;;;;;
+106A5;LINEAR A SIGN A405-VAS;Lo;0;L;;;;;N;;;;;
+106A6;LINEAR A SIGN A406-VAS;Lo;0;L;;;;;N;;;;;
+106A7;LINEAR A SIGN A407-VAS;Lo;0;L;;;;;N;;;;;
+106A8;LINEAR A SIGN A408-VAS;Lo;0;L;;;;;N;;;;;
+106A9;LINEAR A SIGN A409-VAS;Lo;0;L;;;;;N;;;;;
+106AA;LINEAR A SIGN A410-VAS;Lo;0;L;;;;;N;;;;;
+106AB;LINEAR A SIGN A411-VAS;Lo;0;L;;;;;N;;;;;
+106AC;LINEAR A SIGN A412-VAS;Lo;0;L;;;;;N;;;;;
+106AD;LINEAR A SIGN A413-VAS;Lo;0;L;;;;;N;;;;;
+106AE;LINEAR A SIGN A414-VAS;Lo;0;L;;;;;N;;;;;
+106AF;LINEAR A SIGN A415-VAS;Lo;0;L;;;;;N;;;;;
+106B0;LINEAR A SIGN A416-VAS;Lo;0;L;;;;;N;;;;;
+106B1;LINEAR A SIGN A417-VAS;Lo;0;L;;;;;N;;;;;
+106B2;LINEAR A SIGN A418-VAS;Lo;0;L;;;;;N;;;;;
+106B3;LINEAR A SIGN A501;Lo;0;L;;;;;N;;;;;
+106B4;LINEAR A SIGN A502;Lo;0;L;;;;;N;;;;;
+106B5;LINEAR A SIGN A503;Lo;0;L;;;;;N;;;;;
+106B6;LINEAR A SIGN A504;Lo;0;L;;;;;N;;;;;
+106B7;LINEAR A SIGN A505;Lo;0;L;;;;;N;;;;;
+106B8;LINEAR A SIGN A506;Lo;0;L;;;;;N;;;;;
+106B9;LINEAR A SIGN A508;Lo;0;L;;;;;N;;;;;
+106BA;LINEAR A SIGN A509;Lo;0;L;;;;;N;;;;;
+106BB;LINEAR A SIGN A510;Lo;0;L;;;;;N;;;;;
+106BC;LINEAR A SIGN A511;Lo;0;L;;;;;N;;;;;
+106BD;LINEAR A SIGN A512;Lo;0;L;;;;;N;;;;;
+106BE;LINEAR A SIGN A513;Lo;0;L;;;;;N;;;;;
+106BF;LINEAR A SIGN A515;Lo;0;L;;;;;N;;;;;
+106C0;LINEAR A SIGN A516;Lo;0;L;;;;;N;;;;;
+106C1;LINEAR A SIGN A520;Lo;0;L;;;;;N;;;;;
+106C2;LINEAR A SIGN A521;Lo;0;L;;;;;N;;;;;
+106C3;LINEAR A SIGN A523;Lo;0;L;;;;;N;;;;;
+106C4;LINEAR A SIGN A524;Lo;0;L;;;;;N;;;;;
+106C5;LINEAR A SIGN A525;Lo;0;L;;;;;N;;;;;
+106C6;LINEAR A SIGN A526;Lo;0;L;;;;;N;;;;;
+106C7;LINEAR A SIGN A527;Lo;0;L;;;;;N;;;;;
+106C8;LINEAR A SIGN A528;Lo;0;L;;;;;N;;;;;
+106C9;LINEAR A SIGN A529;Lo;0;L;;;;;N;;;;;
+106CA;LINEAR A SIGN A530;Lo;0;L;;;;;N;;;;;
+106CB;LINEAR A SIGN A531;Lo;0;L;;;;;N;;;;;
+106CC;LINEAR A SIGN A532;Lo;0;L;;;;;N;;;;;
+106CD;LINEAR A SIGN A534;Lo;0;L;;;;;N;;;;;
+106CE;LINEAR A SIGN A535;Lo;0;L;;;;;N;;;;;
+106CF;LINEAR A SIGN A536;Lo;0;L;;;;;N;;;;;
+106D0;LINEAR A SIGN A537;Lo;0;L;;;;;N;;;;;
+106D1;LINEAR A SIGN A538;Lo;0;L;;;;;N;;;;;
+106D2;LINEAR A SIGN A539;Lo;0;L;;;;;N;;;;;
+106D3;LINEAR A SIGN A540;Lo;0;L;;;;;N;;;;;
+106D4;LINEAR A SIGN A541;Lo;0;L;;;;;N;;;;;
+106D5;LINEAR A SIGN A542;Lo;0;L;;;;;N;;;;;
+106D6;LINEAR A SIGN A545;Lo;0;L;;;;;N;;;;;
+106D7;LINEAR A SIGN A547;Lo;0;L;;;;;N;;;;;
+106D8;LINEAR A SIGN A548;Lo;0;L;;;;;N;;;;;
+106D9;LINEAR A SIGN A549;Lo;0;L;;;;;N;;;;;
+106DA;LINEAR A SIGN A550;Lo;0;L;;;;;N;;;;;
+106DB;LINEAR A SIGN A551;Lo;0;L;;;;;N;;;;;
+106DC;LINEAR A SIGN A552;Lo;0;L;;;;;N;;;;;
+106DD;LINEAR A SIGN A553;Lo;0;L;;;;;N;;;;;
+106DE;LINEAR A SIGN A554;Lo;0;L;;;;;N;;;;;
+106DF;LINEAR A SIGN A555;Lo;0;L;;;;;N;;;;;
+106E0;LINEAR A SIGN A556;Lo;0;L;;;;;N;;;;;
+106E1;LINEAR A SIGN A557;Lo;0;L;;;;;N;;;;;
+106E2;LINEAR A SIGN A559;Lo;0;L;;;;;N;;;;;
+106E3;LINEAR A SIGN A563;Lo;0;L;;;;;N;;;;;
+106E4;LINEAR A SIGN A564;Lo;0;L;;;;;N;;;;;
+106E5;LINEAR A SIGN A565;Lo;0;L;;;;;N;;;;;
+106E6;LINEAR A SIGN A566;Lo;0;L;;;;;N;;;;;
+106E7;LINEAR A SIGN A568;Lo;0;L;;;;;N;;;;;
+106E8;LINEAR A SIGN A569;Lo;0;L;;;;;N;;;;;
+106E9;LINEAR A SIGN A570;Lo;0;L;;;;;N;;;;;
+106EA;LINEAR A SIGN A571;Lo;0;L;;;;;N;;;;;
+106EB;LINEAR A SIGN A572;Lo;0;L;;;;;N;;;;;
+106EC;LINEAR A SIGN A573;Lo;0;L;;;;;N;;;;;
+106ED;LINEAR A SIGN A574;Lo;0;L;;;;;N;;;;;
+106EE;LINEAR A SIGN A575;Lo;0;L;;;;;N;;;;;
+106EF;LINEAR A SIGN A576;Lo;0;L;;;;;N;;;;;
+106F0;LINEAR A SIGN A577;Lo;0;L;;;;;N;;;;;
+106F1;LINEAR A SIGN A578;Lo;0;L;;;;;N;;;;;
+106F2;LINEAR A SIGN A579;Lo;0;L;;;;;N;;;;;
+106F3;LINEAR A SIGN A580;Lo;0;L;;;;;N;;;;;
+106F4;LINEAR A SIGN A581;Lo;0;L;;;;;N;;;;;
+106F5;LINEAR A SIGN A582;Lo;0;L;;;;;N;;;;;
+106F6;LINEAR A SIGN A583;Lo;0;L;;;;;N;;;;;
+106F7;LINEAR A SIGN A584;Lo;0;L;;;;;N;;;;;
+106F8;LINEAR A SIGN A585;Lo;0;L;;;;;N;;;;;
+106F9;LINEAR A SIGN A586;Lo;0;L;;;;;N;;;;;
+106FA;LINEAR A SIGN A587;Lo;0;L;;;;;N;;;;;
+106FB;LINEAR A SIGN A588;Lo;0;L;;;;;N;;;;;
+106FC;LINEAR A SIGN A589;Lo;0;L;;;;;N;;;;;
+106FD;LINEAR A SIGN A591;Lo;0;L;;;;;N;;;;;
+106FE;LINEAR A SIGN A592;Lo;0;L;;;;;N;;;;;
+106FF;LINEAR A SIGN A594;Lo;0;L;;;;;N;;;;;
+10700;LINEAR A SIGN A595;Lo;0;L;;;;;N;;;;;
+10701;LINEAR A SIGN A596;Lo;0;L;;;;;N;;;;;
+10702;LINEAR A SIGN A598;Lo;0;L;;;;;N;;;;;
+10703;LINEAR A SIGN A600;Lo;0;L;;;;;N;;;;;
+10704;LINEAR A SIGN A601;Lo;0;L;;;;;N;;;;;
+10705;LINEAR A SIGN A602;Lo;0;L;;;;;N;;;;;
+10706;LINEAR A SIGN A603;Lo;0;L;;;;;N;;;;;
+10707;LINEAR A SIGN A604;Lo;0;L;;;;;N;;;;;
+10708;LINEAR A SIGN A606;Lo;0;L;;;;;N;;;;;
+10709;LINEAR A SIGN A608;Lo;0;L;;;;;N;;;;;
+1070A;LINEAR A SIGN A609;Lo;0;L;;;;;N;;;;;
+1070B;LINEAR A SIGN A610;Lo;0;L;;;;;N;;;;;
+1070C;LINEAR A SIGN A611;Lo;0;L;;;;;N;;;;;
+1070D;LINEAR A SIGN A612;Lo;0;L;;;;;N;;;;;
+1070E;LINEAR A SIGN A613;Lo;0;L;;;;;N;;;;;
+1070F;LINEAR A SIGN A614;Lo;0;L;;;;;N;;;;;
+10710;LINEAR A SIGN A615;Lo;0;L;;;;;N;;;;;
+10711;LINEAR A SIGN A616;Lo;0;L;;;;;N;;;;;
+10712;LINEAR A SIGN A617;Lo;0;L;;;;;N;;;;;
+10713;LINEAR A SIGN A618;Lo;0;L;;;;;N;;;;;
+10714;LINEAR A SIGN A619;Lo;0;L;;;;;N;;;;;
+10715;LINEAR A SIGN A620;Lo;0;L;;;;;N;;;;;
+10716;LINEAR A SIGN A621;Lo;0;L;;;;;N;;;;;
+10717;LINEAR A SIGN A622;Lo;0;L;;;;;N;;;;;
+10718;LINEAR A SIGN A623;Lo;0;L;;;;;N;;;;;
+10719;LINEAR A SIGN A624;Lo;0;L;;;;;N;;;;;
+1071A;LINEAR A SIGN A626;Lo;0;L;;;;;N;;;;;
+1071B;LINEAR A SIGN A627;Lo;0;L;;;;;N;;;;;
+1071C;LINEAR A SIGN A628;Lo;0;L;;;;;N;;;;;
+1071D;LINEAR A SIGN A629;Lo;0;L;;;;;N;;;;;
+1071E;LINEAR A SIGN A634;Lo;0;L;;;;;N;;;;;
+1071F;LINEAR A SIGN A637;Lo;0;L;;;;;N;;;;;
+10720;LINEAR A SIGN A638;Lo;0;L;;;;;N;;;;;
+10721;LINEAR A SIGN A640;Lo;0;L;;;;;N;;;;;
+10722;LINEAR A SIGN A642;Lo;0;L;;;;;N;;;;;
+10723;LINEAR A SIGN A643;Lo;0;L;;;;;N;;;;;
+10724;LINEAR A SIGN A644;Lo;0;L;;;;;N;;;;;
+10725;LINEAR A SIGN A645;Lo;0;L;;;;;N;;;;;
+10726;LINEAR A SIGN A646;Lo;0;L;;;;;N;;;;;
+10727;LINEAR A SIGN A648;Lo;0;L;;;;;N;;;;;
+10728;LINEAR A SIGN A649;Lo;0;L;;;;;N;;;;;
+10729;LINEAR A SIGN A651;Lo;0;L;;;;;N;;;;;
+1072A;LINEAR A SIGN A652;Lo;0;L;;;;;N;;;;;
+1072B;LINEAR A SIGN A653;Lo;0;L;;;;;N;;;;;
+1072C;LINEAR A SIGN A654;Lo;0;L;;;;;N;;;;;
+1072D;LINEAR A SIGN A655;Lo;0;L;;;;;N;;;;;
+1072E;LINEAR A SIGN A656;Lo;0;L;;;;;N;;;;;
+1072F;LINEAR A SIGN A657;Lo;0;L;;;;;N;;;;;
+10730;LINEAR A SIGN A658;Lo;0;L;;;;;N;;;;;
+10731;LINEAR A SIGN A659;Lo;0;L;;;;;N;;;;;
+10732;LINEAR A SIGN A660;Lo;0;L;;;;;N;;;;;
+10733;LINEAR A SIGN A661;Lo;0;L;;;;;N;;;;;
+10734;LINEAR A SIGN A662;Lo;0;L;;;;;N;;;;;
+10735;LINEAR A SIGN A663;Lo;0;L;;;;;N;;;;;
+10736;LINEAR A SIGN A664;Lo;0;L;;;;;N;;;;;
+10740;LINEAR A SIGN A701 A;Lo;0;L;;;;;N;;;;;
+10741;LINEAR A SIGN A702 B;Lo;0;L;;;;;N;;;;;
+10742;LINEAR A SIGN A703 D;Lo;0;L;;;;;N;;;;;
+10743;LINEAR A SIGN A704 E;Lo;0;L;;;;;N;;;;;
+10744;LINEAR A SIGN A705 F;Lo;0;L;;;;;N;;;;;
+10745;LINEAR A SIGN A706 H;Lo;0;L;;;;;N;;;;;
+10746;LINEAR A SIGN A707 J;Lo;0;L;;;;;N;;;;;
+10747;LINEAR A SIGN A708 K;Lo;0;L;;;;;N;;;;;
+10748;LINEAR A SIGN A709 L;Lo;0;L;;;;;N;;;;;
+10749;LINEAR A SIGN A709-2 L2;Lo;0;L;;;;;N;;;;;
+1074A;LINEAR A SIGN A709-3 L3;Lo;0;L;;;;;N;;;;;
+1074B;LINEAR A SIGN A709-4 L4;Lo;0;L;;;;;N;;;;;
+1074C;LINEAR A SIGN A709-6 L6;Lo;0;L;;;;;N;;;;;
+1074D;LINEAR A SIGN A710 W;Lo;0;L;;;;;N;;;;;
+1074E;LINEAR A SIGN A711 X;Lo;0;L;;;;;N;;;;;
+1074F;LINEAR A SIGN A712 Y;Lo;0;L;;;;;N;;;;;
+10750;LINEAR A SIGN A713 OMEGA;Lo;0;L;;;;;N;;;;;
+10751;LINEAR A SIGN A714 ABB;Lo;0;L;;;;;N;;;;;
+10752;LINEAR A SIGN A715 BB;Lo;0;L;;;;;N;;;;;
+10753;LINEAR A SIGN A717 DD;Lo;0;L;;;;;N;;;;;
+10754;LINEAR A SIGN A726 EYYY;Lo;0;L;;;;;N;;;;;
+10755;LINEAR A SIGN A732 JE;Lo;0;L;;;;;N;;;;;
+10760;LINEAR A SIGN A800;Lo;0;L;;;;;N;;;;;
+10761;LINEAR A SIGN A801;Lo;0;L;;;;;N;;;;;
+10762;LINEAR A SIGN A802;Lo;0;L;;;;;N;;;;;
+10763;LINEAR A SIGN A803;Lo;0;L;;;;;N;;;;;
+10764;LINEAR A SIGN A804;Lo;0;L;;;;;N;;;;;
+10765;LINEAR A SIGN A805;Lo;0;L;;;;;N;;;;;
+10766;LINEAR A SIGN A806;Lo;0;L;;;;;N;;;;;
+10767;LINEAR A SIGN A807;Lo;0;L;;;;;N;;;;;
 10800;CYPRIOT SYLLABLE A;Lo;0;R;;;;;N;;;;;
 10801;CYPRIOT SYLLABLE E;Lo;0;R;;;;;N;;;;;
 10802;CYPRIOT SYLLABLE I;Lo;0;R;;;;;N;;;;;
@@ -16917,6 +17758,78 @@
 1085D;IMPERIAL ARAMAIC NUMBER ONE HUNDRED;No;0;R;;;;100;N;;;;;
 1085E;IMPERIAL ARAMAIC NUMBER ONE THOUSAND;No;0;R;;;;1000;N;;;;;
 1085F;IMPERIAL ARAMAIC NUMBER TEN THOUSAND;No;0;R;;;;10000;N;;;;;
+10860;PALMYRENE LETTER ALEPH;Lo;0;R;;;;;N;;;;;
+10861;PALMYRENE LETTER BETH;Lo;0;R;;;;;N;;;;;
+10862;PALMYRENE LETTER GIMEL;Lo;0;R;;;;;N;;;;;
+10863;PALMYRENE LETTER DALETH;Lo;0;R;;;;;N;;;;;
+10864;PALMYRENE LETTER HE;Lo;0;R;;;;;N;;;;;
+10865;PALMYRENE LETTER WAW;Lo;0;R;;;;;N;;;;;
+10866;PALMYRENE LETTER ZAYIN;Lo;0;R;;;;;N;;;;;
+10867;PALMYRENE LETTER HETH;Lo;0;R;;;;;N;;;;;
+10868;PALMYRENE LETTER TETH;Lo;0;R;;;;;N;;;;;
+10869;PALMYRENE LETTER YODH;Lo;0;R;;;;;N;;;;;
+1086A;PALMYRENE LETTER KAPH;Lo;0;R;;;;;N;;;;;
+1086B;PALMYRENE LETTER LAMEDH;Lo;0;R;;;;;N;;;;;
+1086C;PALMYRENE LETTER MEM;Lo;0;R;;;;;N;;;;;
+1086D;PALMYRENE LETTER FINAL NUN;Lo;0;R;;;;;N;;;;;
+1086E;PALMYRENE LETTER NUN;Lo;0;R;;;;;N;;;;;
+1086F;PALMYRENE LETTER SAMEKH;Lo;0;R;;;;;N;;;;;
+10870;PALMYRENE LETTER AYIN;Lo;0;R;;;;;N;;;;;
+10871;PALMYRENE LETTER PE;Lo;0;R;;;;;N;;;;;
+10872;PALMYRENE LETTER SADHE;Lo;0;R;;;;;N;;;;;
+10873;PALMYRENE LETTER QOPH;Lo;0;R;;;;;N;;;;;
+10874;PALMYRENE LETTER RESH;Lo;0;R;;;;;N;;;;;
+10875;PALMYRENE LETTER SHIN;Lo;0;R;;;;;N;;;;;
+10876;PALMYRENE LETTER TAW;Lo;0;R;;;;;N;;;;;
+10877;PALMYRENE LEFT-POINTING FLEURON;So;0;R;;;;;N;;;;;
+10878;PALMYRENE RIGHT-POINTING FLEURON;So;0;R;;;;;N;;;;;
+10879;PALMYRENE NUMBER ONE;No;0;R;;;;1;N;;;;;
+1087A;PALMYRENE NUMBER TWO;No;0;R;;;;2;N;;;;;
+1087B;PALMYRENE NUMBER THREE;No;0;R;;;;3;N;;;;;
+1087C;PALMYRENE NUMBER FOUR;No;0;R;;;;4;N;;;;;
+1087D;PALMYRENE NUMBER FIVE;No;0;R;;;;5;N;;;;;
+1087E;PALMYRENE NUMBER TEN;No;0;R;;;;10;N;;;;;
+1087F;PALMYRENE NUMBER TWENTY;No;0;R;;;;20;N;;;;;
+10880;NABATAEAN LETTER FINAL ALEPH;Lo;0;R;;;;;N;;;;;
+10881;NABATAEAN LETTER ALEPH;Lo;0;R;;;;;N;;;;;
+10882;NABATAEAN LETTER FINAL BETH;Lo;0;R;;;;;N;;;;;
+10883;NABATAEAN LETTER BETH;Lo;0;R;;;;;N;;;;;
+10884;NABATAEAN LETTER GIMEL;Lo;0;R;;;;;N;;;;;
+10885;NABATAEAN LETTER DALETH;Lo;0;R;;;;;N;;;;;
+10886;NABATAEAN LETTER FINAL HE;Lo;0;R;;;;;N;;;;;
+10887;NABATAEAN LETTER HE;Lo;0;R;;;;;N;;;;;
+10888;NABATAEAN LETTER WAW;Lo;0;R;;;;;N;;;;;
+10889;NABATAEAN LETTER ZAYIN;Lo;0;R;;;;;N;;;;;
+1088A;NABATAEAN LETTER HETH;Lo;0;R;;;;;N;;;;;
+1088B;NABATAEAN LETTER TETH;Lo;0;R;;;;;N;;;;;
+1088C;NABATAEAN LETTER FINAL YODH;Lo;0;R;;;;;N;;;;;
+1088D;NABATAEAN LETTER YODH;Lo;0;R;;;;;N;;;;;
+1088E;NABATAEAN LETTER FINAL KAPH;Lo;0;R;;;;;N;;;;;
+1088F;NABATAEAN LETTER KAPH;Lo;0;R;;;;;N;;;;;
+10890;NABATAEAN LETTER FINAL LAMEDH;Lo;0;R;;;;;N;;;;;
+10891;NABATAEAN LETTER LAMEDH;Lo;0;R;;;;;N;;;;;
+10892;NABATAEAN LETTER FINAL MEM;Lo;0;R;;;;;N;;;;;
+10893;NABATAEAN LETTER MEM;Lo;0;R;;;;;N;;;;;
+10894;NABATAEAN LETTER FINAL NUN;Lo;0;R;;;;;N;;;;;
+10895;NABATAEAN LETTER NUN;Lo;0;R;;;;;N;;;;;
+10896;NABATAEAN LETTER SAMEKH;Lo;0;R;;;;;N;;;;;
+10897;NABATAEAN LETTER AYIN;Lo;0;R;;;;;N;;;;;
+10898;NABATAEAN LETTER PE;Lo;0;R;;;;;N;;;;;
+10899;NABATAEAN LETTER SADHE;Lo;0;R;;;;;N;;;;;
+1089A;NABATAEAN LETTER QOPH;Lo;0;R;;;;;N;;;;;
+1089B;NABATAEAN LETTER RESH;Lo;0;R;;;;;N;;;;;
+1089C;NABATAEAN LETTER FINAL SHIN;Lo;0;R;;;;;N;;;;;
+1089D;NABATAEAN LETTER SHIN;Lo;0;R;;;;;N;;;;;
+1089E;NABATAEAN LETTER TAW;Lo;0;R;;;;;N;;;;;
+108A7;NABATAEAN NUMBER ONE;No;0;R;;;;1;N;;;;;
+108A8;NABATAEAN NUMBER TWO;No;0;R;;;;2;N;;;;;
+108A9;NABATAEAN NUMBER THREE;No;0;R;;;;3;N;;;;;
+108AA;NABATAEAN NUMBER FOUR;No;0;R;;;;4;N;;;;;
+108AB;NABATAEAN CRUCIFORM NUMBER FOUR;No;0;R;;;;4;N;;;;;
+108AC;NABATAEAN NUMBER FIVE;No;0;R;;;;5;N;;;;;
+108AD;NABATAEAN NUMBER TEN;No;0;R;;;;10;N;;;;;
+108AE;NABATAEAN NUMBER TWENTY;No;0;R;;;;20;N;;;;;
+108AF;NABATAEAN NUMBER ONE HUNDRED;No;0;R;;;;100;N;;;;;
 10900;PHOENICIAN LETTER ALF;Lo;0;R;;;;;N;;;;;
 10901;PHOENICIAN LETTER BET;Lo;0;R;;;;;N;;;;;
 10902;PHOENICIAN LETTER GAML;Lo;0;R;;;;;N;;;;;
@@ -17128,6 +18041,89 @@
 10A7D;OLD SOUTH ARABIAN NUMBER ONE;No;0;R;;;;1;N;;;;;
 10A7E;OLD SOUTH ARABIAN NUMBER FIFTY;No;0;R;;;;50;N;;;;;
 10A7F;OLD SOUTH ARABIAN NUMERIC INDICATOR;Po;0;R;;;;;N;;;;;
+10A80;OLD NORTH ARABIAN LETTER HEH;Lo;0;R;;;;;N;;;;;
+10A81;OLD NORTH ARABIAN LETTER LAM;Lo;0;R;;;;;N;;;;;
+10A82;OLD NORTH ARABIAN LETTER HAH;Lo;0;R;;;;;N;;;;;
+10A83;OLD NORTH ARABIAN LETTER MEEM;Lo;0;R;;;;;N;;;;;
+10A84;OLD NORTH ARABIAN LETTER QAF;Lo;0;R;;;;;N;;;;;
+10A85;OLD NORTH ARABIAN LETTER WAW;Lo;0;R;;;;;N;;;;;
+10A86;OLD NORTH ARABIAN LETTER ES-2;Lo;0;R;;;;;N;;;;;
+10A87;OLD NORTH ARABIAN LETTER REH;Lo;0;R;;;;;N;;;;;
+10A88;OLD NORTH ARABIAN LETTER BEH;Lo;0;R;;;;;N;;;;;
+10A89;OLD NORTH ARABIAN LETTER TEH;Lo;0;R;;;;;N;;;;;
+10A8A;OLD NORTH ARABIAN LETTER ES-1;Lo;0;R;;;;;N;;;;;
+10A8B;OLD NORTH ARABIAN LETTER KAF;Lo;0;R;;;;;N;;;;;
+10A8C;OLD NORTH ARABIAN LETTER NOON;Lo;0;R;;;;;N;;;;;
+10A8D;OLD NORTH ARABIAN LETTER KHAH;Lo;0;R;;;;;N;;;;;
+10A8E;OLD NORTH ARABIAN LETTER SAD;Lo;0;R;;;;;N;;;;;
+10A8F;OLD NORTH ARABIAN LETTER ES-3;Lo;0;R;;;;;N;;;;;
+10A90;OLD NORTH ARABIAN LETTER FEH;Lo;0;R;;;;;N;;;;;
+10A91;OLD NORTH ARABIAN LETTER ALEF;Lo;0;R;;;;;N;;;;;
+10A92;OLD NORTH ARABIAN LETTER AIN;Lo;0;R;;;;;N;;;;;
+10A93;OLD NORTH ARABIAN LETTER DAD;Lo;0;R;;;;;N;;;;;
+10A94;OLD NORTH ARABIAN LETTER GEEM;Lo;0;R;;;;;N;;;;;
+10A95;OLD NORTH ARABIAN LETTER DAL;Lo;0;R;;;;;N;;;;;
+10A96;OLD NORTH ARABIAN LETTER GHAIN;Lo;0;R;;;;;N;;;;;
+10A97;OLD NORTH ARABIAN LETTER TAH;Lo;0;R;;;;;N;;;;;
+10A98;OLD NORTH ARABIAN LETTER ZAIN;Lo;0;R;;;;;N;;;;;
+10A99;OLD NORTH ARABIAN LETTER THAL;Lo;0;R;;;;;N;;;;;
+10A9A;OLD NORTH ARABIAN LETTER YEH;Lo;0;R;;;;;N;;;;;
+10A9B;OLD NORTH ARABIAN LETTER THEH;Lo;0;R;;;;;N;;;;;
+10A9C;OLD NORTH ARABIAN LETTER ZAH;Lo;0;R;;;;;N;;;;;
+10A9D;OLD NORTH ARABIAN NUMBER ONE;No;0;R;;;;1;N;;;;;
+10A9E;OLD NORTH ARABIAN NUMBER TEN;No;0;R;;;;10;N;;;;;
+10A9F;OLD NORTH ARABIAN NUMBER TWENTY;No;0;R;;;;20;N;;;;;
+10AC0;MANICHAEAN LETTER ALEPH;Lo;0;R;;;;;N;;;;;
+10AC1;MANICHAEAN LETTER BETH;Lo;0;R;;;;;N;;;;;
+10AC2;MANICHAEAN LETTER BHETH;Lo;0;R;;;;;N;;;;;
+10AC3;MANICHAEAN LETTER GIMEL;Lo;0;R;;;;;N;;;;;
+10AC4;MANICHAEAN LETTER GHIMEL;Lo;0;R;;;;;N;;;;;
+10AC5;MANICHAEAN LETTER DALETH;Lo;0;R;;;;;N;;;;;
+10AC6;MANICHAEAN LETTER HE;Lo;0;R;;;;;N;;;;;
+10AC7;MANICHAEAN LETTER WAW;Lo;0;R;;;;;N;;;;;
+10AC8;MANICHAEAN SIGN UD;So;0;R;;;;;N;;;;;
+10AC9;MANICHAEAN LETTER ZAYIN;Lo;0;R;;;;;N;;;;;
+10ACA;MANICHAEAN LETTER ZHAYIN;Lo;0;R;;;;;N;;;;;
+10ACB;MANICHAEAN LETTER JAYIN;Lo;0;R;;;;;N;;;;;
+10ACC;MANICHAEAN LETTER JHAYIN;Lo;0;R;;;;;N;;;;;
+10ACD;MANICHAEAN LETTER HETH;Lo;0;R;;;;;N;;;;;
+10ACE;MANICHAEAN LETTER TETH;Lo;0;R;;;;;N;;;;;
+10ACF;MANICHAEAN LETTER YODH;Lo;0;R;;;;;N;;;;;
+10AD0;MANICHAEAN LETTER KAPH;Lo;0;R;;;;;N;;;;;
+10AD1;MANICHAEAN LETTER XAPH;Lo;0;R;;;;;N;;;;;
+10AD2;MANICHAEAN LETTER KHAPH;Lo;0;R;;;;;N;;;;;
+10AD3;MANICHAEAN LETTER LAMEDH;Lo;0;R;;;;;N;;;;;
+10AD4;MANICHAEAN LETTER DHAMEDH;Lo;0;R;;;;;N;;;;;
+10AD5;MANICHAEAN LETTER THAMEDH;Lo;0;R;;;;;N;;;;;
+10AD6;MANICHAEAN LETTER MEM;Lo;0;R;;;;;N;;;;;
+10AD7;MANICHAEAN LETTER NUN;Lo;0;R;;;;;N;;;;;
+10AD8;MANICHAEAN LETTER SAMEKH;Lo;0;R;;;;;N;;;;;
+10AD9;MANICHAEAN LETTER AYIN;Lo;0;R;;;;;N;;;;;
+10ADA;MANICHAEAN LETTER AAYIN;Lo;0;R;;;;;N;;;;;
+10ADB;MANICHAEAN LETTER PE;Lo;0;R;;;;;N;;;;;
+10ADC;MANICHAEAN LETTER FE;Lo;0;R;;;;;N;;;;;
+10ADD;MANICHAEAN LETTER SADHE;Lo;0;R;;;;;N;;;;;
+10ADE;MANICHAEAN LETTER QOPH;Lo;0;R;;;;;N;;;;;
+10ADF;MANICHAEAN LETTER XOPH;Lo;0;R;;;;;N;;;;;
+10AE0;MANICHAEAN LETTER QHOPH;Lo;0;R;;;;;N;;;;;
+10AE1;MANICHAEAN LETTER RESH;Lo;0;R;;;;;N;;;;;
+10AE2;MANICHAEAN LETTER SHIN;Lo;0;R;;;;;N;;;;;
+10AE3;MANICHAEAN LETTER SSHIN;Lo;0;R;;;;;N;;;;;
+10AE4;MANICHAEAN LETTER TAW;Lo;0;R;;;;;N;;;;;
+10AE5;MANICHAEAN ABBREVIATION MARK ABOVE;Mn;230;NSM;;;;;N;;;;;
+10AE6;MANICHAEAN ABBREVIATION MARK BELOW;Mn;220;NSM;;;;;N;;;;;
+10AEB;MANICHAEAN NUMBER ONE;No;0;R;;;;1;N;;;;;
+10AEC;MANICHAEAN NUMBER FIVE;No;0;R;;;;5;N;;;;;
+10AED;MANICHAEAN NUMBER TEN;No;0;R;;;;10;N;;;;;
+10AEE;MANICHAEAN NUMBER TWENTY;No;0;R;;;;20;N;;;;;
+10AEF;MANICHAEAN NUMBER ONE HUNDRED;No;0;R;;;;100;N;;;;;
+10AF0;MANICHAEAN PUNCTUATION STAR;Po;0;R;;;;;N;;;;;
+10AF1;MANICHAEAN PUNCTUATION FLEURON;Po;0;R;;;;;N;;;;;
+10AF2;MANICHAEAN PUNCTUATION DOUBLE DOT WITHIN DOT;Po;0;R;;;;;N;;;;;
+10AF3;MANICHAEAN PUNCTUATION DOT WITHIN DOT;Po;0;R;;;;;N;;;;;
+10AF4;MANICHAEAN PUNCTUATION DOT;Po;0;R;;;;;N;;;;;
+10AF5;MANICHAEAN PUNCTUATION TWO DOTS;Po;0;R;;;;;N;;;;;
+10AF6;MANICHAEAN PUNCTUATION LINE FILLER;Po;0;R;;;;;N;;;;;
 10B00;AVESTAN LETTER A;Lo;0;R;;;;;N;;;;;
 10B01;AVESTAN LETTER AA;Lo;0;R;;;;;N;;;;;
 10B02;AVESTAN LETTER AO;Lo;0;R;;;;;N;;;;;
@@ -17246,6 +18242,35 @@
 10B7D;INSCRIPTIONAL PAHLAVI NUMBER TWENTY;No;0;R;;;;20;N;;;;;
 10B7E;INSCRIPTIONAL PAHLAVI NUMBER ONE HUNDRED;No;0;R;;;;100;N;;;;;
 10B7F;INSCRIPTIONAL PAHLAVI NUMBER ONE THOUSAND;No;0;R;;;;1000;N;;;;;
+10B80;PSALTER PAHLAVI LETTER ALEPH;Lo;0;R;;;;;N;;;;;
+10B81;PSALTER PAHLAVI LETTER BETH;Lo;0;R;;;;;N;;;;;
+10B82;PSALTER PAHLAVI LETTER GIMEL;Lo;0;R;;;;;N;;;;;
+10B83;PSALTER PAHLAVI LETTER DALETH;Lo;0;R;;;;;N;;;;;
+10B84;PSALTER PAHLAVI LETTER HE;Lo;0;R;;;;;N;;;;;
+10B85;PSALTER PAHLAVI LETTER WAW-AYIN-RESH;Lo;0;R;;;;;N;;;;;
+10B86;PSALTER PAHLAVI LETTER ZAYIN;Lo;0;R;;;;;N;;;;;
+10B87;PSALTER PAHLAVI LETTER HETH;Lo;0;R;;;;;N;;;;;
+10B88;PSALTER PAHLAVI LETTER YODH;Lo;0;R;;;;;N;;;;;
+10B89;PSALTER PAHLAVI LETTER KAPH;Lo;0;R;;;;;N;;;;;
+10B8A;PSALTER PAHLAVI LETTER LAMEDH;Lo;0;R;;;;;N;;;;;
+10B8B;PSALTER PAHLAVI LETTER MEM-QOPH;Lo;0;R;;;;;N;;;;;
+10B8C;PSALTER PAHLAVI LETTER NUN;Lo;0;R;;;;;N;;;;;
+10B8D;PSALTER PAHLAVI LETTER SAMEKH;Lo;0;R;;;;;N;;;;;
+10B8E;PSALTER PAHLAVI LETTER PE;Lo;0;R;;;;;N;;;;;
+10B8F;PSALTER PAHLAVI LETTER SADHE;Lo;0;R;;;;;N;;;;;
+10B90;PSALTER PAHLAVI LETTER SHIN;Lo;0;R;;;;;N;;;;;
+10B91;PSALTER PAHLAVI LETTER TAW;Lo;0;R;;;;;N;;;;;
+10B99;PSALTER PAHLAVI SECTION MARK;Po;0;R;;;;;N;;;;;
+10B9A;PSALTER PAHLAVI TURNED SECTION MARK;Po;0;R;;;;;N;;;;;
+10B9B;PSALTER PAHLAVI FOUR DOTS WITH CROSS;Po;0;R;;;;;N;;;;;
+10B9C;PSALTER PAHLAVI FOUR DOTS WITH DOT;Po;0;R;;;;;N;;;;;
+10BA9;PSALTER PAHLAVI NUMBER ONE;No;0;R;;;;1;N;;;;;
+10BAA;PSALTER PAHLAVI NUMBER TWO;No;0;R;;;;2;N;;;;;
+10BAB;PSALTER PAHLAVI NUMBER THREE;No;0;R;;;;3;N;;;;;
+10BAC;PSALTER PAHLAVI NUMBER FOUR;No;0;R;;;;4;N;;;;;
+10BAD;PSALTER PAHLAVI NUMBER TEN;No;0;R;;;;10;N;;;;;
+10BAE;PSALTER PAHLAVI NUMBER TWENTY;No;0;R;;;;20;N;;;;;
+10BAF;PSALTER PAHLAVI NUMBER ONE HUNDRED;No;0;R;;;;100;N;;;;;
 10C00;OLD TURKIC LETTER ORKHON A;Lo;0;R;;;;;N;;;;;
 10C01;OLD TURKIC LETTER YENISEI A;Lo;0;R;;;;;N;;;;;
 10C02;OLD TURKIC LETTER YENISEI AE;Lo;0;R;;;;;N;;;;;
@@ -17458,6 +18483,7 @@
 1106D;BRAHMI DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;;
 1106E;BRAHMI DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;;
 1106F;BRAHMI DIGIT NINE;Nd;0;L;;9;9;9;N;;;;;
+1107F;BRAHMI NUMBER JOINER;Mn;9;NSM;;;;;N;;;;;
 11080;KAITHI SIGN CANDRABINDU;Mn;0;NSM;;;;;N;;;;;
 11081;KAITHI SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;;
 11082;KAITHI SIGN VISARGA;Mc;0;L;;;;;N;;;;;
@@ -17626,6 +18652,45 @@
 11141;CHAKMA DANDA;Po;0;L;;;;;N;;;;;
 11142;CHAKMA DOUBLE DANDA;Po;0;L;;;;;N;;;;;
 11143;CHAKMA QUESTION MARK;Po;0;L;;;;;N;;;;;
+11150;MAHAJANI LETTER A;Lo;0;L;;;;;N;;;;;
+11151;MAHAJANI LETTER I;Lo;0;L;;;;;N;;;;;
+11152;MAHAJANI LETTER U;Lo;0;L;;;;;N;;;;;
+11153;MAHAJANI LETTER E;Lo;0;L;;;;;N;;;;;
+11154;MAHAJANI LETTER O;Lo;0;L;;;;;N;;;;;
+11155;MAHAJANI LETTER KA;Lo;0;L;;;;;N;;;;;
+11156;MAHAJANI LETTER KHA;Lo;0;L;;;;;N;;;;;
+11157;MAHAJANI LETTER GA;Lo;0;L;;;;;N;;;;;
+11158;MAHAJANI LETTER GHA;Lo;0;L;;;;;N;;;;;
+11159;MAHAJANI LETTER CA;Lo;0;L;;;;;N;;;;;
+1115A;MAHAJANI LETTER CHA;Lo;0;L;;;;;N;;;;;
+1115B;MAHAJANI LETTER JA;Lo;0;L;;;;;N;;;;;
+1115C;MAHAJANI LETTER JHA;Lo;0;L;;;;;N;;;;;
+1115D;MAHAJANI LETTER NYA;Lo;0;L;;;;;N;;;;;
+1115E;MAHAJANI LETTER TTA;Lo;0;L;;;;;N;;;;;
+1115F;MAHAJANI LETTER TTHA;Lo;0;L;;;;;N;;;;;
+11160;MAHAJANI LETTER DDA;Lo;0;L;;;;;N;;;;;
+11161;MAHAJANI LETTER DDHA;Lo;0;L;;;;;N;;;;;
+11162;MAHAJANI LETTER NNA;Lo;0;L;;;;;N;;;;;
+11163;MAHAJANI LETTER TA;Lo;0;L;;;;;N;;;;;
+11164;MAHAJANI LETTER THA;Lo;0;L;;;;;N;;;;;
+11165;MAHAJANI LETTER DA;Lo;0;L;;;;;N;;;;;
+11166;MAHAJANI LETTER DHA;Lo;0;L;;;;;N;;;;;
+11167;MAHAJANI LETTER NA;Lo;0;L;;;;;N;;;;;
+11168;MAHAJANI LETTER PA;Lo;0;L;;;;;N;;;;;
+11169;MAHAJANI LETTER PHA;Lo;0;L;;;;;N;;;;;
+1116A;MAHAJANI LETTER BA;Lo;0;L;;;;;N;;;;;
+1116B;MAHAJANI LETTER BHA;Lo;0;L;;;;;N;;;;;
+1116C;MAHAJANI LETTER MA;Lo;0;L;;;;;N;;;;;
+1116D;MAHAJANI LETTER RA;Lo;0;L;;;;;N;;;;;
+1116E;MAHAJANI LETTER LA;Lo;0;L;;;;;N;;;;;
+1116F;MAHAJANI LETTER VA;Lo;0;L;;;;;N;;;;;
+11170;MAHAJANI LETTER SA;Lo;0;L;;;;;N;;;;;
+11171;MAHAJANI LETTER HA;Lo;0;L;;;;;N;;;;;
+11172;MAHAJANI LETTER RRA;Lo;0;L;;;;;N;;;;;
+11173;MAHAJANI SIGN NUKTA;Mn;7;NSM;;;;;N;;;;;
+11174;MAHAJANI ABBREVIATION SIGN;Po;0;L;;;;;N;;;;;
+11175;MAHAJANI SECTION MARK;Po;0;L;;;;;N;;;;;
+11176;MAHAJANI LIGATURE SHRI;Lo;0;L;;;;;N;;;;;
 11180;SHARADA SIGN CANDRABINDU;Mn;0;NSM;;;;;N;;;;;
 11181;SHARADA SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;;
 11182;SHARADA SIGN VISARGA;Mc;0;L;;;;;N;;;;;
@@ -17699,6 +18764,7 @@
 111C6;SHARADA DOUBLE DANDA;Po;0;L;;;;;N;;;;;
 111C7;SHARADA ABBREVIATION SIGN;Po;0;L;;;;;N;;;;;
 111C8;SHARADA SEPARATOR;Po;0;L;;;;;N;;;;;
+111CD;SHARADA SUTRA MARK;Po;0;L;;;;;N;;;;;
 111D0;SHARADA DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;;
 111D1;SHARADA DIGIT ONE;Nd;0;L;;1;1;1;N;;;;;
 111D2;SHARADA DIGIT TWO;Nd;0;L;;2;2;2;N;;;;;
@@ -17709,6 +18775,473 @@
 111D7;SHARADA DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;;
 111D8;SHARADA DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;;
 111D9;SHARADA DIGIT NINE;Nd;0;L;;9;9;9;N;;;;;
+111DA;SHARADA EKAM;Lo;0;L;;;;;N;;;;;
+111E1;SINHALA ARCHAIC DIGIT ONE;No;0;L;;;;1;N;;;;;
+111E2;SINHALA ARCHAIC DIGIT TWO;No;0;L;;;;2;N;;;;;
+111E3;SINHALA ARCHAIC DIGIT THREE;No;0;L;;;;3;N;;;;;
+111E4;SINHALA ARCHAIC DIGIT FOUR;No;0;L;;;;4;N;;;;;
+111E5;SINHALA ARCHAIC DIGIT FIVE;No;0;L;;;;5;N;;;;;
+111E6;SINHALA ARCHAIC DIGIT SIX;No;0;L;;;;6;N;;;;;
+111E7;SINHALA ARCHAIC DIGIT SEVEN;No;0;L;;;;7;N;;;;;
+111E8;SINHALA ARCHAIC DIGIT EIGHT;No;0;L;;;;8;N;;;;;
+111E9;SINHALA ARCHAIC DIGIT NINE;No;0;L;;;;9;N;;;;;
+111EA;SINHALA ARCHAIC NUMBER TEN;No;0;L;;;;10;N;;;;;
+111EB;SINHALA ARCHAIC NUMBER TWENTY;No;0;L;;;;20;N;;;;;
+111EC;SINHALA ARCHAIC NUMBER THIRTY;No;0;L;;;;30;N;;;;;
+111ED;SINHALA ARCHAIC NUMBER FORTY;No;0;L;;;;40;N;;;;;
+111EE;SINHALA ARCHAIC NUMBER FIFTY;No;0;L;;;;50;N;;;;;
+111EF;SINHALA ARCHAIC NUMBER SIXTY;No;0;L;;;;60;N;;;;;
+111F0;SINHALA ARCHAIC NUMBER SEVENTY;No;0;L;;;;70;N;;;;;
+111F1;SINHALA ARCHAIC NUMBER EIGHTY;No;0;L;;;;80;N;;;;;
+111F2;SINHALA ARCHAIC NUMBER NINETY;No;0;L;;;;90;N;;;;;
+111F3;SINHALA ARCHAIC NUMBER ONE HUNDRED;No;0;L;;;;100;N;;;;;
+111F4;SINHALA ARCHAIC NUMBER ONE THOUSAND;No;0;L;;;;1000;N;;;;;
+11200;KHOJKI LETTER A;Lo;0;L;;;;;N;;;;;
+11201;KHOJKI LETTER AA;Lo;0;L;;;;;N;;;;;
+11202;KHOJKI LETTER I;Lo;0;L;;;;;N;;;;;
+11203;KHOJKI LETTER U;Lo;0;L;;;;;N;;;;;
+11204;KHOJKI LETTER E;Lo;0;L;;;;;N;;;;;
+11205;KHOJKI LETTER AI;Lo;0;L;;;;;N;;;;;
+11206;KHOJKI LETTER O;Lo;0;L;;;;;N;;;;;
+11207;KHOJKI LETTER AU;Lo;0;L;;;;;N;;;;;
+11208;KHOJKI LETTER KA;Lo;0;L;;;;;N;;;;;
+11209;KHOJKI LETTER KHA;Lo;0;L;;;;;N;;;;;
+1120A;KHOJKI LETTER GA;Lo;0;L;;;;;N;;;;;
+1120B;KHOJKI LETTER GGA;Lo;0;L;;;;;N;;;;;
+1120C;KHOJKI LETTER GHA;Lo;0;L;;;;;N;;;;;
+1120D;KHOJKI LETTER NGA;Lo;0;L;;;;;N;;;;;
+1120E;KHOJKI LETTER CA;Lo;0;L;;;;;N;;;;;
+1120F;KHOJKI LETTER CHA;Lo;0;L;;;;;N;;;;;
+11210;KHOJKI LETTER JA;Lo;0;L;;;;;N;;;;;
+11211;KHOJKI LETTER JJA;Lo;0;L;;;;;N;;;;;
+11213;KHOJKI LETTER NYA;Lo;0;L;;;;;N;;;;;
+11214;KHOJKI LETTER TTA;Lo;0;L;;;;;N;;;;;
+11215;KHOJKI LETTER TTHA;Lo;0;L;;;;;N;;;;;
+11216;KHOJKI LETTER DDA;Lo;0;L;;;;;N;;;;;
+11217;KHOJKI LETTER DDHA;Lo;0;L;;;;;N;;;;;
+11218;KHOJKI LETTER NNA;Lo;0;L;;;;;N;;;;;
+11219;KHOJKI LETTER TA;Lo;0;L;;;;;N;;;;;
+1121A;KHOJKI LETTER THA;Lo;0;L;;;;;N;;;;;
+1121B;KHOJKI LETTER DA;Lo;0;L;;;;;N;;;;;
+1121C;KHOJKI LETTER DDDA;Lo;0;L;;;;;N;;;;;
+1121D;KHOJKI LETTER DHA;Lo;0;L;;;;;N;;;;;
+1121E;KHOJKI LETTER NA;Lo;0;L;;;;;N;;;;;
+1121F;KHOJKI LETTER PA;Lo;0;L;;;;;N;;;;;
+11220;KHOJKI LETTER PHA;Lo;0;L;;;;;N;;;;;
+11221;KHOJKI LETTER BA;Lo;0;L;;;;;N;;;;;
+11222;KHOJKI LETTER BBA;Lo;0;L;;;;;N;;;;;
+11223;KHOJKI LETTER BHA;Lo;0;L;;;;;N;;;;;
+11224;KHOJKI LETTER MA;Lo;0;L;;;;;N;;;;;
+11225;KHOJKI LETTER YA;Lo;0;L;;;;;N;;;;;
+11226;KHOJKI LETTER RA;Lo;0;L;;;;;N;;;;;
+11227;KHOJKI LETTER LA;Lo;0;L;;;;;N;;;;;
+11228;KHOJKI LETTER VA;Lo;0;L;;;;;N;;;;;
+11229;KHOJKI LETTER SA;Lo;0;L;;;;;N;;;;;
+1122A;KHOJKI LETTER HA;Lo;0;L;;;;;N;;;;;
+1122B;KHOJKI LETTER LLA;Lo;0;L;;;;;N;;;;;
+1122C;KHOJKI VOWEL SIGN AA;Mc;0;L;;;;;N;;;;;
+1122D;KHOJKI VOWEL SIGN I;Mc;0;L;;;;;N;;;;;
+1122E;KHOJKI VOWEL SIGN II;Mc;0;L;;;;;N;;;;;
+1122F;KHOJKI VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;;
+11230;KHOJKI VOWEL SIGN E;Mn;0;NSM;;;;;N;;;;;
+11231;KHOJKI VOWEL SIGN AI;Mn;0;NSM;;;;;N;;;;;
+11232;KHOJKI VOWEL SIGN O;Mc;0;L;;;;;N;;;;;
+11233;KHOJKI VOWEL SIGN AU;Mc;0;L;;;;;N;;;;;
+11234;KHOJKI SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;;
+11235;KHOJKI SIGN VIRAMA;Mc;9;L;;;;;N;;;;;
+11236;KHOJKI SIGN NUKTA;Mn;7;NSM;;;;;N;;;;;
+11237;KHOJKI SIGN SHADDA;Mn;0;NSM;;;;;N;;;;;
+11238;KHOJKI DANDA;Po;0;L;;;;;N;;;;;
+11239;KHOJKI DOUBLE DANDA;Po;0;L;;;;;N;;;;;
+1123A;KHOJKI WORD SEPARATOR;Po;0;L;;;;;N;;;;;
+1123B;KHOJKI SECTION MARK;Po;0;L;;;;;N;;;;;
+1123C;KHOJKI DOUBLE SECTION MARK;Po;0;L;;;;;N;;;;;
+1123D;KHOJKI ABBREVIATION SIGN;Po;0;L;;;;;N;;;;;
+112B0;KHUDAWADI LETTER A;Lo;0;L;;;;;N;;;;;
+112B1;KHUDAWADI LETTER AA;Lo;0;L;;;;;N;;;;;
+112B2;KHUDAWADI LETTER I;Lo;0;L;;;;;N;;;;;
+112B3;KHUDAWADI LETTER II;Lo;0;L;;;;;N;;;;;
+112B4;KHUDAWADI LETTER U;Lo;0;L;;;;;N;;;;;
+112B5;KHUDAWADI LETTER UU;Lo;0;L;;;;;N;;;;;
+112B6;KHUDAWADI LETTER E;Lo;0;L;;;;;N;;;;;
+112B7;KHUDAWADI LETTER AI;Lo;0;L;;;;;N;;;;;
+112B8;KHUDAWADI LETTER O;Lo;0;L;;;;;N;;;;;
+112B9;KHUDAWADI LETTER AU;Lo;0;L;;;;;N;;;;;
+112BA;KHUDAWADI LETTER KA;Lo;0;L;;;;;N;;;;;
+112BB;KHUDAWADI LETTER KHA;Lo;0;L;;;;;N;;;;;
+112BC;KHUDAWADI LETTER GA;Lo;0;L;;;;;N;;;;;
+112BD;KHUDAWADI LETTER GGA;Lo;0;L;;;;;N;;;;;
+112BE;KHUDAWADI LETTER GHA;Lo;0;L;;;;;N;;;;;
+112BF;KHUDAWADI LETTER NGA;Lo;0;L;;;;;N;;;;;
+112C0;KHUDAWADI LETTER CA;Lo;0;L;;;;;N;;;;;
+112C1;KHUDAWADI LETTER CHA;Lo;0;L;;;;;N;;;;;
+112C2;KHUDAWADI LETTER JA;Lo;0;L;;;;;N;;;;;
+112C3;KHUDAWADI LETTER JJA;Lo;0;L;;;;;N;;;;;
+112C4;KHUDAWADI LETTER JHA;Lo;0;L;;;;;N;;;;;
+112C5;KHUDAWADI LETTER NYA;Lo;0;L;;;;;N;;;;;
+112C6;KHUDAWADI LETTER TTA;Lo;0;L;;;;;N;;;;;
+112C7;KHUDAWADI LETTER TTHA;Lo;0;L;;;;;N;;;;;
+112C8;KHUDAWADI LETTER DDA;Lo;0;L;;;;;N;;;;;
+112C9;KHUDAWADI LETTER DDDA;Lo;0;L;;;;;N;;;;;
+112CA;KHUDAWADI LETTER RRA;Lo;0;L;;;;;N;;;;;
+112CB;KHUDAWADI LETTER DDHA;Lo;0;L;;;;;N;;;;;
+112CC;KHUDAWADI LETTER NNA;Lo;0;L;;;;;N;;;;;
+112CD;KHUDAWADI LETTER TA;Lo;0;L;;;;;N;;;;;
+112CE;KHUDAWADI LETTER THA;Lo;0;L;;;;;N;;;;;
+112CF;KHUDAWADI LETTER DA;Lo;0;L;;;;;N;;;;;
+112D0;KHUDAWADI LETTER DHA;Lo;0;L;;;;;N;;;;;
+112D1;KHUDAWADI LETTER NA;Lo;0;L;;;;;N;;;;;
+112D2;KHUDAWADI LETTER PA;Lo;0;L;;;;;N;;;;;
+112D3;KHUDAWADI LETTER PHA;Lo;0;L;;;;;N;;;;;
+112D4;KHUDAWADI LETTER BA;Lo;0;L;;;;;N;;;;;
+112D5;KHUDAWADI LETTER BBA;Lo;0;L;;;;;N;;;;;
+112D6;KHUDAWADI LETTER BHA;Lo;0;L;;;;;N;;;;;
+112D7;KHUDAWADI LETTER MA;Lo;0;L;;;;;N;;;;;
+112D8;KHUDAWADI LETTER YA;Lo;0;L;;;;;N;;;;;
+112D9;KHUDAWADI LETTER RA;Lo;0;L;;;;;N;;;;;
+112DA;KHUDAWADI LETTER LA;Lo;0;L;;;;;N;;;;;
+112DB;KHUDAWADI LETTER VA;Lo;0;L;;;;;N;;;;;
+112DC;KHUDAWADI LETTER SHA;Lo;0;L;;;;;N;;;;;
+112DD;KHUDAWADI LETTER SA;Lo;0;L;;;;;N;;;;;
+112DE;KHUDAWADI LETTER HA;Lo;0;L;;;;;N;;;;;
+112DF;KHUDAWADI SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;;
+112E0;KHUDAWADI VOWEL SIGN AA;Mc;0;L;;;;;N;;;;;
+112E1;KHUDAWADI VOWEL SIGN I;Mc;0;L;;;;;N;;;;;
+112E2;KHUDAWADI VOWEL SIGN II;Mc;0;L;;;;;N;;;;;
+112E3;KHUDAWADI VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;;
+112E4;KHUDAWADI VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;;
+112E5;KHUDAWADI VOWEL SIGN E;Mn;0;NSM;;;;;N;;;;;
+112E6;KHUDAWADI VOWEL SIGN AI;Mn;0;NSM;;;;;N;;;;;
+112E7;KHUDAWADI VOWEL SIGN O;Mn;0;NSM;;;;;N;;;;;
+112E8;KHUDAWADI VOWEL SIGN AU;Mn;0;NSM;;;;;N;;;;;
+112E9;KHUDAWADI SIGN NUKTA;Mn;7;NSM;;;;;N;;;;;
+112EA;KHUDAWADI SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;;
+112F0;KHUDAWADI DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;;
+112F1;KHUDAWADI DIGIT ONE;Nd;0;L;;1;1;1;N;;;;;
+112F2;KHUDAWADI DIGIT TWO;Nd;0;L;;2;2;2;N;;;;;
+112F3;KHUDAWADI DIGIT THREE;Nd;0;L;;3;3;3;N;;;;;
+112F4;KHUDAWADI DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;;
+112F5;KHUDAWADI DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;;
+112F6;KHUDAWADI DIGIT SIX;Nd;0;L;;6;6;6;N;;;;;
+112F7;KHUDAWADI DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;;
+112F8;KHUDAWADI DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;;
+112F9;KHUDAWADI DIGIT NINE;Nd;0;L;;9;9;9;N;;;;;
+11301;GRANTHA SIGN CANDRABINDU;Mn;0;NSM;;;;;N;;;;;
+11302;GRANTHA SIGN ANUSVARA;Mc;0;L;;;;;N;;;;;
+11303;GRANTHA SIGN VISARGA;Mc;0;L;;;;;N;;;;;
+11305;GRANTHA LETTER A;Lo;0;L;;;;;N;;;;;
+11306;GRANTHA LETTER AA;Lo;0;L;;;;;N;;;;;
+11307;GRANTHA LETTER I;Lo;0;L;;;;;N;;;;;
+11308;GRANTHA LETTER II;Lo;0;L;;;;;N;;;;;
+11309;GRANTHA LETTER U;Lo;0;L;;;;;N;;;;;
+1130A;GRANTHA LETTER UU;Lo;0;L;;;;;N;;;;;
+1130B;GRANTHA LETTER VOCALIC R;Lo;0;L;;;;;N;;;;;
+1130C;GRANTHA LETTER VOCALIC L;Lo;0;L;;;;;N;;;;;
+1130F;GRANTHA LETTER EE;Lo;0;L;;;;;N;;;;;
+11310;GRANTHA LETTER AI;Lo;0;L;;;;;N;;;;;
+11313;GRANTHA LETTER OO;Lo;0;L;;;;;N;;;;;
+11314;GRANTHA LETTER AU;Lo;0;L;;;;;N;;;;;
+11315;GRANTHA LETTER KA;Lo;0;L;;;;;N;;;;;
+11316;GRANTHA LETTER KHA;Lo;0;L;;;;;N;;;;;
+11317;GRANTHA LETTER GA;Lo;0;L;;;;;N;;;;;
+11318;GRANTHA LETTER GHA;Lo;0;L;;;;;N;;;;;
+11319;GRANTHA LETTER NGA;Lo;0;L;;;;;N;;;;;
+1131A;GRANTHA LETTER CA;Lo;0;L;;;;;N;;;;;
+1131B;GRANTHA LETTER CHA;Lo;0;L;;;;;N;;;;;
+1131C;GRANTHA LETTER JA;Lo;0;L;;;;;N;;;;;
+1131D;GRANTHA LETTER JHA;Lo;0;L;;;;;N;;;;;
+1131E;GRANTHA LETTER NYA;Lo;0;L;;;;;N;;;;;
+1131F;GRANTHA LETTER TTA;Lo;0;L;;;;;N;;;;;
+11320;GRANTHA LETTER TTHA;Lo;0;L;;;;;N;;;;;
+11321;GRANTHA LETTER DDA;Lo;0;L;;;;;N;;;;;
+11322;GRANTHA LETTER DDHA;Lo;0;L;;;;;N;;;;;
+11323;GRANTHA LETTER NNA;Lo;0;L;;;;;N;;;;;
+11324;GRANTHA LETTER TA;Lo;0;L;;;;;N;;;;;
+11325;GRANTHA LETTER THA;Lo;0;L;;;;;N;;;;;
+11326;GRANTHA LETTER DA;Lo;0;L;;;;;N;;;;;
+11327;GRANTHA LETTER DHA;Lo;0;L;;;;;N;;;;;
+11328;GRANTHA LETTER NA;Lo;0;L;;;;;N;;;;;
+1132A;GRANTHA LETTER PA;Lo;0;L;;;;;N;;;;;
+1132B;GRANTHA LETTER PHA;Lo;0;L;;;;;N;;;;;
+1132C;GRANTHA LETTER BA;Lo;0;L;;;;;N;;;;;
+1132D;GRANTHA LETTER BHA;Lo;0;L;;;;;N;;;;;
+1132E;GRANTHA LETTER MA;Lo;0;L;;;;;N;;;;;
+1132F;GRANTHA LETTER YA;Lo;0;L;;;;;N;;;;;
+11330;GRANTHA LETTER RA;Lo;0;L;;;;;N;;;;;
+11332;GRANTHA LETTER LA;Lo;0;L;;;;;N;;;;;
+11333;GRANTHA LETTER LLA;Lo;0;L;;;;;N;;;;;
+11335;GRANTHA LETTER VA;Lo;0;L;;;;;N;;;;;
+11336;GRANTHA LETTER SHA;Lo;0;L;;;;;N;;;;;
+11337;GRANTHA LETTER SSA;Lo;0;L;;;;;N;;;;;
+11338;GRANTHA LETTER SA;Lo;0;L;;;;;N;;;;;
+11339;GRANTHA LETTER HA;Lo;0;L;;;;;N;;;;;
+1133C;GRANTHA SIGN NUKTA;Mn;7;NSM;;;;;N;;;;;
+1133D;GRANTHA SIGN AVAGRAHA;Lo;0;L;;;;;N;;;;;
+1133E;GRANTHA VOWEL SIGN AA;Mc;0;L;;;;;N;;;;;
+1133F;GRANTHA VOWEL SIGN I;Mc;0;L;;;;;N;;;;;
+11340;GRANTHA VOWEL SIGN II;Mn;0;NSM;;;;;N;;;;;
+11341;GRANTHA VOWEL SIGN U;Mc;0;L;;;;;N;;;;;
+11342;GRANTHA VOWEL SIGN UU;Mc;0;L;;;;;N;;;;;
+11343;GRANTHA VOWEL SIGN VOCALIC R;Mc;0;L;;;;;N;;;;;
+11344;GRANTHA VOWEL SIGN VOCALIC RR;Mc;0;L;;;;;N;;;;;
+11347;GRANTHA VOWEL SIGN EE;Mc;0;L;;;;;N;;;;;
+11348;GRANTHA VOWEL SIGN AI;Mc;0;L;;;;;N;;;;;
+1134B;GRANTHA VOWEL SIGN OO;Mc;0;L;11347 1133E;;;;N;;;;;
+1134C;GRANTHA VOWEL SIGN AU;Mc;0;L;11347 11357;;;;N;;;;;
+1134D;GRANTHA SIGN VIRAMA;Mc;9;L;;;;;N;;;;;
+11357;GRANTHA AU LENGTH MARK;Mc;0;L;;;;;N;;;;;
+1135D;GRANTHA SIGN PLUTA;Lo;0;L;;;;;N;;;;;
+1135E;GRANTHA LETTER VEDIC ANUSVARA;Lo;0;L;;;;;N;;;;;
+1135F;GRANTHA LETTER VEDIC DOUBLE ANUSVARA;Lo;0;L;;;;;N;;;;;
+11360;GRANTHA LETTER VOCALIC RR;Lo;0;L;;;;;N;;;;;
+11361;GRANTHA LETTER VOCALIC LL;Lo;0;L;;;;;N;;;;;
+11362;GRANTHA VOWEL SIGN VOCALIC L;Mc;0;L;;;;;N;;;;;
+11363;GRANTHA VOWEL SIGN VOCALIC LL;Mc;0;L;;;;;N;;;;;
+11366;COMBINING GRANTHA DIGIT ZERO;Mn;230;NSM;;;;;N;;;;;
+11367;COMBINING GRANTHA DIGIT ONE;Mn;230;NSM;;;;;N;;;;;
+11368;COMBINING GRANTHA DIGIT TWO;Mn;230;NSM;;;;;N;;;;;
+11369;COMBINING GRANTHA DIGIT THREE;Mn;230;NSM;;;;;N;;;;;
+1136A;COMBINING GRANTHA DIGIT FOUR;Mn;230;NSM;;;;;N;;;;;
+1136B;COMBINING GRANTHA DIGIT FIVE;Mn;230;NSM;;;;;N;;;;;
+1136C;COMBINING GRANTHA DIGIT SIX;Mn;230;NSM;;;;;N;;;;;
+11370;COMBINING GRANTHA LETTER A;Mn;230;NSM;;;;;N;;;;;
+11371;COMBINING GRANTHA LETTER KA;Mn;230;NSM;;;;;N;;;;;
+11372;COMBINING GRANTHA LETTER NA;Mn;230;NSM;;;;;N;;;;;
+11373;COMBINING GRANTHA LETTER VI;Mn;230;NSM;;;;;N;;;;;
+11374;COMBINING GRANTHA LETTER PA;Mn;230;NSM;;;;;N;;;;;
+11480;TIRHUTA ANJI;Lo;0;L;;;;;N;;;;;
+11481;TIRHUTA LETTER A;Lo;0;L;;;;;N;;;;;
+11482;TIRHUTA LETTER AA;Lo;0;L;;;;;N;;;;;
+11483;TIRHUTA LETTER I;Lo;0;L;;;;;N;;;;;
+11484;TIRHUTA LETTER II;Lo;0;L;;;;;N;;;;;
+11485;TIRHUTA LETTER U;Lo;0;L;;;;;N;;;;;
+11486;TIRHUTA LETTER UU;Lo;0;L;;;;;N;;;;;
+11487;TIRHUTA LETTER VOCALIC R;Lo;0;L;;;;;N;;;;;
+11488;TIRHUTA LETTER VOCALIC RR;Lo;0;L;;;;;N;;;;;
+11489;TIRHUTA LETTER VOCALIC L;Lo;0;L;;;;;N;;;;;
+1148A;TIRHUTA LETTER VOCALIC LL;Lo;0;L;;;;;N;;;;;
+1148B;TIRHUTA LETTER E;Lo;0;L;;;;;N;;;;;
+1148C;TIRHUTA LETTER AI;Lo;0;L;;;;;N;;;;;
+1148D;TIRHUTA LETTER O;Lo;0;L;;;;;N;;;;;
+1148E;TIRHUTA LETTER AU;Lo;0;L;;;;;N;;;;;
+1148F;TIRHUTA LETTER KA;Lo;0;L;;;;;N;;;;;
+11490;TIRHUTA LETTER KHA;Lo;0;L;;;;;N;;;;;
+11491;TIRHUTA LETTER GA;Lo;0;L;;;;;N;;;;;
+11492;TIRHUTA LETTER GHA;Lo;0;L;;;;;N;;;;;
+11493;TIRHUTA LETTER NGA;Lo;0;L;;;;;N;;;;;
+11494;TIRHUTA LETTER CA;Lo;0;L;;;;;N;;;;;
+11495;TIRHUTA LETTER CHA;Lo;0;L;;;;;N;;;;;
+11496;TIRHUTA LETTER JA;Lo;0;L;;;;;N;;;;;
+11497;TIRHUTA LETTER JHA;Lo;0;L;;;;;N;;;;;
+11498;TIRHUTA LETTER NYA;Lo;0;L;;;;;N;;;;;
+11499;TIRHUTA LETTER TTA;Lo;0;L;;;;;N;;;;;
+1149A;TIRHUTA LETTER TTHA;Lo;0;L;;;;;N;;;;;
+1149B;TIRHUTA LETTER DDA;Lo;0;L;;;;;N;;;;;
+1149C;TIRHUTA LETTER DDHA;Lo;0;L;;;;;N;;;;;
+1149D;TIRHUTA LETTER NNA;Lo;0;L;;;;;N;;;;;
+1149E;TIRHUTA LETTER TA;Lo;0;L;;;;;N;;;;;
+1149F;TIRHUTA LETTER THA;Lo;0;L;;;;;N;;;;;
+114A0;TIRHUTA LETTER DA;Lo;0;L;;;;;N;;;;;
+114A1;TIRHUTA LETTER DHA;Lo;0;L;;;;;N;;;;;
+114A2;TIRHUTA LETTER NA;Lo;0;L;;;;;N;;;;;
+114A3;TIRHUTA LETTER PA;Lo;0;L;;;;;N;;;;;
+114A4;TIRHUTA LETTER PHA;Lo;0;L;;;;;N;;;;;
+114A5;TIRHUTA LETTER BA;Lo;0;L;;;;;N;;;;;
+114A6;TIRHUTA LETTER BHA;Lo;0;L;;;;;N;;;;;
+114A7;TIRHUTA LETTER MA;Lo;0;L;;;;;N;;;;;
+114A8;TIRHUTA LETTER YA;Lo;0;L;;;;;N;;;;;
+114A9;TIRHUTA LETTER RA;Lo;0;L;;;;;N;;;;;
+114AA;TIRHUTA LETTER LA;Lo;0;L;;;;;N;;;;;
+114AB;TIRHUTA LETTER VA;Lo;0;L;;;;;N;;;;;
+114AC;TIRHUTA LETTER SHA;Lo;0;L;;;;;N;;;;;
+114AD;TIRHUTA LETTER SSA;Lo;0;L;;;;;N;;;;;
+114AE;TIRHUTA LETTER SA;Lo;0;L;;;;;N;;;;;
+114AF;TIRHUTA LETTER HA;Lo;0;L;;;;;N;;;;;
+114B0;TIRHUTA VOWEL SIGN AA;Mc;0;L;;;;;N;;;;;
+114B1;TIRHUTA VOWEL SIGN I;Mc;0;L;;;;;N;;;;;
+114B2;TIRHUTA VOWEL SIGN II;Mc;0;L;;;;;N;;;;;
+114B3;TIRHUTA VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;;
+114B4;TIRHUTA VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;;
+114B5;TIRHUTA VOWEL SIGN VOCALIC R;Mn;0;NSM;;;;;N;;;;;
+114B6;TIRHUTA VOWEL SIGN VOCALIC RR;Mn;0;NSM;;;;;N;;;;;
+114B7;TIRHUTA VOWEL SIGN VOCALIC L;Mn;0;NSM;;;;;N;;;;;
+114B8;TIRHUTA VOWEL SIGN VOCALIC LL;Mn;0;NSM;;;;;N;;;;;
+114B9;TIRHUTA VOWEL SIGN E;Mc;0;L;;;;;N;;;;;
+114BA;TIRHUTA VOWEL SIGN SHORT E;Mn;0;NSM;;;;;N;;;;;
+114BB;TIRHUTA VOWEL SIGN AI;Mc;0;L;114B9 114BA;;;;N;;;;;
+114BC;TIRHUTA VOWEL SIGN O;Mc;0;L;114B9 114B0;;;;N;;;;;
+114BD;TIRHUTA VOWEL SIGN SHORT O;Mc;0;L;;;;;N;;;;;
+114BE;TIRHUTA VOWEL SIGN AU;Mc;0;L;114B9 114BD;;;;N;;;;;
+114BF;TIRHUTA SIGN CANDRABINDU;Mn;0;NSM;;;;;N;;;;;
+114C0;TIRHUTA SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;;
+114C1;TIRHUTA SIGN VISARGA;Mc;0;L;;;;;N;;;;;
+114C2;TIRHUTA SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;;
+114C3;TIRHUTA SIGN NUKTA;Mn;7;NSM;;;;;N;;;;;
+114C4;TIRHUTA SIGN AVAGRAHA;Lo;0;L;;;;;N;;;;;
+114C5;TIRHUTA GVANG;Lo;0;L;;;;;N;;;;;
+114C6;TIRHUTA ABBREVIATION SIGN;Po;0;L;;;;;N;;;;;
+114C7;TIRHUTA OM;Lo;0;L;;;;;N;;;;;
+114D0;TIRHUTA DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;;
+114D1;TIRHUTA DIGIT ONE;Nd;0;L;;1;1;1;N;;;;;
+114D2;TIRHUTA DIGIT TWO;Nd;0;L;;2;2;2;N;;;;;
+114D3;TIRHUTA DIGIT THREE;Nd;0;L;;3;3;3;N;;;;;
+114D4;TIRHUTA DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;;
+114D5;TIRHUTA DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;;
+114D6;TIRHUTA DIGIT SIX;Nd;0;L;;6;6;6;N;;;;;
+114D7;TIRHUTA DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;;
+114D8;TIRHUTA DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;;
+114D9;TIRHUTA DIGIT NINE;Nd;0;L;;9;9;9;N;;;;;
+11580;SIDDHAM LETTER A;Lo;0;L;;;;;N;;;;;
+11581;SIDDHAM LETTER AA;Lo;0;L;;;;;N;;;;;
+11582;SIDDHAM LETTER I;Lo;0;L;;;;;N;;;;;
+11583;SIDDHAM LETTER II;Lo;0;L;;;;;N;;;;;
+11584;SIDDHAM LETTER U;Lo;0;L;;;;;N;;;;;
+11585;SIDDHAM LETTER UU;Lo;0;L;;;;;N;;;;;
+11586;SIDDHAM LETTER VOCALIC R;Lo;0;L;;;;;N;;;;;
+11587;SIDDHAM LETTER VOCALIC RR;Lo;0;L;;;;;N;;;;;
+11588;SIDDHAM LETTER VOCALIC L;Lo;0;L;;;;;N;;;;;
+11589;SIDDHAM LETTER VOCALIC LL;Lo;0;L;;;;;N;;;;;
+1158A;SIDDHAM LETTER E;Lo;0;L;;;;;N;;;;;
+1158B;SIDDHAM LETTER AI;Lo;0;L;;;;;N;;;;;
+1158C;SIDDHAM LETTER O;Lo;0;L;;;;;N;;;;;
+1158D;SIDDHAM LETTER AU;Lo;0;L;;;;;N;;;;;
+1158E;SIDDHAM LETTER KA;Lo;0;L;;;;;N;;;;;
+1158F;SIDDHAM LETTER KHA;Lo;0;L;;;;;N;;;;;
+11590;SIDDHAM LETTER GA;Lo;0;L;;;;;N;;;;;
+11591;SIDDHAM LETTER GHA;Lo;0;L;;;;;N;;;;;
+11592;SIDDHAM LETTER NGA;Lo;0;L;;;;;N;;;;;
+11593;SIDDHAM LETTER CA;Lo;0;L;;;;;N;;;;;
+11594;SIDDHAM LETTER CHA;Lo;0;L;;;;;N;;;;;
+11595;SIDDHAM LETTER JA;Lo;0;L;;;;;N;;;;;
+11596;SIDDHAM LETTER JHA;Lo;0;L;;;;;N;;;;;
+11597;SIDDHAM LETTER NYA;Lo;0;L;;;;;N;;;;;
+11598;SIDDHAM LETTER TTA;Lo;0;L;;;;;N;;;;;
+11599;SIDDHAM LETTER TTHA;Lo;0;L;;;;;N;;;;;
+1159A;SIDDHAM LETTER DDA;Lo;0;L;;;;;N;;;;;
+1159B;SIDDHAM LETTER DDHA;Lo;0;L;;;;;N;;;;;
+1159C;SIDDHAM LETTER NNA;Lo;0;L;;;;;N;;;;;
+1159D;SIDDHAM LETTER TA;Lo;0;L;;;;;N;;;;;
+1159E;SIDDHAM LETTER THA;Lo;0;L;;;;;N;;;;;
+1159F;SIDDHAM LETTER DA;Lo;0;L;;;;;N;;;;;
+115A0;SIDDHAM LETTER DHA;Lo;0;L;;;;;N;;;;;
+115A1;SIDDHAM LETTER NA;Lo;0;L;;;;;N;;;;;
+115A2;SIDDHAM LETTER PA;Lo;0;L;;;;;N;;;;;
+115A3;SIDDHAM LETTER PHA;Lo;0;L;;;;;N;;;;;
+115A4;SIDDHAM LETTER BA;Lo;0;L;;;;;N;;;;;
+115A5;SIDDHAM LETTER BHA;Lo;0;L;;;;;N;;;;;
+115A6;SIDDHAM LETTER MA;Lo;0;L;;;;;N;;;;;
+115A7;SIDDHAM LETTER YA;Lo;0;L;;;;;N;;;;;
+115A8;SIDDHAM LETTER RA;Lo;0;L;;;;;N;;;;;
+115A9;SIDDHAM LETTER LA;Lo;0;L;;;;;N;;;;;
+115AA;SIDDHAM LETTER VA;Lo;0;L;;;;;N;;;;;
+115AB;SIDDHAM LETTER SHA;Lo;0;L;;;;;N;;;;;
+115AC;SIDDHAM LETTER SSA;Lo;0;L;;;;;N;;;;;
+115AD;SIDDHAM LETTER SA;Lo;0;L;;;;;N;;;;;
+115AE;SIDDHAM LETTER HA;Lo;0;L;;;;;N;;;;;
+115AF;SIDDHAM VOWEL SIGN AA;Mc;0;L;;;;;N;;;;;
+115B0;SIDDHAM VOWEL SIGN I;Mc;0;L;;;;;N;;;;;
+115B1;SIDDHAM VOWEL SIGN II;Mc;0;L;;;;;N;;;;;
+115B2;SIDDHAM VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;;
+115B3;SIDDHAM VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;;
+115B4;SIDDHAM VOWEL SIGN VOCALIC R;Mn;0;NSM;;;;;N;;;;;
+115B5;SIDDHAM VOWEL SIGN VOCALIC RR;Mn;0;NSM;;;;;N;;;;;
+115B8;SIDDHAM VOWEL SIGN E;Mc;0;L;;;;;N;;;;;
+115B9;SIDDHAM VOWEL SIGN AI;Mc;0;L;;;;;N;;;;;
+115BA;SIDDHAM VOWEL SIGN O;Mc;0;L;115B8 115AF;;;;N;;;;;
+115BB;SIDDHAM VOWEL SIGN AU;Mc;0;L;115B9 115AF;;;;N;;;;;
+115BC;SIDDHAM SIGN CANDRABINDU;Mn;0;NSM;;;;;N;;;;;
+115BD;SIDDHAM SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;;
+115BE;SIDDHAM SIGN VISARGA;Mc;0;L;;;;;N;;;;;
+115BF;SIDDHAM SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;;
+115C0;SIDDHAM SIGN NUKTA;Mn;7;NSM;;;;;N;;;;;
+115C1;SIDDHAM SIGN SIDDHAM;Po;0;L;;;;;N;;;;;
+115C2;SIDDHAM DANDA;Po;0;L;;;;;N;;;;;
+115C3;SIDDHAM DOUBLE DANDA;Po;0;L;;;;;N;;;;;
+115C4;SIDDHAM SEPARATOR DOT;Po;0;L;;;;;N;;;;;
+115C5;SIDDHAM SEPARATOR BAR;Po;0;L;;;;;N;;;;;
+115C6;SIDDHAM REPETITION MARK-1;Po;0;L;;;;;N;;;;;
+115C7;SIDDHAM REPETITION MARK-2;Po;0;L;;;;;N;;;;;
+115C8;SIDDHAM REPETITION MARK-3;Po;0;L;;;;;N;;;;;
+115C9;SIDDHAM END OF TEXT MARK;Po;0;L;;;;;N;;;;;
+11600;MODI LETTER A;Lo;0;L;;;;;N;;;;;
+11601;MODI LETTER AA;Lo;0;L;;;;;N;;;;;
+11602;MODI LETTER I;Lo;0;L;;;;;N;;;;;
+11603;MODI LETTER II;Lo;0;L;;;;;N;;;;;
+11604;MODI LETTER U;Lo;0;L;;;;;N;;;;;
+11605;MODI LETTER UU;Lo;0;L;;;;;N;;;;;
+11606;MODI LETTER VOCALIC R;Lo;0;L;;;;;N;;;;;
+11607;MODI LETTER VOCALIC RR;Lo;0;L;;;;;N;;;;;
+11608;MODI LETTER VOCALIC L;Lo;0;L;;;;;N;;;;;
+11609;MODI LETTER VOCALIC LL;Lo;0;L;;;;;N;;;;;
+1160A;MODI LETTER E;Lo;0;L;;;;;N;;;;;
+1160B;MODI LETTER AI;Lo;0;L;;;;;N;;;;;
+1160C;MODI LETTER O;Lo;0;L;;;;;N;;;;;
+1160D;MODI LETTER AU;Lo;0;L;;;;;N;;;;;
+1160E;MODI LETTER KA;Lo;0;L;;;;;N;;;;;
+1160F;MODI LETTER KHA;Lo;0;L;;;;;N;;;;;
+11610;MODI LETTER GA;Lo;0;L;;;;;N;;;;;
+11611;MODI LETTER GHA;Lo;0;L;;;;;N;;;;;
+11612;MODI LETTER NGA;Lo;0;L;;;;;N;;;;;
+11613;MODI LETTER CA;Lo;0;L;;;;;N;;;;;
+11614;MODI LETTER CHA;Lo;0;L;;;;;N;;;;;
+11615;MODI LETTER JA;Lo;0;L;;;;;N;;;;;
+11616;MODI LETTER JHA;Lo;0;L;;;;;N;;;;;
+11617;MODI LETTER NYA;Lo;0;L;;;;;N;;;;;
+11618;MODI LETTER TTA;Lo;0;L;;;;;N;;;;;
+11619;MODI LETTER TTHA;Lo;0;L;;;;;N;;;;;
+1161A;MODI LETTER DDA;Lo;0;L;;;;;N;;;;;
+1161B;MODI LETTER DDHA;Lo;0;L;;;;;N;;;;;
+1161C;MODI LETTER NNA;Lo;0;L;;;;;N;;;;;
+1161D;MODI LETTER TA;Lo;0;L;;;;;N;;;;;
+1161E;MODI LETTER THA;Lo;0;L;;;;;N;;;;;
+1161F;MODI LETTER DA;Lo;0;L;;;;;N;;;;;
+11620;MODI LETTER DHA;Lo;0;L;;;;;N;;;;;
+11621;MODI LETTER NA;Lo;0;L;;;;;N;;;;;
+11622;MODI LETTER PA;Lo;0;L;;;;;N;;;;;
+11623;MODI LETTER PHA;Lo;0;L;;;;;N;;;;;
+11624;MODI LETTER BA;Lo;0;L;;;;;N;;;;;
+11625;MODI LETTER BHA;Lo;0;L;;;;;N;;;;;
+11626;MODI LETTER MA;Lo;0;L;;;;;N;;;;;
+11627;MODI LETTER YA;Lo;0;L;;;;;N;;;;;
+11628;MODI LETTER RA;Lo;0;L;;;;;N;;;;;
+11629;MODI LETTER LA;Lo;0;L;;;;;N;;;;;
+1162A;MODI LETTER VA;Lo;0;L;;;;;N;;;;;
+1162B;MODI LETTER SHA;Lo;0;L;;;;;N;;;;;
+1162C;MODI LETTER SSA;Lo;0;L;;;;;N;;;;;
+1162D;MODI LETTER SA;Lo;0;L;;;;;N;;;;;
+1162E;MODI LETTER HA;Lo;0;L;;;;;N;;;;;
+1162F;MODI LETTER LLA;Lo;0;L;;;;;N;;;;;
+11630;MODI VOWEL SIGN AA;Mc;0;L;;;;;N;;;;;
+11631;MODI VOWEL SIGN I;Mc;0;L;;;;;N;;;;;
+11632;MODI VOWEL SIGN II;Mc;0;L;;;;;N;;;;;
+11633;MODI VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;;
+11634;MODI VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;;
+11635;MODI VOWEL SIGN VOCALIC R;Mn;0;NSM;;;;;N;;;;;
+11636;MODI VOWEL SIGN VOCALIC RR;Mn;0;NSM;;;;;N;;;;;
+11637;MODI VOWEL SIGN VOCALIC L;Mn;0;NSM;;;;;N;;;;;
+11638;MODI VOWEL SIGN VOCALIC LL;Mn;0;NSM;;;;;N;;;;;
+11639;MODI VOWEL SIGN E;Mn;0;NSM;;;;;N;;;;;
+1163A;MODI VOWEL SIGN AI;Mn;0;NSM;;;;;N;;;;;
+1163B;MODI VOWEL SIGN O;Mc;0;L;;;;;N;;;;;
+1163C;MODI VOWEL SIGN AU;Mc;0;L;;;;;N;;;;;
+1163D;MODI SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;;
+1163E;MODI SIGN VISARGA;Mc;0;L;;;;;N;;;;;
+1163F;MODI SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;;
+11640;MODI SIGN ARDHACANDRA;Mn;0;NSM;;;;;N;;;;;
+11641;MODI DANDA;Po;0;L;;;;;N;;;;;
+11642;MODI DOUBLE DANDA;Po;0;L;;;;;N;;;;;
+11643;MODI ABBREVIATION SIGN;Po;0;L;;;;;N;;;;;
+11644;MODI SIGN HUVA;Lo;0;L;;;;;N;;;;;
+11650;MODI DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;;
+11651;MODI DIGIT ONE;Nd;0;L;;1;1;1;N;;;;;
+11652;MODI DIGIT TWO;Nd;0;L;;2;2;2;N;;;;;
+11653;MODI DIGIT THREE;Nd;0;L;;3;3;3;N;;;;;
+11654;MODI DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;;
+11655;MODI DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;;
+11656;MODI DIGIT SIX;Nd;0;L;;6;6;6;N;;;;;
+11657;MODI DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;;
+11658;MODI DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;;
+11659;MODI DIGIT NINE;Nd;0;L;;9;9;9;N;;;;;
 11680;TAKRI LETTER A;Lo;0;L;;;;;N;;;;;
 11681;TAKRI LETTER AA;Lo;0;L;;;;;N;;;;;
 11682;TAKRI LETTER I;Lo;0;L;;;;;N;;;;;
@@ -17775,6 +19308,147 @@
 116C7;TAKRI DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;;
 116C8;TAKRI DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;;
 116C9;TAKRI DIGIT NINE;Nd;0;L;;9;9;9;N;;;;;
+118A0;WARANG CITI CAPITAL LETTER NGAA;Lu;0;L;;;;;N;;;;118C0;
+118A1;WARANG CITI CAPITAL LETTER A;Lu;0;L;;;;;N;;;;118C1;
+118A2;WARANG CITI CAPITAL LETTER WI;Lu;0;L;;;;;N;;;;118C2;
+118A3;WARANG CITI CAPITAL LETTER YU;Lu;0;L;;;;;N;;;;118C3;
+118A4;WARANG CITI CAPITAL LETTER YA;Lu;0;L;;;;;N;;;;118C4;
+118A5;WARANG CITI CAPITAL LETTER YO;Lu;0;L;;;;;N;;;;118C5;
+118A6;WARANG CITI CAPITAL LETTER II;Lu;0;L;;;;;N;;;;118C6;
+118A7;WARANG CITI CAPITAL LETTER UU;Lu;0;L;;;;;N;;;;118C7;
+118A8;WARANG CITI CAPITAL LETTER E;Lu;0;L;;;;;N;;;;118C8;
+118A9;WARANG CITI CAPITAL LETTER O;Lu;0;L;;;;;N;;;;118C9;
+118AA;WARANG CITI CAPITAL LETTER ANG;Lu;0;L;;;;;N;;;;118CA;
+118AB;WARANG CITI CAPITAL LETTER GA;Lu;0;L;;;;;N;;;;118CB;
+118AC;WARANG CITI CAPITAL LETTER KO;Lu;0;L;;;;;N;;;;118CC;
+118AD;WARANG CITI CAPITAL LETTER ENY;Lu;0;L;;;;;N;;;;118CD;
+118AE;WARANG CITI CAPITAL LETTER YUJ;Lu;0;L;;;;;N;;;;118CE;
+118AF;WARANG CITI CAPITAL LETTER UC;Lu;0;L;;;;;N;;;;118CF;
+118B0;WARANG CITI CAPITAL LETTER ENN;Lu;0;L;;;;;N;;;;118D0;
+118B1;WARANG CITI CAPITAL LETTER ODD;Lu;0;L;;;;;N;;;;118D1;
+118B2;WARANG CITI CAPITAL LETTER TTE;Lu;0;L;;;;;N;;;;118D2;
+118B3;WARANG CITI CAPITAL LETTER NUNG;Lu;0;L;;;;;N;;;;118D3;
+118B4;WARANG CITI CAPITAL LETTER DA;Lu;0;L;;;;;N;;;;118D4;
+118B5;WARANG CITI CAPITAL LETTER AT;Lu;0;L;;;;;N;;;;118D5;
+118B6;WARANG CITI CAPITAL LETTER AM;Lu;0;L;;;;;N;;;;118D6;
+118B7;WARANG CITI CAPITAL LETTER BU;Lu;0;L;;;;;N;;;;118D7;
+118B8;WARANG CITI CAPITAL LETTER PU;Lu;0;L;;;;;N;;;;118D8;
+118B9;WARANG CITI CAPITAL LETTER HIYO;Lu;0;L;;;;;N;;;;118D9;
+118BA;WARANG CITI CAPITAL LETTER HOLO;Lu;0;L;;;;;N;;;;118DA;
+118BB;WARANG CITI CAPITAL LETTER HORR;Lu;0;L;;;;;N;;;;118DB;
+118BC;WARANG CITI CAPITAL LETTER HAR;Lu;0;L;;;;;N;;;;118DC;
+118BD;WARANG CITI CAPITAL LETTER SSUU;Lu;0;L;;;;;N;;;;118DD;
+118BE;WARANG CITI CAPITAL LETTER SII;Lu;0;L;;;;;N;;;;118DE;
+118BF;WARANG CITI CAPITAL LETTER VIYO;Lu;0;L;;;;;N;;;;118DF;
+118C0;WARANG CITI SMALL LETTER NGAA;Ll;0;L;;;;;N;;;118A0;;118A0
+118C1;WARANG CITI SMALL LETTER A;Ll;0;L;;;;;N;;;118A1;;118A1
+118C2;WARANG CITI SMALL LETTER WI;Ll;0;L;;;;;N;;;118A2;;118A2
+118C3;WARANG CITI SMALL LETTER YU;Ll;0;L;;;;;N;;;118A3;;118A3
+118C4;WARANG CITI SMALL LETTER YA;Ll;0;L;;;;;N;;;118A4;;118A4
+118C5;WARANG CITI SMALL LETTER YO;Ll;0;L;;;;;N;;;118A5;;118A5
+118C6;WARANG CITI SMALL LETTER II;Ll;0;L;;;;;N;;;118A6;;118A6
+118C7;WARANG CITI SMALL LETTER UU;Ll;0;L;;;;;N;;;118A7;;118A7
+118C8;WARANG CITI SMALL LETTER E;Ll;0;L;;;;;N;;;118A8;;118A8
+118C9;WARANG CITI SMALL LETTER O;Ll;0;L;;;;;N;;;118A9;;118A9
+118CA;WARANG CITI SMALL LETTER ANG;Ll;0;L;;;;;N;;;118AA;;118AA
+118CB;WARANG CITI SMALL LETTER GA;Ll;0;L;;;;;N;;;118AB;;118AB
+118CC;WARANG CITI SMALL LETTER KO;Ll;0;L;;;;;N;;;118AC;;118AC
+118CD;WARANG CITI SMALL LETTER ENY;Ll;0;L;;;;;N;;;118AD;;118AD
+118CE;WARANG CITI SMALL LETTER YUJ;Ll;0;L;;;;;N;;;118AE;;118AE
+118CF;WARANG CITI SMALL LETTER UC;Ll;0;L;;;;;N;;;118AF;;118AF
+118D0;WARANG CITI SMALL LETTER ENN;Ll;0;L;;;;;N;;;118B0;;118B0
+118D1;WARANG CITI SMALL LETTER ODD;Ll;0;L;;;;;N;;;118B1;;118B1
+118D2;WARANG CITI SMALL LETTER TTE;Ll;0;L;;;;;N;;;118B2;;118B2
+118D3;WARANG CITI SMALL LETTER NUNG;Ll;0;L;;;;;N;;;118B3;;118B3
+118D4;WARANG CITI SMALL LETTER DA;Ll;0;L;;;;;N;;;118B4;;118B4
+118D5;WARANG CITI SMALL LETTER AT;Ll;0;L;;;;;N;;;118B5;;118B5
+118D6;WARANG CITI SMALL LETTER AM;Ll;0;L;;;;;N;;;118B6;;118B6
+118D7;WARANG CITI SMALL LETTER BU;Ll;0;L;;;;;N;;;118B7;;118B7
+118D8;WARANG CITI SMALL LETTER PU;Ll;0;L;;;;;N;;;118B8;;118B8
+118D9;WARANG CITI SMALL LETTER HIYO;Ll;0;L;;;;;N;;;118B9;;118B9
+118DA;WARANG CITI SMALL LETTER HOLO;Ll;0;L;;;;;N;;;118BA;;118BA
+118DB;WARANG CITI SMALL LETTER HORR;Ll;0;L;;;;;N;;;118BB;;118BB
+118DC;WARANG CITI SMALL LETTER HAR;Ll;0;L;;;;;N;;;118BC;;118BC
+118DD;WARANG CITI SMALL LETTER SSUU;Ll;0;L;;;;;N;;;118BD;;118BD
+118DE;WARANG CITI SMALL LETTER SII;Ll;0;L;;;;;N;;;118BE;;118BE
+118DF;WARANG CITI SMALL LETTER VIYO;Ll;0;L;;;;;N;;;118BF;;118BF
+118E0;WARANG CITI DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;;
+118E1;WARANG CITI DIGIT ONE;Nd;0;L;;1;1;1;N;;;;;
+118E2;WARANG CITI DIGIT TWO;Nd;0;L;;2;2;2;N;;;;;
+118E3;WARANG CITI DIGIT THREE;Nd;0;L;;3;3;3;N;;;;;
+118E4;WARANG CITI DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;;
+118E5;WARANG CITI DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;;
+118E6;WARANG CITI DIGIT SIX;Nd;0;L;;6;6;6;N;;;;;
+118E7;WARANG CITI DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;;
+118E8;WARANG CITI DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;;
+118E9;WARANG CITI DIGIT NINE;Nd;0;L;;9;9;9;N;;;;;
+118EA;WARANG CITI NUMBER TEN;No;0;L;;;;10;N;;;;;
+118EB;WARANG CITI NUMBER TWENTY;No;0;L;;;;20;N;;;;;
+118EC;WARANG CITI NUMBER THIRTY;No;0;L;;;;30;N;;;;;
+118ED;WARANG CITI NUMBER FORTY;No;0;L;;;;40;N;;;;;
+118EE;WARANG CITI NUMBER FIFTY;No;0;L;;;;50;N;;;;;
+118EF;WARANG CITI NUMBER SIXTY;No;0;L;;;;60;N;;;;;
+118F0;WARANG CITI NUMBER SEVENTY;No;0;L;;;;70;N;;;;;
+118F1;WARANG CITI NUMBER EIGHTY;No;0;L;;;;80;N;;;;;
+118F2;WARANG CITI NUMBER NINETY;No;0;L;;;;90;N;;;;;
+118FF;WARANG CITI OM;Lo;0;L;;;;;N;;;;;
+11AC0;PAU CIN HAU LETTER PA;Lo;0;L;;;;;N;;;;;
+11AC1;PAU CIN HAU LETTER KA;Lo;0;L;;;;;N;;;;;
+11AC2;PAU CIN HAU LETTER LA;Lo;0;L;;;;;N;;;;;
+11AC3;PAU CIN HAU LETTER MA;Lo;0;L;;;;;N;;;;;
+11AC4;PAU CIN HAU LETTER DA;Lo;0;L;;;;;N;;;;;
+11AC5;PAU CIN HAU LETTER ZA;Lo;0;L;;;;;N;;;;;
+11AC6;PAU CIN HAU LETTER VA;Lo;0;L;;;;;N;;;;;
+11AC7;PAU CIN HAU LETTER NGA;Lo;0;L;;;;;N;;;;;
+11AC8;PAU CIN HAU LETTER HA;Lo;0;L;;;;;N;;;;;
+11AC9;PAU CIN HAU LETTER GA;Lo;0;L;;;;;N;;;;;
+11ACA;PAU CIN HAU LETTER KHA;Lo;0;L;;;;;N;;;;;
+11ACB;PAU CIN HAU LETTER SA;Lo;0;L;;;;;N;;;;;
+11ACC;PAU CIN HAU LETTER BA;Lo;0;L;;;;;N;;;;;
+11ACD;PAU CIN HAU LETTER CA;Lo;0;L;;;;;N;;;;;
+11ACE;PAU CIN HAU LETTER TA;Lo;0;L;;;;;N;;;;;
+11ACF;PAU CIN HAU LETTER THA;Lo;0;L;;;;;N;;;;;
+11AD0;PAU CIN HAU LETTER NA;Lo;0;L;;;;;N;;;;;
+11AD1;PAU CIN HAU LETTER PHA;Lo;0;L;;;;;N;;;;;
+11AD2;PAU CIN HAU LETTER RA;Lo;0;L;;;;;N;;;;;
+11AD3;PAU CIN HAU LETTER FA;Lo;0;L;;;;;N;;;;;
+11AD4;PAU CIN HAU LETTER CHA;Lo;0;L;;;;;N;;;;;
+11AD5;PAU CIN HAU LETTER A;Lo;0;L;;;;;N;;;;;
+11AD6;PAU CIN HAU LETTER E;Lo;0;L;;;;;N;;;;;
+11AD7;PAU CIN HAU LETTER I;Lo;0;L;;;;;N;;;;;
+11AD8;PAU CIN HAU LETTER O;Lo;0;L;;;;;N;;;;;
+11AD9;PAU CIN HAU LETTER U;Lo;0;L;;;;;N;;;;;
+11ADA;PAU CIN HAU LETTER UA;Lo;0;L;;;;;N;;;;;
+11ADB;PAU CIN HAU LETTER IA;Lo;0;L;;;;;N;;;;;
+11ADC;PAU CIN HAU LETTER FINAL P;Lo;0;L;;;;;N;;;;;
+11ADD;PAU CIN HAU LETTER FINAL K;Lo;0;L;;;;;N;;;;;
+11ADE;PAU CIN HAU LETTER FINAL T;Lo;0;L;;;;;N;;;;;
+11ADF;PAU CIN HAU LETTER FINAL M;Lo;0;L;;;;;N;;;;;
+11AE0;PAU CIN HAU LETTER FINAL N;Lo;0;L;;;;;N;;;;;
+11AE1;PAU CIN HAU LETTER FINAL L;Lo;0;L;;;;;N;;;;;
+11AE2;PAU CIN HAU LETTER FINAL W;Lo;0;L;;;;;N;;;;;
+11AE3;PAU CIN HAU LETTER FINAL NG;Lo;0;L;;;;;N;;;;;
+11AE4;PAU CIN HAU LETTER FINAL Y;Lo;0;L;;;;;N;;;;;
+11AE5;PAU CIN HAU RISING TONE LONG;Lo;0;L;;;;;N;;;;;
+11AE6;PAU CIN HAU RISING TONE;Lo;0;L;;;;;N;;;;;
+11AE7;PAU CIN HAU SANDHI GLOTTAL STOP;Lo;0;L;;;;;N;;;;;
+11AE8;PAU CIN HAU RISING TONE LONG FINAL;Lo;0;L;;;;;N;;;;;
+11AE9;PAU CIN HAU RISING TONE FINAL;Lo;0;L;;;;;N;;;;;
+11AEA;PAU CIN HAU SANDHI GLOTTAL STOP FINAL;Lo;0;L;;;;;N;;;;;
+11AEB;PAU CIN HAU SANDHI TONE LONG;Lo;0;L;;;;;N;;;;;
+11AEC;PAU CIN HAU SANDHI TONE;Lo;0;L;;;;;N;;;;;
+11AED;PAU CIN HAU SANDHI TONE LONG FINAL;Lo;0;L;;;;;N;;;;;
+11AEE;PAU CIN HAU SANDHI TONE FINAL;Lo;0;L;;;;;N;;;;;
+11AEF;PAU CIN HAU MID-LEVEL TONE;Lo;0;L;;;;;N;;;;;
+11AF0;PAU CIN HAU GLOTTAL STOP VARIANT;Lo;0;L;;;;;N;;;;;
+11AF1;PAU CIN HAU MID-LEVEL TONE LONG FINAL;Lo;0;L;;;;;N;;;;;
+11AF2;PAU CIN HAU MID-LEVEL TONE FINAL;Lo;0;L;;;;;N;;;;;
+11AF3;PAU CIN HAU LOW-FALLING TONE LONG;Lo;0;L;;;;;N;;;;;
+11AF4;PAU CIN HAU LOW-FALLING TONE;Lo;0;L;;;;;N;;;;;
+11AF5;PAU CIN HAU GLOTTAL STOP;Lo;0;L;;;;;N;;;;;
+11AF6;PAU CIN HAU LOW-FALLING TONE LONG FINAL;Lo;0;L;;;;;N;;;;;
+11AF7;PAU CIN HAU LOW-FALLING TONE FINAL;Lo;0;L;;;;;N;;;;;
+11AF8;PAU CIN HAU GLOTTAL STOP FINAL;Lo;0;L;;;;;N;;;;;
 12000;CUNEIFORM SIGN A;Lo;0;L;;;;;N;;;;;
 12001;CUNEIFORM SIGN A TIMES A;Lo;0;L;;;;;N;;;;;
 12002;CUNEIFORM SIGN A TIMES BAD;Lo;0;L;;;;;N;;;;;
@@ -18654,6 +20328,48 @@
 1236C;CUNEIFORM SIGN ZU5 TIMES A;Lo;0;L;;;;;N;;;;;
 1236D;CUNEIFORM SIGN ZUBUR;Lo;0;L;;;;;N;;;;;
 1236E;CUNEIFORM SIGN ZUM;Lo;0;L;;;;;N;;;;;
+1236F;CUNEIFORM SIGN KAP ELAMITE;Lo;0;L;;;;;N;;;;;
+12370;CUNEIFORM SIGN AB TIMES NUN;Lo;0;L;;;;;N;;;;;
+12371;CUNEIFORM SIGN AB2 TIMES A;Lo;0;L;;;;;N;;;;;
+12372;CUNEIFORM SIGN AMAR TIMES KUG;Lo;0;L;;;;;N;;;;;
+12373;CUNEIFORM SIGN DAG KISIM5 TIMES U2 PLUS MASH;Lo;0;L;;;;;N;;;;;
+12374;CUNEIFORM SIGN DAG3;Lo;0;L;;;;;N;;;;;
+12375;CUNEIFORM SIGN DISH PLUS SHU;Lo;0;L;;;;;N;;;;;
+12376;CUNEIFORM SIGN DUB TIMES SHE;Lo;0;L;;;;;N;;;;;
+12377;CUNEIFORM SIGN EZEN TIMES GUD;Lo;0;L;;;;;N;;;;;
+12378;CUNEIFORM SIGN EZEN TIMES SHE;Lo;0;L;;;;;N;;;;;
+12379;CUNEIFORM SIGN GA2 TIMES AN PLUS KAK PLUS A;Lo;0;L;;;;;N;;;;;
+1237A;CUNEIFORM SIGN GA2 TIMES ASH2;Lo;0;L;;;;;N;;;;;
+1237B;CUNEIFORM SIGN GE22;Lo;0;L;;;;;N;;;;;
+1237C;CUNEIFORM SIGN GIG;Lo;0;L;;;;;N;;;;;
+1237D;CUNEIFORM SIGN HUSH;Lo;0;L;;;;;N;;;;;
+1237E;CUNEIFORM SIGN KA TIMES ANSHE;Lo;0;L;;;;;N;;;;;
+1237F;CUNEIFORM SIGN KA TIMES ASH3;Lo;0;L;;;;;N;;;;;
+12380;CUNEIFORM SIGN KA TIMES GISH;Lo;0;L;;;;;N;;;;;
+12381;CUNEIFORM SIGN KA TIMES GUD;Lo;0;L;;;;;N;;;;;
+12382;CUNEIFORM SIGN KA TIMES HI TIMES ASH2;Lo;0;L;;;;;N;;;;;
+12383;CUNEIFORM SIGN KA TIMES LUM;Lo;0;L;;;;;N;;;;;
+12384;CUNEIFORM SIGN KA TIMES PA;Lo;0;L;;;;;N;;;;;
+12385;CUNEIFORM SIGN KA TIMES SHUL;Lo;0;L;;;;;N;;;;;
+12386;CUNEIFORM SIGN KA TIMES TU;Lo;0;L;;;;;N;;;;;
+12387;CUNEIFORM SIGN KA TIMES UR2;Lo;0;L;;;;;N;;;;;
+12388;CUNEIFORM SIGN LAGAB TIMES GI;Lo;0;L;;;;;N;;;;;
+12389;CUNEIFORM SIGN LU2 SHESHIG TIMES BAD;Lo;0;L;;;;;N;;;;;
+1238A;CUNEIFORM SIGN LU2 TIMES ESH2 PLUS LAL;Lo;0;L;;;;;N;;;;;
+1238B;CUNEIFORM SIGN LU2 TIMES SHU;Lo;0;L;;;;;N;;;;;
+1238C;CUNEIFORM SIGN MESH;Lo;0;L;;;;;N;;;;;
+1238D;CUNEIFORM SIGN MUSH3 TIMES ZA;Lo;0;L;;;;;N;;;;;
+1238E;CUNEIFORM SIGN NA4;Lo;0;L;;;;;N;;;;;
+1238F;CUNEIFORM SIGN NIN;Lo;0;L;;;;;N;;;;;
+12390;CUNEIFORM SIGN NIN9;Lo;0;L;;;;;N;;;;;
+12391;CUNEIFORM SIGN NINDA2 TIMES BAL;Lo;0;L;;;;;N;;;;;
+12392;CUNEIFORM SIGN NINDA2 TIMES GI;Lo;0;L;;;;;N;;;;;
+12393;CUNEIFORM SIGN NU11 ROTATED NINETY DEGREES;Lo;0;L;;;;;N;;;;;
+12394;CUNEIFORM SIGN PESH2 ASTERISK;Lo;0;L;;;;;N;;;;;
+12395;CUNEIFORM SIGN PIR2;Lo;0;L;;;;;N;;;;;
+12396;CUNEIFORM SIGN SAG TIMES IGI GUNU;Lo;0;L;;;;;N;;;;;
+12397;CUNEIFORM SIGN TI2;Lo;0;L;;;;;N;;;;;
+12398;CUNEIFORM SIGN UM TIMES ME;Lo;0;L;;;;;N;;;;;
 12400;CUNEIFORM NUMERIC SIGN TWO ASH;Nl;0;L;;;;2;N;;;;;
 12401;CUNEIFORM NUMERIC SIGN THREE ASH;Nl;0;L;;;;3;N;;;;;
 12402;CUNEIFORM NUMERIC SIGN FOUR ASH;Nl;0;L;;;;4;N;;;;;
@@ -18740,8 +20456,8 @@
 12453;CUNEIFORM NUMERIC SIGN FOUR BAN2 VARIANT FORM;Nl;0;L;;;;4;N;;;;;
 12454;CUNEIFORM NUMERIC SIGN FIVE BAN2;Nl;0;L;;;;5;N;;;;;
 12455;CUNEIFORM NUMERIC SIGN FIVE BAN2 VARIANT FORM;Nl;0;L;;;;5;N;;;;;
-12456;CUNEIFORM NUMERIC SIGN NIGIDAMIN;Nl;0;L;;;;-1;N;;;;;
-12457;CUNEIFORM NUMERIC SIGN NIGIDAESH;Nl;0;L;;;;-1;N;;;;;
+12456;CUNEIFORM NUMERIC SIGN NIGIDAMIN;Nl;0;L;;;;2;N;;;;;
+12457;CUNEIFORM NUMERIC SIGN NIGIDAESH;Nl;0;L;;;;3;N;;;;;
 12458;CUNEIFORM NUMERIC SIGN ONE ESHE3;Nl;0;L;;;;1;N;;;;;
 12459;CUNEIFORM NUMERIC SIGN TWO ESHE3;Nl;0;L;;;;2;N;;;;;
 1245A;CUNEIFORM NUMERIC SIGN ONE THIRD DISH;Nl;0;L;;;;1/3;N;;;;;
@@ -18753,10 +20469,23 @@
 12460;CUNEIFORM NUMERIC SIGN ONE QUARTER ASH;Nl;0;L;;;;1/4;N;;;;;
 12461;CUNEIFORM NUMERIC SIGN OLD ASSYRIAN ONE SIXTH;Nl;0;L;;;;1/6;N;;;;;
 12462;CUNEIFORM NUMERIC SIGN OLD ASSYRIAN ONE QUARTER;Nl;0;L;;;;1/4;N;;;;;
+12463;CUNEIFORM NUMERIC SIGN ONE QUARTER GUR;Nl;0;L;;;;1/4;N;;;;;
+12464;CUNEIFORM NUMERIC SIGN ONE HALF GUR;Nl;0;L;;;;1/2;N;;;;;
+12465;CUNEIFORM NUMERIC SIGN ELAMITE ONE THIRD;Nl;0;L;;;;1/3;N;;;;;
+12466;CUNEIFORM NUMERIC SIGN ELAMITE TWO THIRDS;Nl;0;L;;;;2/3;N;;;;;
+12467;CUNEIFORM NUMERIC SIGN ELAMITE FORTY;Nl;0;L;;;;40;N;;;;;
+12468;CUNEIFORM NUMERIC SIGN ELAMITE FIFTY;Nl;0;L;;;;50;N;;;;;
+12469;CUNEIFORM NUMERIC SIGN FOUR U VARIANT FORM;Nl;0;L;;;;4;N;;;;;
+1246A;CUNEIFORM NUMERIC SIGN FIVE U VARIANT FORM;Nl;0;L;;;;5;N;;;;;
+1246B;CUNEIFORM NUMERIC SIGN SIX U VARIANT FORM;Nl;0;L;;;;6;N;;;;;
+1246C;CUNEIFORM NUMERIC SIGN SEVEN U VARIANT FORM;Nl;0;L;;;;7;N;;;;;
+1246D;CUNEIFORM NUMERIC SIGN EIGHT U VARIANT FORM;Nl;0;L;;;;8;N;;;;;
+1246E;CUNEIFORM NUMERIC SIGN NINE U VARIANT FORM;Nl;0;L;;;;9;N;;;;;
 12470;CUNEIFORM PUNCTUATION SIGN OLD ASSYRIAN WORD DIVIDER;Po;0;L;;;;;N;;;;;
 12471;CUNEIFORM PUNCTUATION SIGN VERTICAL COLON;Po;0;L;;;;;N;;;;;
 12472;CUNEIFORM PUNCTUATION SIGN DIAGONAL COLON;Po;0;L;;;;;N;;;;;
 12473;CUNEIFORM PUNCTUATION SIGN DIAGONAL TRICOLON;Po;0;L;;;;;N;;;;;
+12474;CUNEIFORM PUNCTUATION SIGN DIAGONAL QUADCOLON;Po;0;L;;;;;N;;;;;
 13000;EGYPTIAN HIEROGLYPH A001;Lo;0;L;;;;;N;;;;;
 13001;EGYPTIAN HIEROGLYPH A002;Lo;0;L;;;;;N;;;;;
 13002;EGYPTIAN HIEROGLYPH A003;Lo;0;L;;;;;N;;;;;
@@ -20397,6 +22126,212 @@
 16A36;BAMUM LETTER PHASE-F KPA;Lo;0;L;;;;;N;;;;;
 16A37;BAMUM LETTER PHASE-F SAMBA;Lo;0;L;;;;;N;;;;;
 16A38;BAMUM LETTER PHASE-F VUEQ;Lo;0;L;;;;;N;;;;;
+16A40;MRO LETTER TA;Lo;0;L;;;;;N;;;;;
+16A41;MRO LETTER NGI;Lo;0;L;;;;;N;;;;;
+16A42;MRO LETTER YO;Lo;0;L;;;;;N;;;;;
+16A43;MRO LETTER MIM;Lo;0;L;;;;;N;;;;;
+16A44;MRO LETTER BA;Lo;0;L;;;;;N;;;;;
+16A45;MRO LETTER DA;Lo;0;L;;;;;N;;;;;
+16A46;MRO LETTER A;Lo;0;L;;;;;N;;;;;
+16A47;MRO LETTER PHI;Lo;0;L;;;;;N;;;;;
+16A48;MRO LETTER KHAI;Lo;0;L;;;;;N;;;;;
+16A49;MRO LETTER HAO;Lo;0;L;;;;;N;;;;;
+16A4A;MRO LETTER DAI;Lo;0;L;;;;;N;;;;;
+16A4B;MRO LETTER CHU;Lo;0;L;;;;;N;;;;;
+16A4C;MRO LETTER KEAAE;Lo;0;L;;;;;N;;;;;
+16A4D;MRO LETTER OL;Lo;0;L;;;;;N;;;;;
+16A4E;MRO LETTER MAEM;Lo;0;L;;;;;N;;;;;
+16A4F;MRO LETTER NIN;Lo;0;L;;;;;N;;;;;
+16A50;MRO LETTER PA;Lo;0;L;;;;;N;;;;;
+16A51;MRO LETTER OO;Lo;0;L;;;;;N;;;;;
+16A52;MRO LETTER O;Lo;0;L;;;;;N;;;;;
+16A53;MRO LETTER RO;Lo;0;L;;;;;N;;;;;
+16A54;MRO LETTER SHI;Lo;0;L;;;;;N;;;;;
+16A55;MRO LETTER THEA;Lo;0;L;;;;;N;;;;;
+16A56;MRO LETTER EA;Lo;0;L;;;;;N;;;;;
+16A57;MRO LETTER WA;Lo;0;L;;;;;N;;;;;
+16A58;MRO LETTER E;Lo;0;L;;;;;N;;;;;
+16A59;MRO LETTER KO;Lo;0;L;;;;;N;;;;;
+16A5A;MRO LETTER LAN;Lo;0;L;;;;;N;;;;;
+16A5B;MRO LETTER LA;Lo;0;L;;;;;N;;;;;
+16A5C;MRO LETTER HAI;Lo;0;L;;;;;N;;;;;
+16A5D;MRO LETTER RI;Lo;0;L;;;;;N;;;;;
+16A5E;MRO LETTER TEK;Lo;0;L;;;;;N;;;;;
+16A60;MRO DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;;
+16A61;MRO DIGIT ONE;Nd;0;L;;1;1;1;N;;;;;
+16A62;MRO DIGIT TWO;Nd;0;L;;2;2;2;N;;;;;
+16A63;MRO DIGIT THREE;Nd;0;L;;3;3;3;N;;;;;
+16A64;MRO DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;;
+16A65;MRO DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;;
+16A66;MRO DIGIT SIX;Nd;0;L;;6;6;6;N;;;;;
+16A67;MRO DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;;
+16A68;MRO DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;;
+16A69;MRO DIGIT NINE;Nd;0;L;;9;9;9;N;;;;;
+16A6E;MRO DANDA;Po;0;L;;;;;N;;;;;
+16A6F;MRO DOUBLE DANDA;Po;0;L;;;;;N;;;;;
+16AD0;BASSA VAH LETTER ENNI;Lo;0;L;;;;;N;;;;;
+16AD1;BASSA VAH LETTER KA;Lo;0;L;;;;;N;;;;;
+16AD2;BASSA VAH LETTER SE;Lo;0;L;;;;;N;;;;;
+16AD3;BASSA VAH LETTER FA;Lo;0;L;;;;;N;;;;;
+16AD4;BASSA VAH LETTER MBE;Lo;0;L;;;;;N;;;;;
+16AD5;BASSA VAH LETTER YIE;Lo;0;L;;;;;N;;;;;
+16AD6;BASSA VAH LETTER GAH;Lo;0;L;;;;;N;;;;;
+16AD7;BASSA VAH LETTER DHII;Lo;0;L;;;;;N;;;;;
+16AD8;BASSA VAH LETTER KPAH;Lo;0;L;;;;;N;;;;;
+16AD9;BASSA VAH LETTER JO;Lo;0;L;;;;;N;;;;;
+16ADA;BASSA VAH LETTER HWAH;Lo;0;L;;;;;N;;;;;
+16ADB;BASSA VAH LETTER WA;Lo;0;L;;;;;N;;;;;
+16ADC;BASSA VAH LETTER ZO;Lo;0;L;;;;;N;;;;;
+16ADD;BASSA VAH LETTER GBU;Lo;0;L;;;;;N;;;;;
+16ADE;BASSA VAH LETTER DO;Lo;0;L;;;;;N;;;;;
+16ADF;BASSA VAH LETTER CE;Lo;0;L;;;;;N;;;;;
+16AE0;BASSA VAH LETTER UWU;Lo;0;L;;;;;N;;;;;
+16AE1;BASSA VAH LETTER TO;Lo;0;L;;;;;N;;;;;
+16AE2;BASSA VAH LETTER BA;Lo;0;L;;;;;N;;;;;
+16AE3;BASSA VAH LETTER VU;Lo;0;L;;;;;N;;;;;
+16AE4;BASSA VAH LETTER YEIN;Lo;0;L;;;;;N;;;;;
+16AE5;BASSA VAH LETTER PA;Lo;0;L;;;;;N;;;;;
+16AE6;BASSA VAH LETTER WADDA;Lo;0;L;;;;;N;;;;;
+16AE7;BASSA VAH LETTER A;Lo;0;L;;;;;N;;;;;
+16AE8;BASSA VAH LETTER O;Lo;0;L;;;;;N;;;;;
+16AE9;BASSA VAH LETTER OO;Lo;0;L;;;;;N;;;;;
+16AEA;BASSA VAH LETTER U;Lo;0;L;;;;;N;;;;;
+16AEB;BASSA VAH LETTER EE;Lo;0;L;;;;;N;;;;;
+16AEC;BASSA VAH LETTER E;Lo;0;L;;;;;N;;;;;
+16AED;BASSA VAH LETTER I;Lo;0;L;;;;;N;;;;;
+16AF0;BASSA VAH COMBINING HIGH TONE;Mn;1;NSM;;;;;N;;;;;
+16AF1;BASSA VAH COMBINING LOW TONE;Mn;1;NSM;;;;;N;;;;;
+16AF2;BASSA VAH COMBINING MID TONE;Mn;1;NSM;;;;;N;;;;;
+16AF3;BASSA VAH COMBINING LOW-MID TONE;Mn;1;NSM;;;;;N;;;;;
+16AF4;BASSA VAH COMBINING HIGH-LOW TONE;Mn;1;NSM;;;;;N;;;;;
+16AF5;BASSA VAH FULL STOP;Po;0;L;;;;;N;;;;;
+16B00;PAHAWH HMONG VOWEL KEEB;Lo;0;L;;;;;N;;;;;
+16B01;PAHAWH HMONG VOWEL KEEV;Lo;0;L;;;;;N;;;;;
+16B02;PAHAWH HMONG VOWEL KIB;Lo;0;L;;;;;N;;;;;
+16B03;PAHAWH HMONG VOWEL KIV;Lo;0;L;;;;;N;;;;;
+16B04;PAHAWH HMONG VOWEL KAUB;Lo;0;L;;;;;N;;;;;
+16B05;PAHAWH HMONG VOWEL KAUV;Lo;0;L;;;;;N;;;;;
+16B06;PAHAWH HMONG VOWEL KUB;Lo;0;L;;;;;N;;;;;
+16B07;PAHAWH HMONG VOWEL KUV;Lo;0;L;;;;;N;;;;;
+16B08;PAHAWH HMONG VOWEL KEB;Lo;0;L;;;;;N;;;;;
+16B09;PAHAWH HMONG VOWEL KEV;Lo;0;L;;;;;N;;;;;
+16B0A;PAHAWH HMONG VOWEL KAIB;Lo;0;L;;;;;N;;;;;
+16B0B;PAHAWH HMONG VOWEL KAIV;Lo;0;L;;;;;N;;;;;
+16B0C;PAHAWH HMONG VOWEL KOOB;Lo;0;L;;;;;N;;;;;
+16B0D;PAHAWH HMONG VOWEL KOOV;Lo;0;L;;;;;N;;;;;
+16B0E;PAHAWH HMONG VOWEL KAWB;Lo;0;L;;;;;N;;;;;
+16B0F;PAHAWH HMONG VOWEL KAWV;Lo;0;L;;;;;N;;;;;
+16B10;PAHAWH HMONG VOWEL KUAB;Lo;0;L;;;;;N;;;;;
+16B11;PAHAWH HMONG VOWEL KUAV;Lo;0;L;;;;;N;;;;;
+16B12;PAHAWH HMONG VOWEL KOB;Lo;0;L;;;;;N;;;;;
+16B13;PAHAWH HMONG VOWEL KOV;Lo;0;L;;;;;N;;;;;
+16B14;PAHAWH HMONG VOWEL KIAB;Lo;0;L;;;;;N;;;;;
+16B15;PAHAWH HMONG VOWEL KIAV;Lo;0;L;;;;;N;;;;;
+16B16;PAHAWH HMONG VOWEL KAB;Lo;0;L;;;;;N;;;;;
+16B17;PAHAWH HMONG VOWEL KAV;Lo;0;L;;;;;N;;;;;
+16B18;PAHAWH HMONG VOWEL KWB;Lo;0;L;;;;;N;;;;;
+16B19;PAHAWH HMONG VOWEL KWV;Lo;0;L;;;;;N;;;;;
+16B1A;PAHAWH HMONG VOWEL KAAB;Lo;0;L;;;;;N;;;;;
+16B1B;PAHAWH HMONG VOWEL KAAV;Lo;0;L;;;;;N;;;;;
+16B1C;PAHAWH HMONG CONSONANT VAU;Lo;0;L;;;;;N;;;;;
+16B1D;PAHAWH HMONG CONSONANT NTSAU;Lo;0;L;;;;;N;;;;;
+16B1E;PAHAWH HMONG CONSONANT LAU;Lo;0;L;;;;;N;;;;;
+16B1F;PAHAWH HMONG CONSONANT HAU;Lo;0;L;;;;;N;;;;;
+16B20;PAHAWH HMONG CONSONANT NLAU;Lo;0;L;;;;;N;;;;;
+16B21;PAHAWH HMONG CONSONANT RAU;Lo;0;L;;;;;N;;;;;
+16B22;PAHAWH HMONG CONSONANT NKAU;Lo;0;L;;;;;N;;;;;
+16B23;PAHAWH HMONG CONSONANT QHAU;Lo;0;L;;;;;N;;;;;
+16B24;PAHAWH HMONG CONSONANT YAU;Lo;0;L;;;;;N;;;;;
+16B25;PAHAWH HMONG CONSONANT HLAU;Lo;0;L;;;;;N;;;;;
+16B26;PAHAWH HMONG CONSONANT MAU;Lo;0;L;;;;;N;;;;;
+16B27;PAHAWH HMONG CONSONANT CHAU;Lo;0;L;;;;;N;;;;;
+16B28;PAHAWH HMONG CONSONANT NCHAU;Lo;0;L;;;;;N;;;;;
+16B29;PAHAWH HMONG CONSONANT HNAU;Lo;0;L;;;;;N;;;;;
+16B2A;PAHAWH HMONG CONSONANT PLHAU;Lo;0;L;;;;;N;;;;;
+16B2B;PAHAWH HMONG CONSONANT NTHAU;Lo;0;L;;;;;N;;;;;
+16B2C;PAHAWH HMONG CONSONANT NAU;Lo;0;L;;;;;N;;;;;
+16B2D;PAHAWH HMONG CONSONANT AU;Lo;0;L;;;;;N;;;;;
+16B2E;PAHAWH HMONG CONSONANT XAU;Lo;0;L;;;;;N;;;;;
+16B2F;PAHAWH HMONG CONSONANT CAU;Lo;0;L;;;;;N;;;;;
+16B30;PAHAWH HMONG MARK CIM TUB;Mn;230;NSM;;;;;N;;;;;
+16B31;PAHAWH HMONG MARK CIM SO;Mn;230;NSM;;;;;N;;;;;
+16B32;PAHAWH HMONG MARK CIM KES;Mn;230;NSM;;;;;N;;;;;
+16B33;PAHAWH HMONG MARK CIM KHAV;Mn;230;NSM;;;;;N;;;;;
+16B34;PAHAWH HMONG MARK CIM SUAM;Mn;230;NSM;;;;;N;;;;;
+16B35;PAHAWH HMONG MARK CIM HOM;Mn;230;NSM;;;;;N;;;;;
+16B36;PAHAWH HMONG MARK CIM TAUM;Mn;230;NSM;;;;;N;;;;;
+16B37;PAHAWH HMONG SIGN VOS THOM;Po;0;L;;;;;N;;;;;
+16B38;PAHAWH HMONG SIGN VOS TSHAB CEEB;Po;0;L;;;;;N;;;;;
+16B39;PAHAWH HMONG SIGN CIM CHEEM;Po;0;L;;;;;N;;;;;
+16B3A;PAHAWH HMONG SIGN VOS THIAB;Po;0;L;;;;;N;;;;;
+16B3B;PAHAWH HMONG SIGN VOS FEEM;Po;0;L;;;;;N;;;;;
+16B3C;PAHAWH HMONG SIGN XYEEM NTXIV;So;0;L;;;;;N;;;;;
+16B3D;PAHAWH HMONG SIGN XYEEM RHO;So;0;L;;;;;N;;;;;
+16B3E;PAHAWH HMONG SIGN XYEEM TOV;So;0;L;;;;;N;;;;;
+16B3F;PAHAWH HMONG SIGN XYEEM FAIB;So;0;L;;;;;N;;;;;
+16B40;PAHAWH HMONG SIGN VOS SEEV;Lm;0;L;;;;;N;;;;;
+16B41;PAHAWH HMONG SIGN MEEJ SUAB;Lm;0;L;;;;;N;;;;;
+16B42;PAHAWH HMONG SIGN VOS NRUA;Lm;0;L;;;;;N;;;;;
+16B43;PAHAWH HMONG SIGN IB YAM;Lm;0;L;;;;;N;;;;;
+16B44;PAHAWH HMONG SIGN XAUS;Po;0;L;;;;;N;;;;;
+16B45;PAHAWH HMONG SIGN CIM TSOV ROG;So;0;L;;;;;N;;;;;
+16B50;PAHAWH HMONG DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;;
+16B51;PAHAWH HMONG DIGIT ONE;Nd;0;L;;1;1;1;N;;;;;
+16B52;PAHAWH HMONG DIGIT TWO;Nd;0;L;;2;2;2;N;;;;;
+16B53;PAHAWH HMONG DIGIT THREE;Nd;0;L;;3;3;3;N;;;;;
+16B54;PAHAWH HMONG DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;;
+16B55;PAHAWH HMONG DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;;
+16B56;PAHAWH HMONG DIGIT SIX;Nd;0;L;;6;6;6;N;;;;;
+16B57;PAHAWH HMONG DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;;
+16B58;PAHAWH HMONG DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;;
+16B59;PAHAWH HMONG DIGIT NINE;Nd;0;L;;9;9;9;N;;;;;
+16B5B;PAHAWH HMONG NUMBER TENS;No;0;L;;;;10;N;;;;;
+16B5C;PAHAWH HMONG NUMBER HUNDREDS;No;0;L;;;;100;N;;;;;
+16B5D;PAHAWH HMONG NUMBER TEN THOUSANDS;No;0;L;;;;10000;N;;;;;
+16B5E;PAHAWH HMONG NUMBER MILLIONS;No;0;L;;;;1000000;N;;;;;
+16B5F;PAHAWH HMONG NUMBER HUNDRED MILLIONS;No;0;L;;;;100000000;N;;;;;
+16B60;PAHAWH HMONG NUMBER TEN BILLIONS;No;0;L;;;;10000000000;N;;;;;
+16B61;PAHAWH HMONG NUMBER TRILLIONS;No;0;L;;;;1000000000000;N;;;;;
+16B63;PAHAWH HMONG SIGN VOS LUB;Lo;0;L;;;;;N;;;;;
+16B64;PAHAWH HMONG SIGN XYOO;Lo;0;L;;;;;N;;;;;
+16B65;PAHAWH HMONG SIGN HLI;Lo;0;L;;;;;N;;;;;
+16B66;PAHAWH HMONG SIGN THIRD-STAGE HLI;Lo;0;L;;;;;N;;;;;
+16B67;PAHAWH HMONG SIGN ZWJ THAJ;Lo;0;L;;;;;N;;;;;
+16B68;PAHAWH HMONG SIGN HNUB;Lo;0;L;;;;;N;;;;;
+16B69;PAHAWH HMONG SIGN NQIG;Lo;0;L;;;;;N;;;;;
+16B6A;PAHAWH HMONG SIGN XIAB;Lo;0;L;;;;;N;;;;;
+16B6B;PAHAWH HMONG SIGN NTUJ;Lo;0;L;;;;;N;;;;;
+16B6C;PAHAWH HMONG SIGN AV;Lo;0;L;;;;;N;;;;;
+16B6D;PAHAWH HMONG SIGN TXHEEJ CEEV;Lo;0;L;;;;;N;;;;;
+16B6E;PAHAWH HMONG SIGN MEEJ TSEEB;Lo;0;L;;;;;N;;;;;
+16B6F;PAHAWH HMONG SIGN TAU;Lo;0;L;;;;;N;;;;;
+16B70;PAHAWH HMONG SIGN LOS;Lo;0;L;;;;;N;;;;;
+16B71;PAHAWH HMONG SIGN MUS;Lo;0;L;;;;;N;;;;;
+16B72;PAHAWH HMONG SIGN CIM HAIS LUS NTOG NTOG;Lo;0;L;;;;;N;;;;;
+16B73;PAHAWH HMONG SIGN CIM CUAM TSHOOJ;Lo;0;L;;;;;N;;;;;
+16B74;PAHAWH HMONG SIGN CIM TXWV;Lo;0;L;;;;;N;;;;;
+16B75;PAHAWH HMONG SIGN CIM TXWV CHWV;Lo;0;L;;;;;N;;;;;
+16B76;PAHAWH HMONG SIGN CIM PUB DAWB;Lo;0;L;;;;;N;;;;;
+16B77;PAHAWH HMONG SIGN CIM NRES TOS;Lo;0;L;;;;;N;;;;;
+16B7D;PAHAWH HMONG CLAN SIGN TSHEEJ;Lo;0;L;;;;;N;;;;;
+16B7E;PAHAWH HMONG CLAN SIGN YEEG;Lo;0;L;;;;;N;;;;;
+16B7F;PAHAWH HMONG CLAN SIGN LIS;Lo;0;L;;;;;N;;;;;
+16B80;PAHAWH HMONG CLAN SIGN LAUJ;Lo;0;L;;;;;N;;;;;
+16B81;PAHAWH HMONG CLAN SIGN XYOOJ;Lo;0;L;;;;;N;;;;;
+16B82;PAHAWH HMONG CLAN SIGN KOO;Lo;0;L;;;;;N;;;;;
+16B83;PAHAWH HMONG CLAN SIGN HAWJ;Lo;0;L;;;;;N;;;;;
+16B84;PAHAWH HMONG CLAN SIGN MUAS;Lo;0;L;;;;;N;;;;;
+16B85;PAHAWH HMONG CLAN SIGN THOJ;Lo;0;L;;;;;N;;;;;
+16B86;PAHAWH HMONG CLAN SIGN TSAB;Lo;0;L;;;;;N;;;;;
+16B87;PAHAWH HMONG CLAN SIGN PHAB;Lo;0;L;;;;;N;;;;;
+16B88;PAHAWH HMONG CLAN SIGN KHAB;Lo;0;L;;;;;N;;;;;
+16B89;PAHAWH HMONG CLAN SIGN HAM;Lo;0;L;;;;;N;;;;;
+16B8A;PAHAWH HMONG CLAN SIGN VAJ;Lo;0;L;;;;;N;;;;;
+16B8B;PAHAWH HMONG CLAN SIGN FAJ;Lo;0;L;;;;;N;;;;;
+16B8C;PAHAWH HMONG CLAN SIGN YAJ;Lo;0;L;;;;;N;;;;;
+16B8D;PAHAWH HMONG CLAN SIGN TSWB;Lo;0;L;;;;;N;;;;;
+16B8E;PAHAWH HMONG CLAN SIGN KWM;Lo;0;L;;;;;N;;;;;
+16B8F;PAHAWH HMONG CLAN SIGN VWJ;Lo;0;L;;;;;N;;;;;
 16F00;MIAO LETTER PA;Lo;0;L;;;;;N;;;;;
 16F01;MIAO LETTER BA;Lo;0;L;;;;;N;;;;;
 16F02;MIAO LETTER YI PA;Lo;0;L;;;;;N;;;;;
@@ -20532,6 +22467,153 @@
 16F9F;MIAO LETTER REFORMED TONE-8;Lm;0;L;;;;;N;;;;;
 1B000;KATAKANA LETTER ARCHAIC E;Lo;0;L;;;;;N;;;;;
 1B001;HIRAGANA LETTER ARCHAIC YE;Lo;0;L;;;;;N;;;;;
+1BC00;DUPLOYAN LETTER H;Lo;0;L;;;;;N;;;;;
+1BC01;DUPLOYAN LETTER X;Lo;0;L;;;;;N;;;;;
+1BC02;DUPLOYAN LETTER P;Lo;0;L;;;;;N;;;;;
+1BC03;DUPLOYAN LETTER T;Lo;0;L;;;;;N;;;;;
+1BC04;DUPLOYAN LETTER F;Lo;0;L;;;;;N;;;;;
+1BC05;DUPLOYAN LETTER K;Lo;0;L;;;;;N;;;;;
+1BC06;DUPLOYAN LETTER L;Lo;0;L;;;;;N;;;;;
+1BC07;DUPLOYAN LETTER B;Lo;0;L;;;;;N;;;;;
+1BC08;DUPLOYAN LETTER D;Lo;0;L;;;;;N;;;;;
+1BC09;DUPLOYAN LETTER V;Lo;0;L;;;;;N;;;;;
+1BC0A;DUPLOYAN LETTER G;Lo;0;L;;;;;N;;;;;
+1BC0B;DUPLOYAN LETTER R;Lo;0;L;;;;;N;;;;;
+1BC0C;DUPLOYAN LETTER P N;Lo;0;L;;;;;N;;;;;
+1BC0D;DUPLOYAN LETTER D S;Lo;0;L;;;;;N;;;;;
+1BC0E;DUPLOYAN LETTER F N;Lo;0;L;;;;;N;;;;;
+1BC0F;DUPLOYAN LETTER K M;Lo;0;L;;;;;N;;;;;
+1BC10;DUPLOYAN LETTER R S;Lo;0;L;;;;;N;;;;;
+1BC11;DUPLOYAN LETTER TH;Lo;0;L;;;;;N;;;;;
+1BC12;DUPLOYAN LETTER SLOAN DH;Lo;0;L;;;;;N;;;;;
+1BC13;DUPLOYAN LETTER DH;Lo;0;L;;;;;N;;;;;
+1BC14;DUPLOYAN LETTER KK;Lo;0;L;;;;;N;;;;;
+1BC15;DUPLOYAN LETTER SLOAN J;Lo;0;L;;;;;N;;;;;
+1BC16;DUPLOYAN LETTER HL;Lo;0;L;;;;;N;;;;;
+1BC17;DUPLOYAN LETTER LH;Lo;0;L;;;;;N;;;;;
+1BC18;DUPLOYAN LETTER RH;Lo;0;L;;;;;N;;;;;
+1BC19;DUPLOYAN LETTER M;Lo;0;L;;;;;N;;;;;
+1BC1A;DUPLOYAN LETTER N;Lo;0;L;;;;;N;;;;;
+1BC1B;DUPLOYAN LETTER J;Lo;0;L;;;;;N;;;;;
+1BC1C;DUPLOYAN LETTER S;Lo;0;L;;;;;N;;;;;
+1BC1D;DUPLOYAN LETTER M N;Lo;0;L;;;;;N;;;;;
+1BC1E;DUPLOYAN LETTER N M;Lo;0;L;;;;;N;;;;;
+1BC1F;DUPLOYAN LETTER J M;Lo;0;L;;;;;N;;;;;
+1BC20;DUPLOYAN LETTER S J;Lo;0;L;;;;;N;;;;;
+1BC21;DUPLOYAN LETTER M WITH DOT;Lo;0;L;;;;;N;;;;;
+1BC22;DUPLOYAN LETTER N WITH DOT;Lo;0;L;;;;;N;;;;;
+1BC23;DUPLOYAN LETTER J WITH DOT;Lo;0;L;;;;;N;;;;;
+1BC24;DUPLOYAN LETTER J WITH DOTS INSIDE AND ABOVE;Lo;0;L;;;;;N;;;;;
+1BC25;DUPLOYAN LETTER S WITH DOT;Lo;0;L;;;;;N;;;;;
+1BC26;DUPLOYAN LETTER S WITH DOT BELOW;Lo;0;L;;;;;N;;;;;
+1BC27;DUPLOYAN LETTER M S;Lo;0;L;;;;;N;;;;;
+1BC28;DUPLOYAN LETTER N S;Lo;0;L;;;;;N;;;;;
+1BC29;DUPLOYAN LETTER J S;Lo;0;L;;;;;N;;;;;
+1BC2A;DUPLOYAN LETTER S S;Lo;0;L;;;;;N;;;;;
+1BC2B;DUPLOYAN LETTER M N S;Lo;0;L;;;;;N;;;;;
+1BC2C;DUPLOYAN LETTER N M S;Lo;0;L;;;;;N;;;;;
+1BC2D;DUPLOYAN LETTER J M S;Lo;0;L;;;;;N;;;;;
+1BC2E;DUPLOYAN LETTER S J S;Lo;0;L;;;;;N;;;;;
+1BC2F;DUPLOYAN LETTER J S WITH DOT;Lo;0;L;;;;;N;;;;;
+1BC30;DUPLOYAN LETTER J N;Lo;0;L;;;;;N;;;;;
+1BC31;DUPLOYAN LETTER J N S;Lo;0;L;;;;;N;;;;;
+1BC32;DUPLOYAN LETTER S T;Lo;0;L;;;;;N;;;;;
+1BC33;DUPLOYAN LETTER S T R;Lo;0;L;;;;;N;;;;;
+1BC34;DUPLOYAN LETTER S P;Lo;0;L;;;;;N;;;;;
+1BC35;DUPLOYAN LETTER S P R;Lo;0;L;;;;;N;;;;;
+1BC36;DUPLOYAN LETTER T S;Lo;0;L;;;;;N;;;;;
+1BC37;DUPLOYAN LETTER T R S;Lo;0;L;;;;;N;;;;;
+1BC38;DUPLOYAN LETTER W;Lo;0;L;;;;;N;;;;;
+1BC39;DUPLOYAN LETTER WH;Lo;0;L;;;;;N;;;;;
+1BC3A;DUPLOYAN LETTER W R;Lo;0;L;;;;;N;;;;;
+1BC3B;DUPLOYAN LETTER S N;Lo;0;L;;;;;N;;;;;
+1BC3C;DUPLOYAN LETTER S M;Lo;0;L;;;;;N;;;;;
+1BC3D;DUPLOYAN LETTER K R S;Lo;0;L;;;;;N;;;;;
+1BC3E;DUPLOYAN LETTER G R S;Lo;0;L;;;;;N;;;;;
+1BC3F;DUPLOYAN LETTER S K;Lo;0;L;;;;;N;;;;;
+1BC40;DUPLOYAN LETTER S K R;Lo;0;L;;;;;N;;;;;
+1BC41;DUPLOYAN LETTER A;Lo;0;L;;;;;N;;;;;
+1BC42;DUPLOYAN LETTER SLOAN OW;Lo;0;L;;;;;N;;;;;
+1BC43;DUPLOYAN LETTER OA;Lo;0;L;;;;;N;;;;;
+1BC44;DUPLOYAN LETTER O;Lo;0;L;;;;;N;;;;;
+1BC45;DUPLOYAN LETTER AOU;Lo;0;L;;;;;N;;;;;
+1BC46;DUPLOYAN LETTER I;Lo;0;L;;;;;N;;;;;
+1BC47;DUPLOYAN LETTER E;Lo;0;L;;;;;N;;;;;
+1BC48;DUPLOYAN LETTER IE;Lo;0;L;;;;;N;;;;;
+1BC49;DUPLOYAN LETTER SHORT I;Lo;0;L;;;;;N;;;;;
+1BC4A;DUPLOYAN LETTER UI;Lo;0;L;;;;;N;;;;;
+1BC4B;DUPLOYAN LETTER EE;Lo;0;L;;;;;N;;;;;
+1BC4C;DUPLOYAN LETTER SLOAN EH;Lo;0;L;;;;;N;;;;;
+1BC4D;DUPLOYAN LETTER ROMANIAN I;Lo;0;L;;;;;N;;;;;
+1BC4E;DUPLOYAN LETTER SLOAN EE;Lo;0;L;;;;;N;;;;;
+1BC4F;DUPLOYAN LETTER LONG I;Lo;0;L;;;;;N;;;;;
+1BC50;DUPLOYAN LETTER YE;Lo;0;L;;;;;N;;;;;
+1BC51;DUPLOYAN LETTER U;Lo;0;L;;;;;N;;;;;
+1BC52;DUPLOYAN LETTER EU;Lo;0;L;;;;;N;;;;;
+1BC53;DUPLOYAN LETTER XW;Lo;0;L;;;;;N;;;;;
+1BC54;DUPLOYAN LETTER U N;Lo;0;L;;;;;N;;;;;
+1BC55;DUPLOYAN LETTER LONG U;Lo;0;L;;;;;N;;;;;
+1BC56;DUPLOYAN LETTER ROMANIAN U;Lo;0;L;;;;;N;;;;;
+1BC57;DUPLOYAN LETTER UH;Lo;0;L;;;;;N;;;;;
+1BC58;DUPLOYAN LETTER SLOAN U;Lo;0;L;;;;;N;;;;;
+1BC59;DUPLOYAN LETTER OOH;Lo;0;L;;;;;N;;;;;
+1BC5A;DUPLOYAN LETTER OW;Lo;0;L;;;;;N;;;;;
+1BC5B;DUPLOYAN LETTER OU;Lo;0;L;;;;;N;;;;;
+1BC5C;DUPLOYAN LETTER WA;Lo;0;L;;;;;N;;;;;
+1BC5D;DUPLOYAN LETTER WO;Lo;0;L;;;;;N;;;;;
+1BC5E;DUPLOYAN LETTER WI;Lo;0;L;;;;;N;;;;;
+1BC5F;DUPLOYAN LETTER WEI;Lo;0;L;;;;;N;;;;;
+1BC60;DUPLOYAN LETTER WOW;Lo;0;L;;;;;N;;;;;
+1BC61;DUPLOYAN LETTER NASAL U;Lo;0;L;;;;;N;;;;;
+1BC62;DUPLOYAN LETTER NASAL O;Lo;0;L;;;;;N;;;;;
+1BC63;DUPLOYAN LETTER NASAL I;Lo;0;L;;;;;N;;;;;
+1BC64;DUPLOYAN LETTER NASAL A;Lo;0;L;;;;;N;;;;;
+1BC65;DUPLOYAN LETTER PERNIN AN;Lo;0;L;;;;;N;;;;;
+1BC66;DUPLOYAN LETTER PERNIN AM;Lo;0;L;;;;;N;;;;;
+1BC67;DUPLOYAN LETTER SLOAN EN;Lo;0;L;;;;;N;;;;;
+1BC68;DUPLOYAN LETTER SLOAN AN;Lo;0;L;;;;;N;;;;;
+1BC69;DUPLOYAN LETTER SLOAN ON;Lo;0;L;;;;;N;;;;;
+1BC6A;DUPLOYAN LETTER VOCALIC M;Lo;0;L;;;;;N;;;;;
+1BC70;DUPLOYAN AFFIX LEFT HORIZONTAL SECANT;Lo;0;L;;;;;N;;;;;
+1BC71;DUPLOYAN AFFIX MID HORIZONTAL SECANT;Lo;0;L;;;;;N;;;;;
+1BC72;DUPLOYAN AFFIX RIGHT HORIZONTAL SECANT;Lo;0;L;;;;;N;;;;;
+1BC73;DUPLOYAN AFFIX LOW VERTICAL SECANT;Lo;0;L;;;;;N;;;;;
+1BC74;DUPLOYAN AFFIX MID VERTICAL SECANT;Lo;0;L;;;;;N;;;;;
+1BC75;DUPLOYAN AFFIX HIGH VERTICAL SECANT;Lo;0;L;;;;;N;;;;;
+1BC76;DUPLOYAN AFFIX ATTACHED SECANT;Lo;0;L;;;;;N;;;;;
+1BC77;DUPLOYAN AFFIX ATTACHED LEFT-TO-RIGHT SECANT;Lo;0;L;;;;;N;;;;;
+1BC78;DUPLOYAN AFFIX ATTACHED TANGENT;Lo;0;L;;;;;N;;;;;
+1BC79;DUPLOYAN AFFIX ATTACHED TAIL;Lo;0;L;;;;;N;;;;;
+1BC7A;DUPLOYAN AFFIX ATTACHED E HOOK;Lo;0;L;;;;;N;;;;;
+1BC7B;DUPLOYAN AFFIX ATTACHED I HOOK;Lo;0;L;;;;;N;;;;;
+1BC7C;DUPLOYAN AFFIX ATTACHED TANGENT HOOK;Lo;0;L;;;;;N;;;;;
+1BC80;DUPLOYAN AFFIX HIGH ACUTE;Lo;0;L;;;;;N;;;;;
+1BC81;DUPLOYAN AFFIX HIGH TIGHT ACUTE;Lo;0;L;;;;;N;;;;;
+1BC82;DUPLOYAN AFFIX HIGH GRAVE;Lo;0;L;;;;;N;;;;;
+1BC83;DUPLOYAN AFFIX HIGH LONG GRAVE;Lo;0;L;;;;;N;;;;;
+1BC84;DUPLOYAN AFFIX HIGH DOT;Lo;0;L;;;;;N;;;;;
+1BC85;DUPLOYAN AFFIX HIGH CIRCLE;Lo;0;L;;;;;N;;;;;
+1BC86;DUPLOYAN AFFIX HIGH LINE;Lo;0;L;;;;;N;;;;;
+1BC87;DUPLOYAN AFFIX HIGH WAVE;Lo;0;L;;;;;N;;;;;
+1BC88;DUPLOYAN AFFIX HIGH VERTICAL;Lo;0;L;;;;;N;;;;;
+1BC90;DUPLOYAN AFFIX LOW ACUTE;Lo;0;L;;;;;N;;;;;
+1BC91;DUPLOYAN AFFIX LOW TIGHT ACUTE;Lo;0;L;;;;;N;;;;;
+1BC92;DUPLOYAN AFFIX LOW GRAVE;Lo;0;L;;;;;N;;;;;
+1BC93;DUPLOYAN AFFIX LOW LONG GRAVE;Lo;0;L;;;;;N;;;;;
+1BC94;DUPLOYAN AFFIX LOW DOT;Lo;0;L;;;;;N;;;;;
+1BC95;DUPLOYAN AFFIX LOW CIRCLE;Lo;0;L;;;;;N;;;;;
+1BC96;DUPLOYAN AFFIX LOW LINE;Lo;0;L;;;;;N;;;;;
+1BC97;DUPLOYAN AFFIX LOW WAVE;Lo;0;L;;;;;N;;;;;
+1BC98;DUPLOYAN AFFIX LOW VERTICAL;Lo;0;L;;;;;N;;;;;
+1BC99;DUPLOYAN AFFIX LOW ARROW;Lo;0;L;;;;;N;;;;;
+1BC9C;DUPLOYAN SIGN O WITH CROSS;So;0;L;;;;;N;;;;;
+1BC9D;DUPLOYAN THICK LETTER SELECTOR;Mn;0;NSM;;;;;N;;;;;
+1BC9E;DUPLOYAN DOUBLE MARK;Mn;1;NSM;;;;;N;;;;;
+1BC9F;DUPLOYAN PUNCTUATION CHINOOK FULL STOP;Po;0;L;;;;;N;;;;;
+1BCA0;SHORTHAND FORMAT LETTER OVERLAP;Cf;0;BN;;;;;N;;;;;
+1BCA1;SHORTHAND FORMAT CONTINUING OVERLAP;Cf;0;BN;;;;;N;;;;;
+1BCA2;SHORTHAND FORMAT DOWN STEP;Cf;0;BN;;;;;N;;;;;
+1BCA3;SHORTHAND FORMAT UP STEP;Cf;0;BN;;;;;N;;;;;
 1D000;BYZANTINE MUSICAL SYMBOL PSILI;So;0;L;;;;;N;;;;;
 1D001;BYZANTINE MUSICAL SYMBOL DASEIA;So;0;L;;;;;N;;;;;
 1D002;BYZANTINE MUSICAL SYMBOL PERISPOMENI;So;0;L;;;;;N;;;;;
@@ -22169,6 +24251,219 @@
 1D7FD;MATHEMATICAL MONOSPACE DIGIT SEVEN;Nd;0;EN;<font> 0037;7;7;7;N;;;;;
 1D7FE;MATHEMATICAL MONOSPACE DIGIT EIGHT;Nd;0;EN;<font> 0038;8;8;8;N;;;;;
 1D7FF;MATHEMATICAL MONOSPACE DIGIT NINE;Nd;0;EN;<font> 0039;9;9;9;N;;;;;
+1E800;MENDE KIKAKUI SYLLABLE M001 KI;Lo;0;R;;;;;N;;;;;
+1E801;MENDE KIKAKUI SYLLABLE M002 KA;Lo;0;R;;;;;N;;;;;
+1E802;MENDE KIKAKUI SYLLABLE M003 KU;Lo;0;R;;;;;N;;;;;
+1E803;MENDE KIKAKUI SYLLABLE M065 KEE;Lo;0;R;;;;;N;;;;;
+1E804;MENDE KIKAKUI SYLLABLE M095 KE;Lo;0;R;;;;;N;;;;;
+1E805;MENDE KIKAKUI SYLLABLE M076 KOO;Lo;0;R;;;;;N;;;;;
+1E806;MENDE KIKAKUI SYLLABLE M048 KO;Lo;0;R;;;;;N;;;;;
+1E807;MENDE KIKAKUI SYLLABLE M179 KUA;Lo;0;R;;;;;N;;;;;
+1E808;MENDE KIKAKUI SYLLABLE M004 WI;Lo;0;R;;;;;N;;;;;
+1E809;MENDE KIKAKUI SYLLABLE M005 WA;Lo;0;R;;;;;N;;;;;
+1E80A;MENDE KIKAKUI SYLLABLE M006 WU;Lo;0;R;;;;;N;;;;;
+1E80B;MENDE KIKAKUI SYLLABLE M126 WEE;Lo;0;R;;;;;N;;;;;
+1E80C;MENDE KIKAKUI SYLLABLE M118 WE;Lo;0;R;;;;;N;;;;;
+1E80D;MENDE KIKAKUI SYLLABLE M114 WOO;Lo;0;R;;;;;N;;;;;
+1E80E;MENDE KIKAKUI SYLLABLE M045 WO;Lo;0;R;;;;;N;;;;;
+1E80F;MENDE KIKAKUI SYLLABLE M194 WUI;Lo;0;R;;;;;N;;;;;
+1E810;MENDE KIKAKUI SYLLABLE M143 WEI;Lo;0;R;;;;;N;;;;;
+1E811;MENDE KIKAKUI SYLLABLE M061 WVI;Lo;0;R;;;;;N;;;;;
+1E812;MENDE KIKAKUI SYLLABLE M049 WVA;Lo;0;R;;;;;N;;;;;
+1E813;MENDE KIKAKUI SYLLABLE M139 WVE;Lo;0;R;;;;;N;;;;;
+1E814;MENDE KIKAKUI SYLLABLE M007 MIN;Lo;0;R;;;;;N;;;;;
+1E815;MENDE KIKAKUI SYLLABLE M008 MAN;Lo;0;R;;;;;N;;;;;
+1E816;MENDE KIKAKUI SYLLABLE M009 MUN;Lo;0;R;;;;;N;;;;;
+1E817;MENDE KIKAKUI SYLLABLE M059 MEN;Lo;0;R;;;;;N;;;;;
+1E818;MENDE KIKAKUI SYLLABLE M094 MON;Lo;0;R;;;;;N;;;;;
+1E819;MENDE KIKAKUI SYLLABLE M154 MUAN;Lo;0;R;;;;;N;;;;;
+1E81A;MENDE KIKAKUI SYLLABLE M189 MUEN;Lo;0;R;;;;;N;;;;;
+1E81B;MENDE KIKAKUI SYLLABLE M010 BI;Lo;0;R;;;;;N;;;;;
+1E81C;MENDE KIKAKUI SYLLABLE M011 BA;Lo;0;R;;;;;N;;;;;
+1E81D;MENDE KIKAKUI SYLLABLE M012 BU;Lo;0;R;;;;;N;;;;;
+1E81E;MENDE KIKAKUI SYLLABLE M150 BEE;Lo;0;R;;;;;N;;;;;
+1E81F;MENDE KIKAKUI SYLLABLE M097 BE;Lo;0;R;;;;;N;;;;;
+1E820;MENDE KIKAKUI SYLLABLE M103 BOO;Lo;0;R;;;;;N;;;;;
+1E821;MENDE KIKAKUI SYLLABLE M138 BO;Lo;0;R;;;;;N;;;;;
+1E822;MENDE KIKAKUI SYLLABLE M013 I;Lo;0;R;;;;;N;;;;;
+1E823;MENDE KIKAKUI SYLLABLE M014 A;Lo;0;R;;;;;N;;;;;
+1E824;MENDE KIKAKUI SYLLABLE M015 U;Lo;0;R;;;;;N;;;;;
+1E825;MENDE KIKAKUI SYLLABLE M163 EE;Lo;0;R;;;;;N;;;;;
+1E826;MENDE KIKAKUI SYLLABLE M100 E;Lo;0;R;;;;;N;;;;;
+1E827;MENDE KIKAKUI SYLLABLE M165 OO;Lo;0;R;;;;;N;;;;;
+1E828;MENDE KIKAKUI SYLLABLE M147 O;Lo;0;R;;;;;N;;;;;
+1E829;MENDE KIKAKUI SYLLABLE M137 EI;Lo;0;R;;;;;N;;;;;
+1E82A;MENDE KIKAKUI SYLLABLE M131 IN;Lo;0;R;;;;;N;;;;;
+1E82B;MENDE KIKAKUI SYLLABLE M135 IN;Lo;0;R;;;;;N;;;;;
+1E82C;MENDE KIKAKUI SYLLABLE M195 AN;Lo;0;R;;;;;N;;;;;
+1E82D;MENDE KIKAKUI SYLLABLE M178 EN;Lo;0;R;;;;;N;;;;;
+1E82E;MENDE KIKAKUI SYLLABLE M019 SI;Lo;0;R;;;;;N;;;;;
+1E82F;MENDE KIKAKUI SYLLABLE M020 SA;Lo;0;R;;;;;N;;;;;
+1E830;MENDE KIKAKUI SYLLABLE M021 SU;Lo;0;R;;;;;N;;;;;
+1E831;MENDE KIKAKUI SYLLABLE M162 SEE;Lo;0;R;;;;;N;;;;;
+1E832;MENDE KIKAKUI SYLLABLE M116 SE;Lo;0;R;;;;;N;;;;;
+1E833;MENDE KIKAKUI SYLLABLE M136 SOO;Lo;0;R;;;;;N;;;;;
+1E834;MENDE KIKAKUI SYLLABLE M079 SO;Lo;0;R;;;;;N;;;;;
+1E835;MENDE KIKAKUI SYLLABLE M196 SIA;Lo;0;R;;;;;N;;;;;
+1E836;MENDE KIKAKUI SYLLABLE M025 LI;Lo;0;R;;;;;N;;;;;
+1E837;MENDE KIKAKUI SYLLABLE M026 LA;Lo;0;R;;;;;N;;;;;
+1E838;MENDE KIKAKUI SYLLABLE M027 LU;Lo;0;R;;;;;N;;;;;
+1E839;MENDE KIKAKUI SYLLABLE M084 LEE;Lo;0;R;;;;;N;;;;;
+1E83A;MENDE KIKAKUI SYLLABLE M073 LE;Lo;0;R;;;;;N;;;;;
+1E83B;MENDE KIKAKUI SYLLABLE M054 LOO;Lo;0;R;;;;;N;;;;;
+1E83C;MENDE KIKAKUI SYLLABLE M153 LO;Lo;0;R;;;;;N;;;;;
+1E83D;MENDE KIKAKUI SYLLABLE M110 LONG LE;Lo;0;R;;;;;N;;;;;
+1E83E;MENDE KIKAKUI SYLLABLE M016 DI;Lo;0;R;;;;;N;;;;;
+1E83F;MENDE KIKAKUI SYLLABLE M017 DA;Lo;0;R;;;;;N;;;;;
+1E840;MENDE KIKAKUI SYLLABLE M018 DU;Lo;0;R;;;;;N;;;;;
+1E841;MENDE KIKAKUI SYLLABLE M089 DEE;Lo;0;R;;;;;N;;;;;
+1E842;MENDE KIKAKUI SYLLABLE M180 DOO;Lo;0;R;;;;;N;;;;;
+1E843;MENDE KIKAKUI SYLLABLE M181 DO;Lo;0;R;;;;;N;;;;;
+1E844;MENDE KIKAKUI SYLLABLE M022 TI;Lo;0;R;;;;;N;;;;;
+1E845;MENDE KIKAKUI SYLLABLE M023 TA;Lo;0;R;;;;;N;;;;;
+1E846;MENDE KIKAKUI SYLLABLE M024 TU;Lo;0;R;;;;;N;;;;;
+1E847;MENDE KIKAKUI SYLLABLE M091 TEE;Lo;0;R;;;;;N;;;;;
+1E848;MENDE KIKAKUI SYLLABLE M055 TE;Lo;0;R;;;;;N;;;;;
+1E849;MENDE KIKAKUI SYLLABLE M104 TOO;Lo;0;R;;;;;N;;;;;
+1E84A;MENDE KIKAKUI SYLLABLE M069 TO;Lo;0;R;;;;;N;;;;;
+1E84B;MENDE KIKAKUI SYLLABLE M028 JI;Lo;0;R;;;;;N;;;;;
+1E84C;MENDE KIKAKUI SYLLABLE M029 JA;Lo;0;R;;;;;N;;;;;
+1E84D;MENDE KIKAKUI SYLLABLE M030 JU;Lo;0;R;;;;;N;;;;;
+1E84E;MENDE KIKAKUI SYLLABLE M157 JEE;Lo;0;R;;;;;N;;;;;
+1E84F;MENDE KIKAKUI SYLLABLE M113 JE;Lo;0;R;;;;;N;;;;;
+1E850;MENDE KIKAKUI SYLLABLE M160 JOO;Lo;0;R;;;;;N;;;;;
+1E851;MENDE KIKAKUI SYLLABLE M063 JO;Lo;0;R;;;;;N;;;;;
+1E852;MENDE KIKAKUI SYLLABLE M175 LONG JO;Lo;0;R;;;;;N;;;;;
+1E853;MENDE KIKAKUI SYLLABLE M031 YI;Lo;0;R;;;;;N;;;;;
+1E854;MENDE KIKAKUI SYLLABLE M032 YA;Lo;0;R;;;;;N;;;;;
+1E855;MENDE KIKAKUI SYLLABLE M033 YU;Lo;0;R;;;;;N;;;;;
+1E856;MENDE KIKAKUI SYLLABLE M109 YEE;Lo;0;R;;;;;N;;;;;
+1E857;MENDE KIKAKUI SYLLABLE M080 YE;Lo;0;R;;;;;N;;;;;
+1E858;MENDE KIKAKUI SYLLABLE M141 YOO;Lo;0;R;;;;;N;;;;;
+1E859;MENDE KIKAKUI SYLLABLE M121 YO;Lo;0;R;;;;;N;;;;;
+1E85A;MENDE KIKAKUI SYLLABLE M034 FI;Lo;0;R;;;;;N;;;;;
+1E85B;MENDE KIKAKUI SYLLABLE M035 FA;Lo;0;R;;;;;N;;;;;
+1E85C;MENDE KIKAKUI SYLLABLE M036 FU;Lo;0;R;;;;;N;;;;;
+1E85D;MENDE KIKAKUI SYLLABLE M078 FEE;Lo;0;R;;;;;N;;;;;
+1E85E;MENDE KIKAKUI SYLLABLE M075 FE;Lo;0;R;;;;;N;;;;;
+1E85F;MENDE KIKAKUI SYLLABLE M133 FOO;Lo;0;R;;;;;N;;;;;
+1E860;MENDE KIKAKUI SYLLABLE M088 FO;Lo;0;R;;;;;N;;;;;
+1E861;MENDE KIKAKUI SYLLABLE M197 FUA;Lo;0;R;;;;;N;;;;;
+1E862;MENDE KIKAKUI SYLLABLE M101 FAN;Lo;0;R;;;;;N;;;;;
+1E863;MENDE KIKAKUI SYLLABLE M037 NIN;Lo;0;R;;;;;N;;;;;
+1E864;MENDE KIKAKUI SYLLABLE M038 NAN;Lo;0;R;;;;;N;;;;;
+1E865;MENDE KIKAKUI SYLLABLE M039 NUN;Lo;0;R;;;;;N;;;;;
+1E866;MENDE KIKAKUI SYLLABLE M117 NEN;Lo;0;R;;;;;N;;;;;
+1E867;MENDE KIKAKUI SYLLABLE M169 NON;Lo;0;R;;;;;N;;;;;
+1E868;MENDE KIKAKUI SYLLABLE M176 HI;Lo;0;R;;;;;N;;;;;
+1E869;MENDE KIKAKUI SYLLABLE M041 HA;Lo;0;R;;;;;N;;;;;
+1E86A;MENDE KIKAKUI SYLLABLE M186 HU;Lo;0;R;;;;;N;;;;;
+1E86B;MENDE KIKAKUI SYLLABLE M040 HEE;Lo;0;R;;;;;N;;;;;
+1E86C;MENDE KIKAKUI SYLLABLE M096 HE;Lo;0;R;;;;;N;;;;;
+1E86D;MENDE KIKAKUI SYLLABLE M042 HOO;Lo;0;R;;;;;N;;;;;
+1E86E;MENDE KIKAKUI SYLLABLE M140 HO;Lo;0;R;;;;;N;;;;;
+1E86F;MENDE KIKAKUI SYLLABLE M083 HEEI;Lo;0;R;;;;;N;;;;;
+1E870;MENDE KIKAKUI SYLLABLE M128 HOOU;Lo;0;R;;;;;N;;;;;
+1E871;MENDE KIKAKUI SYLLABLE M053 HIN;Lo;0;R;;;;;N;;;;;
+1E872;MENDE KIKAKUI SYLLABLE M130 HAN;Lo;0;R;;;;;N;;;;;
+1E873;MENDE KIKAKUI SYLLABLE M087 HUN;Lo;0;R;;;;;N;;;;;
+1E874;MENDE KIKAKUI SYLLABLE M052 HEN;Lo;0;R;;;;;N;;;;;
+1E875;MENDE KIKAKUI SYLLABLE M193 HON;Lo;0;R;;;;;N;;;;;
+1E876;MENDE KIKAKUI SYLLABLE M046 HUAN;Lo;0;R;;;;;N;;;;;
+1E877;MENDE KIKAKUI SYLLABLE M090 NGGI;Lo;0;R;;;;;N;;;;;
+1E878;MENDE KIKAKUI SYLLABLE M043 NGGA;Lo;0;R;;;;;N;;;;;
+1E879;MENDE KIKAKUI SYLLABLE M082 NGGU;Lo;0;R;;;;;N;;;;;
+1E87A;MENDE KIKAKUI SYLLABLE M115 NGGEE;Lo;0;R;;;;;N;;;;;
+1E87B;MENDE KIKAKUI SYLLABLE M146 NGGE;Lo;0;R;;;;;N;;;;;
+1E87C;MENDE KIKAKUI SYLLABLE M156 NGGOO;Lo;0;R;;;;;N;;;;;
+1E87D;MENDE KIKAKUI SYLLABLE M120 NGGO;Lo;0;R;;;;;N;;;;;
+1E87E;MENDE KIKAKUI SYLLABLE M159 NGGAA;Lo;0;R;;;;;N;;;;;
+1E87F;MENDE KIKAKUI SYLLABLE M127 NGGUA;Lo;0;R;;;;;N;;;;;
+1E880;MENDE KIKAKUI SYLLABLE M086 LONG NGGE;Lo;0;R;;;;;N;;;;;
+1E881;MENDE KIKAKUI SYLLABLE M106 LONG NGGOO;Lo;0;R;;;;;N;;;;;
+1E882;MENDE KIKAKUI SYLLABLE M183 LONG NGGO;Lo;0;R;;;;;N;;;;;
+1E883;MENDE KIKAKUI SYLLABLE M155 GI;Lo;0;R;;;;;N;;;;;
+1E884;MENDE KIKAKUI SYLLABLE M111 GA;Lo;0;R;;;;;N;;;;;
+1E885;MENDE KIKAKUI SYLLABLE M168 GU;Lo;0;R;;;;;N;;;;;
+1E886;MENDE KIKAKUI SYLLABLE M190 GEE;Lo;0;R;;;;;N;;;;;
+1E887;MENDE KIKAKUI SYLLABLE M166 GUEI;Lo;0;R;;;;;N;;;;;
+1E888;MENDE KIKAKUI SYLLABLE M167 GUAN;Lo;0;R;;;;;N;;;;;
+1E889;MENDE KIKAKUI SYLLABLE M184 NGEN;Lo;0;R;;;;;N;;;;;
+1E88A;MENDE KIKAKUI SYLLABLE M057 NGON;Lo;0;R;;;;;N;;;;;
+1E88B;MENDE KIKAKUI SYLLABLE M177 NGUAN;Lo;0;R;;;;;N;;;;;
+1E88C;MENDE KIKAKUI SYLLABLE M068 PI;Lo;0;R;;;;;N;;;;;
+1E88D;MENDE KIKAKUI SYLLABLE M099 PA;Lo;0;R;;;;;N;;;;;
+1E88E;MENDE KIKAKUI SYLLABLE M050 PU;Lo;0;R;;;;;N;;;;;
+1E88F;MENDE KIKAKUI SYLLABLE M081 PEE;Lo;0;R;;;;;N;;;;;
+1E890;MENDE KIKAKUI SYLLABLE M051 PE;Lo;0;R;;;;;N;;;;;
+1E891;MENDE KIKAKUI SYLLABLE M102 POO;Lo;0;R;;;;;N;;;;;
+1E892;MENDE KIKAKUI SYLLABLE M066 PO;Lo;0;R;;;;;N;;;;;
+1E893;MENDE KIKAKUI SYLLABLE M145 MBI;Lo;0;R;;;;;N;;;;;
+1E894;MENDE KIKAKUI SYLLABLE M062 MBA;Lo;0;R;;;;;N;;;;;
+1E895;MENDE KIKAKUI SYLLABLE M122 MBU;Lo;0;R;;;;;N;;;;;
+1E896;MENDE KIKAKUI SYLLABLE M047 MBEE;Lo;0;R;;;;;N;;;;;
+1E897;MENDE KIKAKUI SYLLABLE M188 MBEE;Lo;0;R;;;;;N;;;;;
+1E898;MENDE KIKAKUI SYLLABLE M072 MBE;Lo;0;R;;;;;N;;;;;
+1E899;MENDE KIKAKUI SYLLABLE M172 MBOO;Lo;0;R;;;;;N;;;;;
+1E89A;MENDE KIKAKUI SYLLABLE M174 MBO;Lo;0;R;;;;;N;;;;;
+1E89B;MENDE KIKAKUI SYLLABLE M187 MBUU;Lo;0;R;;;;;N;;;;;
+1E89C;MENDE KIKAKUI SYLLABLE M161 LONG MBE;Lo;0;R;;;;;N;;;;;
+1E89D;MENDE KIKAKUI SYLLABLE M105 LONG MBOO;Lo;0;R;;;;;N;;;;;
+1E89E;MENDE KIKAKUI SYLLABLE M142 LONG MBO;Lo;0;R;;;;;N;;;;;
+1E89F;MENDE KIKAKUI SYLLABLE M132 KPI;Lo;0;R;;;;;N;;;;;
+1E8A0;MENDE KIKAKUI SYLLABLE M092 KPA;Lo;0;R;;;;;N;;;;;
+1E8A1;MENDE KIKAKUI SYLLABLE M074 KPU;Lo;0;R;;;;;N;;;;;
+1E8A2;MENDE KIKAKUI SYLLABLE M044 KPEE;Lo;0;R;;;;;N;;;;;
+1E8A3;MENDE KIKAKUI SYLLABLE M108 KPE;Lo;0;R;;;;;N;;;;;
+1E8A4;MENDE KIKAKUI SYLLABLE M112 KPOO;Lo;0;R;;;;;N;;;;;
+1E8A5;MENDE KIKAKUI SYLLABLE M158 KPO;Lo;0;R;;;;;N;;;;;
+1E8A6;MENDE KIKAKUI SYLLABLE M124 GBI;Lo;0;R;;;;;N;;;;;
+1E8A7;MENDE KIKAKUI SYLLABLE M056 GBA;Lo;0;R;;;;;N;;;;;
+1E8A8;MENDE KIKAKUI SYLLABLE M148 GBU;Lo;0;R;;;;;N;;;;;
+1E8A9;MENDE KIKAKUI SYLLABLE M093 GBEE;Lo;0;R;;;;;N;;;;;
+1E8AA;MENDE KIKAKUI SYLLABLE M107 GBE;Lo;0;R;;;;;N;;;;;
+1E8AB;MENDE KIKAKUI SYLLABLE M071 GBOO;Lo;0;R;;;;;N;;;;;
+1E8AC;MENDE KIKAKUI SYLLABLE M070 GBO;Lo;0;R;;;;;N;;;;;
+1E8AD;MENDE KIKAKUI SYLLABLE M171 RA;Lo;0;R;;;;;N;;;;;
+1E8AE;MENDE KIKAKUI SYLLABLE M123 NDI;Lo;0;R;;;;;N;;;;;
+1E8AF;MENDE KIKAKUI SYLLABLE M129 NDA;Lo;0;R;;;;;N;;;;;
+1E8B0;MENDE KIKAKUI SYLLABLE M125 NDU;Lo;0;R;;;;;N;;;;;
+1E8B1;MENDE KIKAKUI SYLLABLE M191 NDEE;Lo;0;R;;;;;N;;;;;
+1E8B2;MENDE KIKAKUI SYLLABLE M119 NDE;Lo;0;R;;;;;N;;;;;
+1E8B3;MENDE KIKAKUI SYLLABLE M067 NDOO;Lo;0;R;;;;;N;;;;;
+1E8B4;MENDE KIKAKUI SYLLABLE M064 NDO;Lo;0;R;;;;;N;;;;;
+1E8B5;MENDE KIKAKUI SYLLABLE M152 NJA;Lo;0;R;;;;;N;;;;;
+1E8B6;MENDE KIKAKUI SYLLABLE M192 NJU;Lo;0;R;;;;;N;;;;;
+1E8B7;MENDE KIKAKUI SYLLABLE M149 NJEE;Lo;0;R;;;;;N;;;;;
+1E8B8;MENDE KIKAKUI SYLLABLE M134 NJOO;Lo;0;R;;;;;N;;;;;
+1E8B9;MENDE KIKAKUI SYLLABLE M182 VI;Lo;0;R;;;;;N;;;;;
+1E8BA;MENDE KIKAKUI SYLLABLE M185 VA;Lo;0;R;;;;;N;;;;;
+1E8BB;MENDE KIKAKUI SYLLABLE M151 VU;Lo;0;R;;;;;N;;;;;
+1E8BC;MENDE KIKAKUI SYLLABLE M173 VEE;Lo;0;R;;;;;N;;;;;
+1E8BD;MENDE KIKAKUI SYLLABLE M085 VE;Lo;0;R;;;;;N;;;;;
+1E8BE;MENDE KIKAKUI SYLLABLE M144 VOO;Lo;0;R;;;;;N;;;;;
+1E8BF;MENDE KIKAKUI SYLLABLE M077 VO;Lo;0;R;;;;;N;;;;;
+1E8C0;MENDE KIKAKUI SYLLABLE M164 NYIN;Lo;0;R;;;;;N;;;;;
+1E8C1;MENDE KIKAKUI SYLLABLE M058 NYAN;Lo;0;R;;;;;N;;;;;
+1E8C2;MENDE KIKAKUI SYLLABLE M170 NYUN;Lo;0;R;;;;;N;;;;;
+1E8C3;MENDE KIKAKUI SYLLABLE M098 NYEN;Lo;0;R;;;;;N;;;;;
+1E8C4;MENDE KIKAKUI SYLLABLE M060 NYON;Lo;0;R;;;;;N;;;;;
+1E8C7;MENDE KIKAKUI DIGIT ONE;No;0;R;;;;1;N;;;;;
+1E8C8;MENDE KIKAKUI DIGIT TWO;No;0;R;;;;2;N;;;;;
+1E8C9;MENDE KIKAKUI DIGIT THREE;No;0;R;;;;3;N;;;;;
+1E8CA;MENDE KIKAKUI DIGIT FOUR;No;0;R;;;;4;N;;;;;
+1E8CB;MENDE KIKAKUI DIGIT FIVE;No;0;R;;;;5;N;;;;;
+1E8CC;MENDE KIKAKUI DIGIT SIX;No;0;R;;;;6;N;;;;;
+1E8CD;MENDE KIKAKUI DIGIT SEVEN;No;0;R;;;;7;N;;;;;
+1E8CE;MENDE KIKAKUI DIGIT EIGHT;No;0;R;;;;8;N;;;;;
+1E8CF;MENDE KIKAKUI DIGIT NINE;No;0;R;;;;9;N;;;;;
+1E8D0;MENDE KIKAKUI COMBINING NUMBER TEENS;Mn;220;NSM;;;;;N;;;;;
+1E8D1;MENDE KIKAKUI COMBINING NUMBER TENS;Mn;220;NSM;;;;;N;;;;;
+1E8D2;MENDE KIKAKUI COMBINING NUMBER HUNDREDS;Mn;220;NSM;;;;;N;;;;;
+1E8D3;MENDE KIKAKUI COMBINING NUMBER THOUSANDS;Mn;220;NSM;;;;;N;;;;;
+1E8D4;MENDE KIKAKUI COMBINING NUMBER TEN THOUSANDS;Mn;220;NSM;;;;;N;;;;;
+1E8D5;MENDE KIKAKUI COMBINING NUMBER HUNDRED THOUSANDS;Mn;220;NSM;;;;;N;;;;;
+1E8D6;MENDE KIKAKUI COMBINING NUMBER MILLIONS;Mn;220;NSM;;;;;N;;;;;
 1EE00;ARABIC MATHEMATICAL ALEF;Lo;0;AL;<font> 0627;;;;N;;;;;
 1EE01;ARABIC MATHEMATICAL BEH;Lo;0;AL;<font> 0628;;;;N;;;;;
 1EE02;ARABIC MATHEMATICAL JEEM;Lo;0;AL;<font> 062C;;;;N;;;;;
@@ -22485,6 +24780,7 @@
 1F0BC;PLAYING CARD KNIGHT OF HEARTS;So;0;ON;;;;;N;;;;;
 1F0BD;PLAYING CARD QUEEN OF HEARTS;So;0;ON;;;;;N;;;;;
 1F0BE;PLAYING CARD KING OF HEARTS;So;0;ON;;;;;N;;;;;
+1F0BF;PLAYING CARD RED JOKER;So;0;ON;;;;;N;;;;;
 1F0C1;PLAYING CARD ACE OF DIAMONDS;So;0;ON;;;;;N;;;;;
 1F0C2;PLAYING CARD TWO OF DIAMONDS;So;0;ON;;;;;N;;;;;
 1F0C3;PLAYING CARD THREE OF DIAMONDS;So;0;ON;;;;;N;;;;;
@@ -22515,6 +24811,28 @@
 1F0DD;PLAYING CARD QUEEN OF CLUBS;So;0;ON;;;;;N;;;;;
 1F0DE;PLAYING CARD KING OF CLUBS;So;0;ON;;;;;N;;;;;
 1F0DF;PLAYING CARD WHITE JOKER;So;0;ON;;;;;N;;;;;
+1F0E0;PLAYING CARD FOOL;So;0;ON;;;;;N;;;;;
+1F0E1;PLAYING CARD TRUMP-1;So;0;ON;;;;;N;;;;;
+1F0E2;PLAYING CARD TRUMP-2;So;0;ON;;;;;N;;;;;
+1F0E3;PLAYING CARD TRUMP-3;So;0;ON;;;;;N;;;;;
+1F0E4;PLAYING CARD TRUMP-4;So;0;ON;;;;;N;;;;;
+1F0E5;PLAYING CARD TRUMP-5;So;0;ON;;;;;N;;;;;
+1F0E6;PLAYING CARD TRUMP-6;So;0;ON;;;;;N;;;;;
+1F0E7;PLAYING CARD TRUMP-7;So;0;ON;;;;;N;;;;;
+1F0E8;PLAYING CARD TRUMP-8;So;0;ON;;;;;N;;;;;
+1F0E9;PLAYING CARD TRUMP-9;So;0;ON;;;;;N;;;;;
+1F0EA;PLAYING CARD TRUMP-10;So;0;ON;;;;;N;;;;;
+1F0EB;PLAYING CARD TRUMP-11;So;0;ON;;;;;N;;;;;
+1F0EC;PLAYING CARD TRUMP-12;So;0;ON;;;;;N;;;;;
+1F0ED;PLAYING CARD TRUMP-13;So;0;ON;;;;;N;;;;;
+1F0EE;PLAYING CARD TRUMP-14;So;0;ON;;;;;N;;;;;
+1F0EF;PLAYING CARD TRUMP-15;So;0;ON;;;;;N;;;;;
+1F0F0;PLAYING CARD TRUMP-16;So;0;ON;;;;;N;;;;;
+1F0F1;PLAYING CARD TRUMP-17;So;0;ON;;;;;N;;;;;
+1F0F2;PLAYING CARD TRUMP-18;So;0;ON;;;;;N;;;;;
+1F0F3;PLAYING CARD TRUMP-19;So;0;ON;;;;;N;;;;;
+1F0F4;PLAYING CARD TRUMP-20;So;0;ON;;;;;N;;;;;
+1F0F5;PLAYING CARD TRUMP-21;So;0;ON;;;;;N;;;;;
 1F100;DIGIT ZERO FULL STOP;No;0;EN;<compat> 0030 002E;;0;0;N;;;;;
 1F101;DIGIT ZERO COMMA;No;0;EN;<compat> 0030 002C;;0;0;N;;;;;
 1F102;DIGIT ONE COMMA;No;0;EN;<compat> 0031 002C;;1;1;N;;;;;
@@ -22526,6 +24844,8 @@
 1F108;DIGIT SEVEN COMMA;No;0;EN;<compat> 0037 002C;;7;7;N;;;;;
 1F109;DIGIT EIGHT COMMA;No;0;EN;<compat> 0038 002C;;8;8;N;;;;;
 1F10A;DIGIT NINE COMMA;No;0;EN;<compat> 0039 002C;;9;9;N;;;;;
+1F10B;DINGBAT CIRCLED SANS-SERIF DIGIT ZERO;No;0;ON;;;;0;N;;;;;
+1F10C;DINGBAT NEGATIVE CIRCLED SANS-SERIF DIGIT ZERO;No;0;ON;;;;0;N;;;;;
 1F110;PARENTHESIZED LATIN CAPITAL LETTER A;So;0;L;<compat> 0028 0041 0029;;;;N;;;;;
 1F111;PARENTHESIZED LATIN CAPITAL LETTER B;So;0;L;<compat> 0028 0042 0029;;;;N;;;;;
 1F112;PARENTHESIZED LATIN CAPITAL LETTER C;So;0;L;<compat> 0028 0043 0029;;;;N;;;;;
@@ -22776,12 +25096,25 @@
 1F31E;SUN WITH FACE;So;0;ON;;;;;N;;;;;
 1F31F;GLOWING STAR;So;0;ON;;;;;N;;;;;
 1F320;SHOOTING STAR;So;0;ON;;;;;N;;;;;
+1F321;THERMOMETER;So;0;ON;;;;;N;;;;;
+1F322;BLACK DROPLET;So;0;ON;;;;;N;;;;;
+1F323;WHITE SUN;So;0;ON;;;;;N;;;;;
+1F324;WHITE SUN WITH SMALL CLOUD;So;0;ON;;;;;N;;;;;
+1F325;WHITE SUN BEHIND CLOUD;So;0;ON;;;;;N;;;;;
+1F326;WHITE SUN BEHIND CLOUD WITH RAIN;So;0;ON;;;;;N;;;;;
+1F327;CLOUD WITH RAIN;So;0;ON;;;;;N;;;;;
+1F328;CLOUD WITH SNOW;So;0;ON;;;;;N;;;;;
+1F329;CLOUD WITH LIGHTNING;So;0;ON;;;;;N;;;;;
+1F32A;CLOUD WITH TORNADO;So;0;ON;;;;;N;;;;;
+1F32B;FOG;So;0;ON;;;;;N;;;;;
+1F32C;WIND BLOWING FACE;So;0;ON;;;;;N;;;;;
 1F330;CHESTNUT;So;0;ON;;;;;N;;;;;
 1F331;SEEDLING;So;0;ON;;;;;N;;;;;
 1F332;EVERGREEN TREE;So;0;ON;;;;;N;;;;;
 1F333;DECIDUOUS TREE;So;0;ON;;;;;N;;;;;
 1F334;PALM TREE;So;0;ON;;;;;N;;;;;
 1F335;CACTUS;So;0;ON;;;;;N;;;;;
+1F336;HOT PEPPER;So;0;ON;;;;;N;;;;;
 1F337;TULIP;So;0;ON;;;;;N;;;;;
 1F338;CHERRY BLOSSOM;So;0;ON;;;;;N;;;;;
 1F339;ROSE;So;0;ON;;;;;N;;;;;
@@ -22852,6 +25185,7 @@
 1F37A;BEER MUG;So;0;ON;;;;;N;;;;;
 1F37B;CLINKING BEER MUGS;So;0;ON;;;;;N;;;;;
 1F37C;BABY BOTTLE;So;0;ON;;;;;N;;;;;
+1F37D;FORK AND KNIFE WITH PLATE;So;0;ON;;;;;N;;;;;
 1F380;RIBBON;So;0;ON;;;;;N;;;;;
 1F381;WRAPPED PRESENT;So;0;ON;;;;;N;;;;;
 1F382;BIRTHDAY CAKE;So;0;ON;;;;;N;;;;;
@@ -22872,6 +25206,18 @@
 1F391;MOON VIEWING CEREMONY;So;0;ON;;;;;N;;;;;
 1F392;SCHOOL SATCHEL;So;0;ON;;;;;N;;;;;
 1F393;GRADUATION CAP;So;0;ON;;;;;N;;;;;
+1F394;HEART WITH TIP ON THE LEFT;So;0;ON;;;;;N;;;;;
+1F395;BOUQUET OF FLOWERS;So;0;ON;;;;;N;;;;;
+1F396;MILITARY MEDAL;So;0;ON;;;;;N;;;;;
+1F397;REMINDER RIBBON;So;0;ON;;;;;N;;;;;
+1F398;MUSICAL KEYBOARD WITH JACKS;So;0;ON;;;;;N;;;;;
+1F399;STUDIO MICROPHONE;So;0;ON;;;;;N;;;;;
+1F39A;LEVEL SLIDER;So;0;ON;;;;;N;;;;;
+1F39B;CONTROL KNOBS;So;0;ON;;;;;N;;;;;
+1F39C;BEAMED ASCENDING MUSICAL NOTES;So;0;ON;;;;;N;;;;;
+1F39D;BEAMED DESCENDING MUSICAL NOTES;So;0;ON;;;;;N;;;;;
+1F39E;FILM FRAMES;So;0;ON;;;;;N;;;;;
+1F39F;ADMISSION TICKETS;So;0;ON;;;;;N;;;;;
 1F3A0;CAROUSEL HORSE;So;0;ON;;;;;N;;;;;
 1F3A1;FERRIS WHEEL;So;0;ON;;;;;N;;;;;
 1F3A2;ROLLER COASTER;So;0;ON;;;;;N;;;;;
@@ -22909,11 +25255,28 @@
 1F3C2;SNOWBOARDER;So;0;ON;;;;;N;;;;;
 1F3C3;RUNNER;So;0;ON;;;;;N;;;;;
 1F3C4;SURFER;So;0;ON;;;;;N;;;;;
+1F3C5;SPORTS MEDAL;So;0;ON;;;;;N;;;;;
 1F3C6;TROPHY;So;0;ON;;;;;N;;;;;
 1F3C7;HORSE RACING;So;0;ON;;;;;N;;;;;
 1F3C8;AMERICAN FOOTBALL;So;0;ON;;;;;N;;;;;
 1F3C9;RUGBY FOOTBALL;So;0;ON;;;;;N;;;;;
 1F3CA;SWIMMER;So;0;ON;;;;;N;;;;;
+1F3CB;WEIGHT LIFTER;So;0;ON;;;;;N;;;;;
+1F3CC;GOLFER;So;0;ON;;;;;N;;;;;
+1F3CD;RACING MOTORCYCLE;So;0;ON;;;;;N;;;;;
+1F3CE;RACING CAR;So;0;ON;;;;;N;;;;;
+1F3D4;SNOW CAPPED MOUNTAIN;So;0;ON;;;;;N;;;;;
+1F3D5;CAMPING;So;0;ON;;;;;N;;;;;
+1F3D6;BEACH WITH UMBRELLA;So;0;ON;;;;;N;;;;;
+1F3D7;BUILDING CONSTRUCTION;So;0;ON;;;;;N;;;;;
+1F3D8;HOUSE BUILDINGS;So;0;ON;;;;;N;;;;;
+1F3D9;CITYSCAPE;So;0;ON;;;;;N;;;;;
+1F3DA;DERELICT HOUSE BUILDING;So;0;ON;;;;;N;;;;;
+1F3DB;CLASSICAL BUILDING;So;0;ON;;;;;N;;;;;
+1F3DC;DESERT;So;0;ON;;;;;N;;;;;
+1F3DD;DESERT ISLAND;So;0;ON;;;;;N;;;;;
+1F3DE;NATIONAL PARK;So;0;ON;;;;;N;;;;;
+1F3DF;STADIUM;So;0;ON;;;;;N;;;;;
 1F3E0;HOUSE BUILDING;So;0;ON;;;;;N;;;;;
 1F3E1;HOUSE WITH GARDEN;So;0;ON;;;;;N;;;;;
 1F3E2;OFFICE BUILDING;So;0;ON;;;;;N;;;;;
@@ -22931,6 +25294,13 @@
 1F3EE;IZAKAYA LANTERN;So;0;ON;;;;;N;;;;;
 1F3EF;JAPANESE CASTLE;So;0;ON;;;;;N;;;;;
 1F3F0;EUROPEAN CASTLE;So;0;ON;;;;;N;;;;;
+1F3F1;WHITE PENNANT;So;0;ON;;;;;N;;;;;
+1F3F2;BLACK PENNANT;So;0;ON;;;;;N;;;;;
+1F3F3;WAVING WHITE FLAG;So;0;ON;;;;;N;;;;;
+1F3F4;WAVING BLACK FLAG;So;0;ON;;;;;N;;;;;
+1F3F5;ROSETTE;So;0;ON;;;;;N;;;;;
+1F3F6;BLACK ROSETTE;So;0;ON;;;;;N;;;;;
+1F3F7;LABEL;So;0;ON;;;;;N;;;;;
 1F400;RAT;So;0;ON;;;;;N;;;;;
 1F401;MOUSE;So;0;ON;;;;;N;;;;;
 1F402;OX;So;0;ON;;;;;N;;;;;
@@ -22994,7 +25364,9 @@
 1F43C;PANDA FACE;So;0;ON;;;;;N;;;;;
 1F43D;PIG NOSE;So;0;ON;;;;;N;;;;;
 1F43E;PAW PRINTS;So;0;ON;;;;;N;;;;;
+1F43F;CHIPMUNK;So;0;ON;;;;;N;;;;;
 1F440;EYES;So;0;ON;;;;;N;;;;;
+1F441;EYE;So;0;ON;;;;;N;;;;;
 1F442;EAR;So;0;ON;;;;;N;;;;;
 1F443;NOSE;So;0;ON;;;;;N;;;;;
 1F444;MOUTH;So;0;ON;;;;;N;;;;;
@@ -23177,10 +25549,13 @@
 1F4F5;NO MOBILE PHONES;So;0;ON;;;;;N;;;;;
 1F4F6;ANTENNA WITH BARS;So;0;ON;;;;;N;;;;;
 1F4F7;CAMERA;So;0;ON;;;;;N;;;;;
+1F4F8;CAMERA WITH FLASH;So;0;ON;;;;;N;;;;;
 1F4F9;VIDEO CAMERA;So;0;ON;;;;;N;;;;;
 1F4FA;TELEVISION;So;0;ON;;;;;N;;;;;
 1F4FB;RADIO;So;0;ON;;;;;N;;;;;
 1F4FC;VIDEOCASSETTE;So;0;ON;;;;;N;;;;;
+1F4FD;FILM PROJECTOR;So;0;ON;;;;;N;;;;;
+1F4FE;PORTABLE STEREO;So;0;ON;;;;;N;;;;;
 1F500;TWISTED RIGHTWARDS ARROWS;So;0;ON;;;;;N;;;;;
 1F501;CLOCKWISE RIGHTWARDS AND LEFTWARDS OPEN CIRCLE ARROWS;So;0;ON;;;;;N;;;;;
 1F502;CLOCKWISE RIGHTWARDS AND LEFTWARDS OPEN CIRCLE ARROWS WITH CIRCLED ONE OVERLAY;So;0;ON;;;;;N;;;;;
@@ -23243,10 +25618,19 @@
 1F53B;DOWN-POINTING RED TRIANGLE;So;0;ON;;;;;N;;;;;
 1F53C;UP-POINTING SMALL RED TRIANGLE;So;0;ON;;;;;N;;;;;
 1F53D;DOWN-POINTING SMALL RED TRIANGLE;So;0;ON;;;;;N;;;;;
+1F53E;LOWER RIGHT SHADOWED WHITE CIRCLE;So;0;ON;;;;;N;;;;;
+1F53F;UPPER RIGHT SHADOWED WHITE CIRCLE;So;0;ON;;;;;N;;;;;
 1F540;CIRCLED CROSS POMMEE;So;0;ON;;;;;N;;;;;
 1F541;CROSS POMMEE WITH HALF-CIRCLE BELOW;So;0;ON;;;;;N;;;;;
 1F542;CROSS POMMEE;So;0;ON;;;;;N;;;;;
 1F543;NOTCHED LEFT SEMICIRCLE WITH THREE DOTS;So;0;ON;;;;;N;;;;;
+1F544;NOTCHED RIGHT SEMICIRCLE WITH THREE DOTS;So;0;ON;;;;;N;;;;;
+1F545;SYMBOL FOR MARKS CHAPTER;So;0;ON;;;;;N;;;;;
+1F546;WHITE LATIN CROSS;So;0;ON;;;;;N;;;;;
+1F547;HEAVY LATIN CROSS;So;0;ON;;;;;N;;;;;
+1F548;CELTIC CROSS;So;0;ON;;;;;N;;;;;
+1F549;OM SYMBOL;So;0;ON;;;;;N;;;;;
+1F54A;DOVE OF PEACE;So;0;ON;;;;;N;;;;;
 1F550;CLOCK FACE ONE OCLOCK;So;0;ON;;;;;N;;;;;
 1F551;CLOCK FACE TWO OCLOCK;So;0;ON;;;;;N;;;;;
 1F552;CLOCK FACE THREE OCLOCK;So;0;ON;;;;;N;;;;;
@@ -23271,6 +25655,151 @@
 1F565;CLOCK FACE TEN-THIRTY;So;0;ON;;;;;N;;;;;
 1F566;CLOCK FACE ELEVEN-THIRTY;So;0;ON;;;;;N;;;;;
 1F567;CLOCK FACE TWELVE-THIRTY;So;0;ON;;;;;N;;;;;
+1F568;RIGHT SPEAKER;So;0;ON;;;;;N;;;;;
+1F569;RIGHT SPEAKER WITH ONE SOUND WAVE;So;0;ON;;;;;N;;;;;
+1F56A;RIGHT SPEAKER WITH THREE SOUND WAVES;So;0;ON;;;;;N;;;;;
+1F56B;BULLHORN;So;0;ON;;;;;N;;;;;
+1F56C;BULLHORN WITH SOUND WAVES;So;0;ON;;;;;N;;;;;
+1F56D;RINGING BELL;So;0;ON;;;;;N;;;;;
+1F56E;BOOK;So;0;ON;;;;;N;;;;;
+1F56F;CANDLE;So;0;ON;;;;;N;;;;;
+1F570;MANTELPIECE CLOCK;So;0;ON;;;;;N;;;;;
+1F571;BLACK SKULL AND CROSSBONES;So;0;ON;;;;;N;;;;;
+1F572;NO PIRACY;So;0;ON;;;;;N;;;;;
+1F573;HOLE;So;0;ON;;;;;N;;;;;
+1F574;MAN IN BUSINESS SUIT LEVITATING;So;0;ON;;;;;N;;;;;
+1F575;SLEUTH OR SPY;So;0;ON;;;;;N;;;;;
+1F576;DARK SUNGLASSES;So;0;ON;;;;;N;;;;;
+1F577;SPIDER;So;0;ON;;;;;N;;;;;
+1F578;SPIDER WEB;So;0;ON;;;;;N;;;;;
+1F579;JOYSTICK;So;0;ON;;;;;N;;;;;
+1F57B;LEFT HAND TELEPHONE RECEIVER;So;0;ON;;;;;N;;;;;
+1F57C;TELEPHONE RECEIVER WITH PAGE;So;0;ON;;;;;N;;;;;
+1F57D;RIGHT HAND TELEPHONE RECEIVER;So;0;ON;;;;;N;;;;;
+1F57E;WHITE TOUCHTONE TELEPHONE;So;0;ON;;;;;N;;;;;
+1F57F;BLACK TOUCHTONE TELEPHONE;So;0;ON;;;;;N;;;;;
+1F580;TELEPHONE ON TOP OF MODEM;So;0;ON;;;;;N;;;;;
+1F581;CLAMSHELL MOBILE PHONE;So;0;ON;;;;;N;;;;;
+1F582;BACK OF ENVELOPE;So;0;ON;;;;;N;;;;;
+1F583;STAMPED ENVELOPE;So;0;ON;;;;;N;;;;;
+1F584;ENVELOPE WITH LIGHTNING;So;0;ON;;;;;N;;;;;
+1F585;FLYING ENVELOPE;So;0;ON;;;;;N;;;;;
+1F586;PEN OVER STAMPED ENVELOPE;So;0;ON;;;;;N;;;;;
+1F587;LINKED PAPERCLIPS;So;0;ON;;;;;N;;;;;
+1F588;BLACK PUSHPIN;So;0;ON;;;;;N;;;;;
+1F589;LOWER LEFT PENCIL;So;0;ON;;;;;N;;;;;
+1F58A;LOWER LEFT BALLPOINT PEN;So;0;ON;;;;;N;;;;;
+1F58B;LOWER LEFT FOUNTAIN PEN;So;0;ON;;;;;N;;;;;
+1F58C;LOWER LEFT PAINTBRUSH;So;0;ON;;;;;N;;;;;
+1F58D;LOWER LEFT CRAYON;So;0;ON;;;;;N;;;;;
+1F58E;LEFT WRITING HAND;So;0;ON;;;;;N;;;;;
+1F58F;TURNED OK HAND SIGN;So;0;ON;;;;;N;;;;;
+1F590;RAISED HAND WITH FINGERS SPLAYED;So;0;ON;;;;;N;;;;;
+1F591;REVERSED RAISED HAND WITH FINGERS SPLAYED;So;0;ON;;;;;N;;;;;
+1F592;REVERSED THUMBS UP SIGN;So;0;ON;;;;;N;;;;;
+1F593;REVERSED THUMBS DOWN SIGN;So;0;ON;;;;;N;;;;;
+1F594;REVERSED VICTORY HAND;So;0;ON;;;;;N;;;;;
+1F595;REVERSED HAND WITH MIDDLE FINGER EXTENDED;So;0;ON;;;;;N;;;;;
+1F596;RAISED HAND WITH PART BETWEEN MIDDLE AND RING FINGERS;So;0;ON;;;;;N;;;;;
+1F597;WHITE DOWN POINTING LEFT HAND INDEX;So;0;ON;;;;;N;;;;;
+1F598;SIDEWAYS WHITE LEFT POINTING INDEX;So;0;ON;;;;;N;;;;;
+1F599;SIDEWAYS WHITE RIGHT POINTING INDEX;So;0;ON;;;;;N;;;;;
+1F59A;SIDEWAYS BLACK LEFT POINTING INDEX;So;0;ON;;;;;N;;;;;
+1F59B;SIDEWAYS BLACK RIGHT POINTING INDEX;So;0;ON;;;;;N;;;;;
+1F59C;BLACK LEFT POINTING BACKHAND INDEX;So;0;ON;;;;;N;;;;;
+1F59D;BLACK RIGHT POINTING BACKHAND INDEX;So;0;ON;;;;;N;;;;;
+1F59E;SIDEWAYS WHITE UP POINTING INDEX;So;0;ON;;;;;N;;;;;
+1F59F;SIDEWAYS WHITE DOWN POINTING INDEX;So;0;ON;;;;;N;;;;;
+1F5A0;SIDEWAYS BLACK UP POINTING INDEX;So;0;ON;;;;;N;;;;;
+1F5A1;SIDEWAYS BLACK DOWN POINTING INDEX;So;0;ON;;;;;N;;;;;
+1F5A2;BLACK UP POINTING BACKHAND INDEX;So;0;ON;;;;;N;;;;;
+1F5A3;BLACK DOWN POINTING BACKHAND INDEX;So;0;ON;;;;;N;;;;;
+1F5A5;DESKTOP COMPUTER;So;0;ON;;;;;N;;;;;
+1F5A6;KEYBOARD AND MOUSE;So;0;ON;;;;;N;;;;;
+1F5A7;THREE NETWORKED COMPUTERS;So;0;ON;;;;;N;;;;;
+1F5A8;PRINTER;So;0;ON;;;;;N;;;;;
+1F5A9;POCKET CALCULATOR;So;0;ON;;;;;N;;;;;
+1F5AA;BLACK HARD SHELL FLOPPY DISK;So;0;ON;;;;;N;;;;;
+1F5AB;WHITE HARD SHELL FLOPPY DISK;So;0;ON;;;;;N;;;;;
+1F5AC;SOFT SHELL FLOPPY DISK;So;0;ON;;;;;N;;;;;
+1F5AD;TAPE CARTRIDGE;So;0;ON;;;;;N;;;;;
+1F5AE;WIRED KEYBOARD;So;0;ON;;;;;N;;;;;
+1F5AF;ONE BUTTON MOUSE;So;0;ON;;;;;N;;;;;
+1F5B0;TWO BUTTON MOUSE;So;0;ON;;;;;N;;;;;
+1F5B1;THREE BUTTON MOUSE;So;0;ON;;;;;N;;;;;
+1F5B2;TRACKBALL;So;0;ON;;;;;N;;;;;
+1F5B3;OLD PERSONAL COMPUTER;So;0;ON;;;;;N;;;;;
+1F5B4;HARD DISK;So;0;ON;;;;;N;;;;;
+1F5B5;SCREEN;So;0;ON;;;;;N;;;;;
+1F5B6;PRINTER ICON;So;0;ON;;;;;N;;;;;
+1F5B7;FAX ICON;So;0;ON;;;;;N;;;;;
+1F5B8;OPTICAL DISC ICON;So;0;ON;;;;;N;;;;;
+1F5B9;DOCUMENT WITH TEXT;So;0;ON;;;;;N;;;;;
+1F5BA;DOCUMENT WITH TEXT AND PICTURE;So;0;ON;;;;;N;;;;;
+1F5BB;DOCUMENT WITH PICTURE;So;0;ON;;;;;N;;;;;
+1F5BC;FRAME WITH PICTURE;So;0;ON;;;;;N;;;;;
+1F5BD;FRAME WITH TILES;So;0;ON;;;;;N;;;;;
+1F5BE;FRAME WITH AN X;So;0;ON;;;;;N;;;;;
+1F5BF;BLACK FOLDER;So;0;ON;;;;;N;;;;;
+1F5C0;FOLDER;So;0;ON;;;;;N;;;;;
+1F5C1;OPEN FOLDER;So;0;ON;;;;;N;;;;;
+1F5C2;CARD INDEX DIVIDERS;So;0;ON;;;;;N;;;;;
+1F5C3;CARD FILE BOX;So;0;ON;;;;;N;;;;;
+1F5C4;FILE CABINET;So;0;ON;;;;;N;;;;;
+1F5C5;EMPTY NOTE;So;0;ON;;;;;N;;;;;
+1F5C6;EMPTY NOTE PAGE;So;0;ON;;;;;N;;;;;
+1F5C7;EMPTY NOTE PAD;So;0;ON;;;;;N;;;;;
+1F5C8;NOTE;So;0;ON;;;;;N;;;;;
+1F5C9;NOTE PAGE;So;0;ON;;;;;N;;;;;
+1F5CA;NOTE PAD;So;0;ON;;;;;N;;;;;
+1F5CB;EMPTY DOCUMENT;So;0;ON;;;;;N;;;;;
+1F5CC;EMPTY PAGE;So;0;ON;;;;;N;;;;;
+1F5CD;EMPTY PAGES;So;0;ON;;;;;N;;;;;
+1F5CE;DOCUMENT;So;0;ON;;;;;N;;;;;
+1F5CF;PAGE;So;0;ON;;;;;N;;;;;
+1F5D0;PAGES;So;0;ON;;;;;N;;;;;
+1F5D1;WASTEBASKET;So;0;ON;;;;;N;;;;;
+1F5D2;SPIRAL NOTE PAD;So;0;ON;;;;;N;;;;;
+1F5D3;SPIRAL CALENDAR PAD;So;0;ON;;;;;N;;;;;
+1F5D4;DESKTOP WINDOW;So;0;ON;;;;;N;;;;;
+1F5D5;MINIMIZE;So;0;ON;;;;;N;;;;;
+1F5D6;MAXIMIZE;So;0;ON;;;;;N;;;;;
+1F5D7;OVERLAP;So;0;ON;;;;;N;;;;;
+1F5D8;CLOCKWISE RIGHT AND LEFT SEMICIRCLE ARROWS;So;0;ON;;;;;N;;;;;
+1F5D9;CANCELLATION X;So;0;ON;;;;;N;;;;;
+1F5DA;INCREASE FONT SIZE SYMBOL;So;0;ON;;;;;N;;;;;
+1F5DB;DECREASE FONT SIZE SYMBOL;So;0;ON;;;;;N;;;;;
+1F5DC;COMPRESSION;So;0;ON;;;;;N;;;;;
+1F5DD;OLD KEY;So;0;ON;;;;;N;;;;;
+1F5DE;ROLLED-UP NEWSPAPER;So;0;ON;;;;;N;;;;;
+1F5DF;PAGE WITH CIRCLED TEXT;So;0;ON;;;;;N;;;;;
+1F5E0;STOCK CHART;So;0;ON;;;;;N;;;;;
+1F5E1;DAGGER KNIFE;So;0;ON;;;;;N;;;;;
+1F5E2;LIPS;So;0;ON;;;;;N;;;;;
+1F5E3;SPEAKING HEAD IN SILHOUETTE;So;0;ON;;;;;N;;;;;
+1F5E4;THREE RAYS ABOVE;So;0;ON;;;;;N;;;;;
+1F5E5;THREE RAYS BELOW;So;0;ON;;;;;N;;;;;
+1F5E6;THREE RAYS LEFT;So;0;ON;;;;;N;;;;;
+1F5E7;THREE RAYS RIGHT;So;0;ON;;;;;N;;;;;
+1F5E8;LEFT SPEECH BUBBLE;So;0;ON;;;;;N;;;;;
+1F5E9;RIGHT SPEECH BUBBLE;So;0;ON;;;;;N;;;;;
+1F5EA;TWO SPEECH BUBBLES;So;0;ON;;;;;N;;;;;
+1F5EB;THREE SPEECH BUBBLES;So;0;ON;;;;;N;;;;;
+1F5EC;LEFT THOUGHT BUBBLE;So;0;ON;;;;;N;;;;;
+1F5ED;RIGHT THOUGHT BUBBLE;So;0;ON;;;;;N;;;;;
+1F5EE;LEFT ANGER BUBBLE;So;0;ON;;;;;N;;;;;
+1F5EF;RIGHT ANGER BUBBLE;So;0;ON;;;;;N;;;;;
+1F5F0;MOOD BUBBLE;So;0;ON;;;;;N;;;;;
+1F5F1;LIGHTNING MOOD BUBBLE;So;0;ON;;;;;N;;;;;
+1F5F2;LIGHTNING MOOD;So;0;ON;;;;;N;;;;;
+1F5F3;BALLOT BOX WITH BALLOT;So;0;ON;;;;;N;;;;;
+1F5F4;BALLOT SCRIPT X;So;0;ON;;;;;N;;;;;
+1F5F5;BALLOT BOX WITH SCRIPT X;So;0;ON;;;;;N;;;;;
+1F5F6;BALLOT BOLD SCRIPT X;So;0;ON;;;;;N;;;;;
+1F5F7;BALLOT BOX WITH BOLD SCRIPT X;So;0;ON;;;;;N;;;;;
+1F5F8;LIGHT CHECK MARK;So;0;ON;;;;;N;;;;;
+1F5F9;BALLOT BOX WITH BOLD CHECK;So;0;ON;;;;;N;;;;;
+1F5FA;WORLD MAP;So;0;ON;;;;;N;;;;;
 1F5FB;MOUNT FUJI;So;0;ON;;;;;N;;;;;
 1F5FC;TOKYO TOWER;So;0;ON;;;;;N;;;;;
 1F5FD;STATUE OF LIBERTY;So;0;ON;;;;;N;;;;;
@@ -23341,6 +25870,8 @@
 1F63E;POUTING CAT FACE;So;0;ON;;;;;N;;;;;
 1F63F;CRYING CAT FACE;So;0;ON;;;;;N;;;;;
 1F640;WEARY CAT FACE;So;0;ON;;;;;N;;;;;
+1F641;SLIGHTLY FROWNING FACE;So;0;ON;;;;;N;;;;;
+1F642;SLIGHTLY SMILING FACE;So;0;ON;;;;;N;;;;;
 1F645;FACE WITH NO GOOD GESTURE;So;0;ON;;;;;N;;;;;
 1F646;FACE WITH OK GESTURE;So;0;ON;;;;;N;;;;;
 1F647;PERSON BOWING DEEPLY;So;0;ON;;;;;N;;;;;
@@ -23352,6 +25883,54 @@
 1F64D;PERSON FROWNING;So;0;ON;;;;;N;;;;;
 1F64E;PERSON WITH POUTING FACE;So;0;ON;;;;;N;;;;;
 1F64F;PERSON WITH FOLDED HANDS;So;0;ON;;;;;N;;;;;
+1F650;NORTH WEST POINTING LEAF;So;0;ON;;;;;N;;;;;
+1F651;SOUTH WEST POINTING LEAF;So;0;ON;;;;;N;;;;;
+1F652;NORTH EAST POINTING LEAF;So;0;ON;;;;;N;;;;;
+1F653;SOUTH EAST POINTING LEAF;So;0;ON;;;;;N;;;;;
+1F654;TURNED NORTH WEST POINTING LEAF;So;0;ON;;;;;N;;;;;
+1F655;TURNED SOUTH WEST POINTING LEAF;So;0;ON;;;;;N;;;;;
+1F656;TURNED NORTH EAST POINTING LEAF;So;0;ON;;;;;N;;;;;
+1F657;TURNED SOUTH EAST POINTING LEAF;So;0;ON;;;;;N;;;;;
+1F658;NORTH WEST POINTING VINE LEAF;So;0;ON;;;;;N;;;;;
+1F659;SOUTH WEST POINTING VINE LEAF;So;0;ON;;;;;N;;;;;
+1F65A;NORTH EAST POINTING VINE LEAF;So;0;ON;;;;;N;;;;;
+1F65B;SOUTH EAST POINTING VINE LEAF;So;0;ON;;;;;N;;;;;
+1F65C;HEAVY NORTH WEST POINTING VINE LEAF;So;0;ON;;;;;N;;;;;
+1F65D;HEAVY SOUTH WEST POINTING VINE LEAF;So;0;ON;;;;;N;;;;;
+1F65E;HEAVY NORTH EAST POINTING VINE LEAF;So;0;ON;;;;;N;;;;;
+1F65F;HEAVY SOUTH EAST POINTING VINE LEAF;So;0;ON;;;;;N;;;;;
+1F660;NORTH WEST POINTING BUD;So;0;ON;;;;;N;;;;;
+1F661;SOUTH WEST POINTING BUD;So;0;ON;;;;;N;;;;;
+1F662;NORTH EAST POINTING BUD;So;0;ON;;;;;N;;;;;
+1F663;SOUTH EAST POINTING BUD;So;0;ON;;;;;N;;;;;
+1F664;HEAVY NORTH WEST POINTING BUD;So;0;ON;;;;;N;;;;;
+1F665;HEAVY SOUTH WEST POINTING BUD;So;0;ON;;;;;N;;;;;
+1F666;HEAVY NORTH EAST POINTING BUD;So;0;ON;;;;;N;;;;;
+1F667;HEAVY SOUTH EAST POINTING BUD;So;0;ON;;;;;N;;;;;
+1F668;HOLLOW QUILT SQUARE ORNAMENT;So;0;ON;;;;;N;;;;;
+1F669;HOLLOW QUILT SQUARE ORNAMENT IN BLACK SQUARE;So;0;ON;;;;;N;;;;;
+1F66A;SOLID QUILT SQUARE ORNAMENT;So;0;ON;;;;;N;;;;;
+1F66B;SOLID QUILT SQUARE ORNAMENT IN BLACK SQUARE;So;0;ON;;;;;N;;;;;
+1F66C;LEFTWARDS ROCKET;So;0;ON;;;;;N;;;;;
+1F66D;UPWARDS ROCKET;So;0;ON;;;;;N;;;;;
+1F66E;RIGHTWARDS ROCKET;So;0;ON;;;;;N;;;;;
+1F66F;DOWNWARDS ROCKET;So;0;ON;;;;;N;;;;;
+1F670;SCRIPT LIGATURE ET ORNAMENT;So;0;ON;;;;;N;;;;;
+1F671;HEAVY SCRIPT LIGATURE ET ORNAMENT;So;0;ON;;;;;N;;;;;
+1F672;LIGATURE OPEN ET ORNAMENT;So;0;ON;;;;;N;;;;;
+1F673;HEAVY LIGATURE OPEN ET ORNAMENT;So;0;ON;;;;;N;;;;;
+1F674;HEAVY AMPERSAND ORNAMENT;So;0;ON;;;;;N;;;;;
+1F675;SWASH AMPERSAND ORNAMENT;So;0;ON;;;;;N;;;;;
+1F676;SANS-SERIF HEAVY DOUBLE TURNED COMMA QUOTATION MARK ORNAMENT;So;0;ON;;;;;N;;;;;
+1F677;SANS-SERIF HEAVY DOUBLE COMMA QUOTATION MARK ORNAMENT;So;0;ON;;;;;N;;;;;
+1F678;SANS-SERIF HEAVY LOW DOUBLE COMMA QUOTATION MARK ORNAMENT;So;0;ON;;;;;N;;;;;
+1F679;HEAVY INTERROBANG ORNAMENT;So;0;ON;;;;;N;;;;;
+1F67A;SANS-SERIF INTERROBANG ORNAMENT;So;0;ON;;;;;N;;;;;
+1F67B;HEAVY SANS-SERIF INTERROBANG ORNAMENT;So;0;ON;;;;;N;;;;;
+1F67C;VERY HEAVY SOLIDUS;So;0;ON;;;;;N;;;;;
+1F67D;VERY HEAVY REVERSE SOLIDUS;So;0;ON;;;;;N;;;;;
+1F67E;CHECKER BOARD;So;0;ON;;;;;N;;;;;
+1F67F;REVERSE CHECKER BOARD;So;0;ON;;;;;N;;;;;
 1F680;ROCKET;So;0;ON;;;;;N;;;;;
 1F681;HELICOPTER;So;0;ON;;;;;N;;;;;
 1F682;STEAM LOCOMOTIVE;So;0;ON;;;;;N;;;;;
@@ -23422,6 +26001,33 @@
 1F6C3;CUSTOMS;So;0;ON;;;;;N;;;;;
 1F6C4;BAGGAGE CLAIM;So;0;ON;;;;;N;;;;;
 1F6C5;LEFT LUGGAGE;So;0;ON;;;;;N;;;;;
+1F6C6;TRIANGLE WITH ROUNDED CORNERS;So;0;ON;;;;;N;;;;;
+1F6C7;PROHIBITED SIGN;So;0;ON;;;;;N;;;;;
+1F6C8;CIRCLED INFORMATION SOURCE;So;0;ON;;;;;N;;;;;
+1F6C9;BOYS SYMBOL;So;0;ON;;;;;N;;;;;
+1F6CA;GIRLS SYMBOL;So;0;ON;;;;;N;;;;;
+1F6CB;COUCH AND LAMP;So;0;ON;;;;;N;;;;;
+1F6CC;SLEEPING ACCOMMODATION;So;0;ON;;;;;N;;;;;
+1F6CD;SHOPPING BAGS;So;0;ON;;;;;N;;;;;
+1F6CE;BELLHOP BELL;So;0;ON;;;;;N;;;;;
+1F6CF;BED;So;0;ON;;;;;N;;;;;
+1F6E0;HAMMER AND WRENCH;So;0;ON;;;;;N;;;;;
+1F6E1;SHIELD;So;0;ON;;;;;N;;;;;
+1F6E2;OIL DRUM;So;0;ON;;;;;N;;;;;
+1F6E3;MOTORWAY;So;0;ON;;;;;N;;;;;
+1F6E4;RAILWAY TRACK;So;0;ON;;;;;N;;;;;
+1F6E5;MOTOR BOAT;So;0;ON;;;;;N;;;;;
+1F6E6;UP-POINTING MILITARY AIRPLANE;So;0;ON;;;;;N;;;;;
+1F6E7;UP-POINTING AIRPLANE;So;0;ON;;;;;N;;;;;
+1F6E8;UP-POINTING SMALL AIRPLANE;So;0;ON;;;;;N;;;;;
+1F6E9;SMALL AIRPLANE;So;0;ON;;;;;N;;;;;
+1F6EA;NORTHEAST-POINTING AIRPLANE;So;0;ON;;;;;N;;;;;
+1F6EB;AIRPLANE DEPARTURE;So;0;ON;;;;;N;;;;;
+1F6EC;AIRPLANE ARRIVING;So;0;ON;;;;;N;;;;;
+1F6F0;SATELLITE;So;0;ON;;;;;N;;;;;
+1F6F1;ONCOMING FIRE ENGINE;So;0;ON;;;;;N;;;;;
+1F6F2;DIESEL LOCOMOTIVE;So;0;ON;;;;;N;;;;;
+1F6F3;PASSENGER SHIP;So;0;ON;;;;;N;;;;;
 1F700;ALCHEMICAL SYMBOL FOR QUINTESSENCE;So;0;ON;;;;;N;;;;;
 1F701;ALCHEMICAL SYMBOL FOR AIR;So;0;ON;;;;;N;;;;;
 1F702;ALCHEMICAL SYMBOL FOR FIRE;So;0;ON;;;;;N;;;;;
@@ -23538,6 +26144,239 @@
 1F771;ALCHEMICAL SYMBOL FOR MONTH;So;0;ON;;;;;N;;;;;
 1F772;ALCHEMICAL SYMBOL FOR HALF DRAM;So;0;ON;;;;;N;;;;;
 1F773;ALCHEMICAL SYMBOL FOR HALF OUNCE;So;0;ON;;;;;N;;;;;
+1F780;BLACK LEFT-POINTING ISOSCELES RIGHT TRIANGLE;So;0;ON;;;;;N;;;;;
+1F781;BLACK UP-POINTING ISOSCELES RIGHT TRIANGLE;So;0;ON;;;;;N;;;;;
+1F782;BLACK RIGHT-POINTING ISOSCELES RIGHT TRIANGLE;So;0;ON;;;;;N;;;;;
+1F783;BLACK DOWN-POINTING ISOSCELES RIGHT TRIANGLE;So;0;ON;;;;;N;;;;;
+1F784;BLACK SLIGHTLY SMALL CIRCLE;So;0;ON;;;;;N;;;;;
+1F785;MEDIUM BOLD WHITE CIRCLE;So;0;ON;;;;;N;;;;;
+1F786;BOLD WHITE CIRCLE;So;0;ON;;;;;N;;;;;
+1F787;HEAVY WHITE CIRCLE;So;0;ON;;;;;N;;;;;
+1F788;VERY HEAVY WHITE CIRCLE;So;0;ON;;;;;N;;;;;
+1F789;EXTREMELY HEAVY WHITE CIRCLE;So;0;ON;;;;;N;;;;;
+1F78A;WHITE CIRCLE CONTAINING BLACK SMALL CIRCLE;So;0;ON;;;;;N;;;;;
+1F78B;ROUND TARGET;So;0;ON;;;;;N;;;;;
+1F78C;BLACK TINY SQUARE;So;0;ON;;;;;N;;;;;
+1F78D;BLACK SLIGHTLY SMALL SQUARE;So;0;ON;;;;;N;;;;;
+1F78E;LIGHT WHITE SQUARE;So;0;ON;;;;;N;;;;;
+1F78F;MEDIUM WHITE SQUARE;So;0;ON;;;;;N;;;;;
+1F790;BOLD WHITE SQUARE;So;0;ON;;;;;N;;;;;
+1F791;HEAVY WHITE SQUARE;So;0;ON;;;;;N;;;;;
+1F792;VERY HEAVY WHITE SQUARE;So;0;ON;;;;;N;;;;;
+1F793;EXTREMELY HEAVY WHITE SQUARE;So;0;ON;;;;;N;;;;;
+1F794;WHITE SQUARE CONTAINING BLACK VERY SMALL SQUARE;So;0;ON;;;;;N;;;;;
+1F795;WHITE SQUARE CONTAINING BLACK MEDIUM SQUARE;So;0;ON;;;;;N;;;;;
+1F796;SQUARE TARGET;So;0;ON;;;;;N;;;;;
+1F797;BLACK TINY DIAMOND;So;0;ON;;;;;N;;;;;
+1F798;BLACK VERY SMALL DIAMOND;So;0;ON;;;;;N;;;;;
+1F799;BLACK MEDIUM SMALL DIAMOND;So;0;ON;;;;;N;;;;;
+1F79A;WHITE DIAMOND CONTAINING BLACK VERY SMALL DIAMOND;So;0;ON;;;;;N;;;;;
+1F79B;WHITE DIAMOND CONTAINING BLACK MEDIUM DIAMOND;So;0;ON;;;;;N;;;;;
+1F79C;DIAMOND TARGET;So;0;ON;;;;;N;;;;;
+1F79D;BLACK TINY LOZENGE;So;0;ON;;;;;N;;;;;
+1F79E;BLACK VERY SMALL LOZENGE;So;0;ON;;;;;N;;;;;
+1F79F;BLACK MEDIUM SMALL LOZENGE;So;0;ON;;;;;N;;;;;
+1F7A0;WHITE LOZENGE CONTAINING BLACK SMALL LOZENGE;So;0;ON;;;;;N;;;;;
+1F7A1;THIN GREEK CROSS;So;0;ON;;;;;N;;;;;
+1F7A2;LIGHT GREEK CROSS;So;0;ON;;;;;N;;;;;
+1F7A3;MEDIUM GREEK CROSS;So;0;ON;;;;;N;;;;;
+1F7A4;BOLD GREEK CROSS;So;0;ON;;;;;N;;;;;
+1F7A5;VERY BOLD GREEK CROSS;So;0;ON;;;;;N;;;;;
+1F7A6;VERY HEAVY GREEK CROSS;So;0;ON;;;;;N;;;;;
+1F7A7;EXTREMELY HEAVY GREEK CROSS;So;0;ON;;;;;N;;;;;
+1F7A8;THIN SALTIRE;So;0;ON;;;;;N;;;;;
+1F7A9;LIGHT SALTIRE;So;0;ON;;;;;N;;;;;
+1F7AA;MEDIUM SALTIRE;So;0;ON;;;;;N;;;;;
+1F7AB;BOLD SALTIRE;So;0;ON;;;;;N;;;;;
+1F7AC;HEAVY SALTIRE;So;0;ON;;;;;N;;;;;
+1F7AD;VERY HEAVY SALTIRE;So;0;ON;;;;;N;;;;;
+1F7AE;EXTREMELY HEAVY SALTIRE;So;0;ON;;;;;N;;;;;
+1F7AF;LIGHT FIVE SPOKED ASTERISK;So;0;ON;;;;;N;;;;;
+1F7B0;MEDIUM FIVE SPOKED ASTERISK;So;0;ON;;;;;N;;;;;
+1F7B1;BOLD FIVE SPOKED ASTERISK;So;0;ON;;;;;N;;;;;
+1F7B2;HEAVY FIVE SPOKED ASTERISK;So;0;ON;;;;;N;;;;;
+1F7B3;VERY HEAVY FIVE SPOKED ASTERISK;So;0;ON;;;;;N;;;;;
+1F7B4;EXTREMELY HEAVY FIVE SPOKED ASTERISK;So;0;ON;;;;;N;;;;;
+1F7B5;LIGHT SIX SPOKED ASTERISK;So;0;ON;;;;;N;;;;;
+1F7B6;MEDIUM SIX SPOKED ASTERISK;So;0;ON;;;;;N;;;;;
+1F7B7;BOLD SIX SPOKED ASTERISK;So;0;ON;;;;;N;;;;;
+1F7B8;HEAVY SIX SPOKED ASTERISK;So;0;ON;;;;;N;;;;;
+1F7B9;VERY HEAVY SIX SPOKED ASTERISK;So;0;ON;;;;;N;;;;;
+1F7BA;EXTREMELY HEAVY SIX SPOKED ASTERISK;So;0;ON;;;;;N;;;;;
+1F7BB;LIGHT EIGHT SPOKED ASTERISK;So;0;ON;;;;;N;;;;;
+1F7BC;MEDIUM EIGHT SPOKED ASTERISK;So;0;ON;;;;;N;;;;;
+1F7BD;BOLD EIGHT SPOKED ASTERISK;So;0;ON;;;;;N;;;;;
+1F7BE;HEAVY EIGHT SPOKED ASTERISK;So;0;ON;;;;;N;;;;;
+1F7BF;VERY HEAVY EIGHT SPOKED ASTERISK;So;0;ON;;;;;N;;;;;
+1F7C0;LIGHT THREE POINTED BLACK STAR;So;0;ON;;;;;N;;;;;
+1F7C1;MEDIUM THREE POINTED BLACK STAR;So;0;ON;;;;;N;;;;;
+1F7C2;THREE POINTED BLACK STAR;So;0;ON;;;;;N;;;;;
+1F7C3;MEDIUM THREE POINTED PINWHEEL STAR;So;0;ON;;;;;N;;;;;
+1F7C4;LIGHT FOUR POINTED BLACK STAR;So;0;ON;;;;;N;;;;;
+1F7C5;MEDIUM FOUR POINTED BLACK STAR;So;0;ON;;;;;N;;;;;
+1F7C6;FOUR POINTED BLACK STAR;So;0;ON;;;;;N;;;;;
+1F7C7;MEDIUM FOUR POINTED PINWHEEL STAR;So;0;ON;;;;;N;;;;;
+1F7C8;REVERSE LIGHT FOUR POINTED PINWHEEL STAR;So;0;ON;;;;;N;;;;;
+1F7C9;LIGHT FIVE POINTED BLACK STAR;So;0;ON;;;;;N;;;;;
+1F7CA;HEAVY FIVE POINTED BLACK STAR;So;0;ON;;;;;N;;;;;
+1F7CB;MEDIUM SIX POINTED BLACK STAR;So;0;ON;;;;;N;;;;;
+1F7CC;HEAVY SIX POINTED BLACK STAR;So;0;ON;;;;;N;;;;;
+1F7CD;SIX POINTED PINWHEEL STAR;So;0;ON;;;;;N;;;;;
+1F7CE;MEDIUM EIGHT POINTED BLACK STAR;So;0;ON;;;;;N;;;;;
+1F7CF;HEAVY EIGHT POINTED BLACK STAR;So;0;ON;;;;;N;;;;;
+1F7D0;VERY HEAVY EIGHT POINTED BLACK STAR;So;0;ON;;;;;N;;;;;
+1F7D1;HEAVY EIGHT POINTED PINWHEEL STAR;So;0;ON;;;;;N;;;;;
+1F7D2;LIGHT TWELVE POINTED BLACK STAR;So;0;ON;;;;;N;;;;;
+1F7D3;HEAVY TWELVE POINTED BLACK STAR;So;0;ON;;;;;N;;;;;
+1F7D4;HEAVY TWELVE POINTED PINWHEEL STAR;So;0;ON;;;;;N;;;;;
+1F800;LEFTWARDS ARROW WITH SMALL TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F801;UPWARDS ARROW WITH SMALL TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F802;RIGHTWARDS ARROW WITH SMALL TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F803;DOWNWARDS ARROW WITH SMALL TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F804;LEFTWARDS ARROW WITH MEDIUM TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F805;UPWARDS ARROW WITH MEDIUM TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F806;RIGHTWARDS ARROW WITH MEDIUM TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F807;DOWNWARDS ARROW WITH MEDIUM TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F808;LEFTWARDS ARROW WITH LARGE TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F809;UPWARDS ARROW WITH LARGE TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F80A;RIGHTWARDS ARROW WITH LARGE TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F80B;DOWNWARDS ARROW WITH LARGE TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F810;LEFTWARDS ARROW WITH SMALL EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F811;UPWARDS ARROW WITH SMALL EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F812;RIGHTWARDS ARROW WITH SMALL EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F813;DOWNWARDS ARROW WITH SMALL EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F814;LEFTWARDS ARROW WITH EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F815;UPWARDS ARROW WITH EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F816;RIGHTWARDS ARROW WITH EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F817;DOWNWARDS ARROW WITH EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F818;HEAVY LEFTWARDS ARROW WITH EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F819;HEAVY UPWARDS ARROW WITH EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F81A;HEAVY RIGHTWARDS ARROW WITH EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F81B;HEAVY DOWNWARDS ARROW WITH EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F81C;HEAVY LEFTWARDS ARROW WITH LARGE EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F81D;HEAVY UPWARDS ARROW WITH LARGE EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F81E;HEAVY RIGHTWARDS ARROW WITH LARGE EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F81F;HEAVY DOWNWARDS ARROW WITH LARGE EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F820;LEFTWARDS TRIANGLE-HEADED ARROW WITH NARROW SHAFT;So;0;ON;;;;;N;;;;;
+1F821;UPWARDS TRIANGLE-HEADED ARROW WITH NARROW SHAFT;So;0;ON;;;;;N;;;;;
+1F822;RIGHTWARDS TRIANGLE-HEADED ARROW WITH NARROW SHAFT;So;0;ON;;;;;N;;;;;
+1F823;DOWNWARDS TRIANGLE-HEADED ARROW WITH NARROW SHAFT;So;0;ON;;;;;N;;;;;
+1F824;LEFTWARDS TRIANGLE-HEADED ARROW WITH MEDIUM SHAFT;So;0;ON;;;;;N;;;;;
+1F825;UPWARDS TRIANGLE-HEADED ARROW WITH MEDIUM SHAFT;So;0;ON;;;;;N;;;;;
+1F826;RIGHTWARDS TRIANGLE-HEADED ARROW WITH MEDIUM SHAFT;So;0;ON;;;;;N;;;;;
+1F827;DOWNWARDS TRIANGLE-HEADED ARROW WITH MEDIUM SHAFT;So;0;ON;;;;;N;;;;;
+1F828;LEFTWARDS TRIANGLE-HEADED ARROW WITH BOLD SHAFT;So;0;ON;;;;;N;;;;;
+1F829;UPWARDS TRIANGLE-HEADED ARROW WITH BOLD SHAFT;So;0;ON;;;;;N;;;;;
+1F82A;RIGHTWARDS TRIANGLE-HEADED ARROW WITH BOLD SHAFT;So;0;ON;;;;;N;;;;;
+1F82B;DOWNWARDS TRIANGLE-HEADED ARROW WITH BOLD SHAFT;So;0;ON;;;;;N;;;;;
+1F82C;LEFTWARDS TRIANGLE-HEADED ARROW WITH HEAVY SHAFT;So;0;ON;;;;;N;;;;;
+1F82D;UPWARDS TRIANGLE-HEADED ARROW WITH HEAVY SHAFT;So;0;ON;;;;;N;;;;;
+1F82E;RIGHTWARDS TRIANGLE-HEADED ARROW WITH HEAVY SHAFT;So;0;ON;;;;;N;;;;;
+1F82F;DOWNWARDS TRIANGLE-HEADED ARROW WITH HEAVY SHAFT;So;0;ON;;;;;N;;;;;
+1F830;LEFTWARDS TRIANGLE-HEADED ARROW WITH VERY HEAVY SHAFT;So;0;ON;;;;;N;;;;;
+1F831;UPWARDS TRIANGLE-HEADED ARROW WITH VERY HEAVY SHAFT;So;0;ON;;;;;N;;;;;
+1F832;RIGHTWARDS TRIANGLE-HEADED ARROW WITH VERY HEAVY SHAFT;So;0;ON;;;;;N;;;;;
+1F833;DOWNWARDS TRIANGLE-HEADED ARROW WITH VERY HEAVY SHAFT;So;0;ON;;;;;N;;;;;
+1F834;LEFTWARDS FINGER-POST ARROW;So;0;ON;;;;;N;;;;;
+1F835;UPWARDS FINGER-POST ARROW;So;0;ON;;;;;N;;;;;
+1F836;RIGHTWARDS FINGER-POST ARROW;So;0;ON;;;;;N;;;;;
+1F837;DOWNWARDS FINGER-POST ARROW;So;0;ON;;;;;N;;;;;
+1F838;LEFTWARDS SQUARED ARROW;So;0;ON;;;;;N;;;;;
+1F839;UPWARDS SQUARED ARROW;So;0;ON;;;;;N;;;;;
+1F83A;RIGHTWARDS SQUARED ARROW;So;0;ON;;;;;N;;;;;
+1F83B;DOWNWARDS SQUARED ARROW;So;0;ON;;;;;N;;;;;
+1F83C;LEFTWARDS COMPRESSED ARROW;So;0;ON;;;;;N;;;;;
+1F83D;UPWARDS COMPRESSED ARROW;So;0;ON;;;;;N;;;;;
+1F83E;RIGHTWARDS COMPRESSED ARROW;So;0;ON;;;;;N;;;;;
+1F83F;DOWNWARDS COMPRESSED ARROW;So;0;ON;;;;;N;;;;;
+1F840;LEFTWARDS HEAVY COMPRESSED ARROW;So;0;ON;;;;;N;;;;;
+1F841;UPWARDS HEAVY COMPRESSED ARROW;So;0;ON;;;;;N;;;;;
+1F842;RIGHTWARDS HEAVY COMPRESSED ARROW;So;0;ON;;;;;N;;;;;
+1F843;DOWNWARDS HEAVY COMPRESSED ARROW;So;0;ON;;;;;N;;;;;
+1F844;LEFTWARDS HEAVY ARROW;So;0;ON;;;;;N;;;;;
+1F845;UPWARDS HEAVY ARROW;So;0;ON;;;;;N;;;;;
+1F846;RIGHTWARDS HEAVY ARROW;So;0;ON;;;;;N;;;;;
+1F847;DOWNWARDS HEAVY ARROW;So;0;ON;;;;;N;;;;;
+1F850;LEFTWARDS SANS-SERIF ARROW;So;0;ON;;;;;N;;;;;
+1F851;UPWARDS SANS-SERIF ARROW;So;0;ON;;;;;N;;;;;
+1F852;RIGHTWARDS SANS-SERIF ARROW;So;0;ON;;;;;N;;;;;
+1F853;DOWNWARDS SANS-SERIF ARROW;So;0;ON;;;;;N;;;;;
+1F854;NORTH WEST SANS-SERIF ARROW;So;0;ON;;;;;N;;;;;
+1F855;NORTH EAST SANS-SERIF ARROW;So;0;ON;;;;;N;;;;;
+1F856;SOUTH EAST SANS-SERIF ARROW;So;0;ON;;;;;N;;;;;
+1F857;SOUTH WEST SANS-SERIF ARROW;So;0;ON;;;;;N;;;;;
+1F858;LEFT RIGHT SANS-SERIF ARROW;So;0;ON;;;;;N;;;;;
+1F859;UP DOWN SANS-SERIF ARROW;So;0;ON;;;;;N;;;;;
+1F860;WIDE-HEADED LEFTWARDS LIGHT BARB ARROW;So;0;ON;;;;;N;;;;;
+1F861;WIDE-HEADED UPWARDS LIGHT BARB ARROW;So;0;ON;;;;;N;;;;;
+1F862;WIDE-HEADED RIGHTWARDS LIGHT BARB ARROW;So;0;ON;;;;;N;;;;;
+1F863;WIDE-HEADED DOWNWARDS LIGHT BARB ARROW;So;0;ON;;;;;N;;;;;
+1F864;WIDE-HEADED NORTH WEST LIGHT BARB ARROW;So;0;ON;;;;;N;;;;;
+1F865;WIDE-HEADED NORTH EAST LIGHT BARB ARROW;So;0;ON;;;;;N;;;;;
+1F866;WIDE-HEADED SOUTH EAST LIGHT BARB ARROW;So;0;ON;;;;;N;;;;;
+1F867;WIDE-HEADED SOUTH WEST LIGHT BARB ARROW;So;0;ON;;;;;N;;;;;
+1F868;WIDE-HEADED LEFTWARDS BARB ARROW;So;0;ON;;;;;N;;;;;
+1F869;WIDE-HEADED UPWARDS BARB ARROW;So;0;ON;;;;;N;;;;;
+1F86A;WIDE-HEADED RIGHTWARDS BARB ARROW;So;0;ON;;;;;N;;;;;
+1F86B;WIDE-HEADED DOWNWARDS BARB ARROW;So;0;ON;;;;;N;;;;;
+1F86C;WIDE-HEADED NORTH WEST BARB ARROW;So;0;ON;;;;;N;;;;;
+1F86D;WIDE-HEADED NORTH EAST BARB ARROW;So;0;ON;;;;;N;;;;;
+1F86E;WIDE-HEADED SOUTH EAST BARB ARROW;So;0;ON;;;;;N;;;;;
+1F86F;WIDE-HEADED SOUTH WEST BARB ARROW;So;0;ON;;;;;N;;;;;
+1F870;WIDE-HEADED LEFTWARDS MEDIUM BARB ARROW;So;0;ON;;;;;N;;;;;
+1F871;WIDE-HEADED UPWARDS MEDIUM BARB ARROW;So;0;ON;;;;;N;;;;;
+1F872;WIDE-HEADED RIGHTWARDS MEDIUM BARB ARROW;So;0;ON;;;;;N;;;;;
+1F873;WIDE-HEADED DOWNWARDS MEDIUM BARB ARROW;So;0;ON;;;;;N;;;;;
+1F874;WIDE-HEADED NORTH WEST MEDIUM BARB ARROW;So;0;ON;;;;;N;;;;;
+1F875;WIDE-HEADED NORTH EAST MEDIUM BARB ARROW;So;0;ON;;;;;N;;;;;
+1F876;WIDE-HEADED SOUTH EAST MEDIUM BARB ARROW;So;0;ON;;;;;N;;;;;
+1F877;WIDE-HEADED SOUTH WEST MEDIUM BARB ARROW;So;0;ON;;;;;N;;;;;
+1F878;WIDE-HEADED LEFTWARDS HEAVY BARB ARROW;So;0;ON;;;;;N;;;;;
+1F879;WIDE-HEADED UPWARDS HEAVY BARB ARROW;So;0;ON;;;;;N;;;;;
+1F87A;WIDE-HEADED RIGHTWARDS HEAVY BARB ARROW;So;0;ON;;;;;N;;;;;
+1F87B;WIDE-HEADED DOWNWARDS HEAVY BARB ARROW;So;0;ON;;;;;N;;;;;
+1F87C;WIDE-HEADED NORTH WEST HEAVY BARB ARROW;So;0;ON;;;;;N;;;;;
+1F87D;WIDE-HEADED NORTH EAST HEAVY BARB ARROW;So;0;ON;;;;;N;;;;;
+1F87E;WIDE-HEADED SOUTH EAST HEAVY BARB ARROW;So;0;ON;;;;;N;;;;;
+1F87F;WIDE-HEADED SOUTH WEST HEAVY BARB ARROW;So;0;ON;;;;;N;;;;;
+1F880;WIDE-HEADED LEFTWARDS VERY HEAVY BARB ARROW;So;0;ON;;;;;N;;;;;
+1F881;WIDE-HEADED UPWARDS VERY HEAVY BARB ARROW;So;0;ON;;;;;N;;;;;
+1F882;WIDE-HEADED RIGHTWARDS VERY HEAVY BARB ARROW;So;0;ON;;;;;N;;;;;
+1F883;WIDE-HEADED DOWNWARDS VERY HEAVY BARB ARROW;So;0;ON;;;;;N;;;;;
+1F884;WIDE-HEADED NORTH WEST VERY HEAVY BARB ARROW;So;0;ON;;;;;N;;;;;
+1F885;WIDE-HEADED NORTH EAST VERY HEAVY BARB ARROW;So;0;ON;;;;;N;;;;;
+1F886;WIDE-HEADED SOUTH EAST VERY HEAVY BARB ARROW;So;0;ON;;;;;N;;;;;
+1F887;WIDE-HEADED SOUTH WEST VERY HEAVY BARB ARROW;So;0;ON;;;;;N;;;;;
+1F890;LEFTWARDS TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F891;UPWARDS TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F892;RIGHTWARDS TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F893;DOWNWARDS TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F894;LEFTWARDS WHITE ARROW WITHIN TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F895;UPWARDS WHITE ARROW WITHIN TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F896;RIGHTWARDS WHITE ARROW WITHIN TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F897;DOWNWARDS WHITE ARROW WITHIN TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;;
+1F898;LEFTWARDS ARROW WITH NOTCHED TAIL;So;0;ON;;;;;N;;;;;
+1F899;UPWARDS ARROW WITH NOTCHED TAIL;So;0;ON;;;;;N;;;;;
+1F89A;RIGHTWARDS ARROW WITH NOTCHED TAIL;So;0;ON;;;;;N;;;;;
+1F89B;DOWNWARDS ARROW WITH NOTCHED TAIL;So;0;ON;;;;;N;;;;;
+1F89C;HEAVY ARROW SHAFT WIDTH ONE;So;0;ON;;;;;N;;;;;
+1F89D;HEAVY ARROW SHAFT WIDTH TWO THIRDS;So;0;ON;;;;;N;;;;;
+1F89E;HEAVY ARROW SHAFT WIDTH ONE HALF;So;0;ON;;;;;N;;;;;
+1F89F;HEAVY ARROW SHAFT WIDTH ONE THIRD;So;0;ON;;;;;N;;;;;
+1F8A0;LEFTWARDS BOTTOM-SHADED WHITE ARROW;So;0;ON;;;;;N;;;;;
+1F8A1;RIGHTWARDS BOTTOM SHADED WHITE ARROW;So;0;ON;;;;;N;;;;;
+1F8A2;LEFTWARDS TOP SHADED WHITE ARROW;So;0;ON;;;;;N;;;;;
+1F8A3;RIGHTWARDS TOP SHADED WHITE ARROW;So;0;ON;;;;;N;;;;;
+1F8A4;LEFTWARDS LEFT-SHADED WHITE ARROW;So;0;ON;;;;;N;;;;;
+1F8A5;RIGHTWARDS RIGHT-SHADED WHITE ARROW;So;0;ON;;;;;N;;;;;
+1F8A6;LEFTWARDS RIGHT-SHADED WHITE ARROW;So;0;ON;;;;;N;;;;;
+1F8A7;RIGHTWARDS LEFT-SHADED WHITE ARROW;So;0;ON;;;;;N;;;;;
+1F8A8;LEFTWARDS BACK-TILTED SHADOWED WHITE ARROW;So;0;ON;;;;;N;;;;;
+1F8A9;RIGHTWARDS BACK-TILTED SHADOWED WHITE ARROW;So;0;ON;;;;;N;;;;;
+1F8AA;LEFTWARDS FRONT-TILTED SHADOWED WHITE ARROW;So;0;ON;;;;;N;;;;;
+1F8AB;RIGHTWARDS FRONT-TILTED SHADOWED WHITE ARROW;So;0;ON;;;;;N;;;;;
+1F8AC;WHITE ARROW SHAFT WIDTH ONE;So;0;ON;;;;;N;;;;;
+1F8AD;WHITE ARROW SHAFT WIDTH TWO THIRDS;So;0;ON;;;;;N;;;;;
 20000;<CJK Ideograph Extension B, First>;Lo;0;L;;;;;N;;;;;
 2A6D6;<CJK Ideograph Extension B, Last>;Lo;0;L;;;;;N;;;;;
 2A700;<CJK Ideograph Extension C, First>;Lo;0;L;;;;;N;;;;;
--- a/jdk/make/data/unicodedata/VERSION	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/make/data/unicodedata/VERSION	Wed Jul 05 20:42:36 2017 +0200
@@ -1,1 +1,1 @@
-6.2.0
+7.0.0
--- a/jdk/make/mapfiles/libawt/mapfile-mawt-vers	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/make/mapfiles/libawt/mapfile-mawt-vers	Wed Jul 05 20:42:36 2017 +0200
@@ -196,7 +196,6 @@
                 Java_sun_java2d_opengl_GLXGraphicsConfig_initConfig;
                 Java_sun_java2d_opengl_GLXGraphicsConfig_getOGLCapabilities;
                 Java_sun_java2d_opengl_GLXSurfaceData_initOps;
-                Java_sun_java2d_opengl_GLXSurfaceData_initPbuffer;
 
                 Java_sun_print_CUPSPrinter_initIDs;
                 Java_sun_print_CUPSPrinter_getCupsServer;
--- a/jdk/make/mapfiles/libawt/mapfile-vers	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/make/mapfiles/libawt/mapfile-vers	Wed Jul 05 20:42:36 2017 +0200
@@ -37,7 +37,6 @@
 		Java_sun_awt_image_DataBufferNative_getElem;
 		Java_sun_awt_image_DataBufferNative_setElem;
 		Java_java_awt_image_ColorModel_initIDs;
-		Java_java_awt_image_ComponentSampleModel_initIDs;
 		Java_java_awt_image_IndexColorModel_initIDs;
 		Java_java_awt_image_Kernel_initIDs;
 		Java_java_awt_image_Raster_initIDs;
@@ -89,7 +88,6 @@
 		Java_java_awt_Choice_initIDs;
 		Java_java_awt_Dimension_initIDs;
 		Java_java_awt_event_MouseEvent_initIDs;
-		Java_java_awt_image_DataBufferInt_initIDs;
 		Java_java_awt_image_SinglePixelPackedSampleModel_initIDs;
 		Java_java_awt_Rectangle_initIDs;
 		Java_sun_awt_image_BufImgSurfaceData_initIDs;
--- a/jdk/make/mapfiles/libawt/mapfile-vers-linux	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/make/mapfiles/libawt/mapfile-vers-linux	Wed Jul 05 20:42:36 2017 +0200
@@ -37,7 +37,6 @@
 		Java_sun_awt_image_DataBufferNative_getElem;
 		Java_sun_awt_image_DataBufferNative_setElem;
 		Java_java_awt_image_ColorModel_initIDs;
-		Java_java_awt_image_ComponentSampleModel_initIDs;
 		Java_java_awt_image_IndexColorModel_initIDs;
 		Java_java_awt_image_Kernel_initIDs;
 		Java_java_awt_image_Raster_initIDs;
@@ -89,7 +88,6 @@
 		Java_java_awt_Choice_initIDs;
 		Java_java_awt_Dimension_initIDs;
 		Java_java_awt_event_MouseEvent_initIDs;
-		Java_java_awt_image_DataBufferInt_initIDs;
 		Java_java_awt_image_SinglePixelPackedSampleModel_initIDs;
 		Java_java_awt_Rectangle_initIDs;
 		Java_sun_awt_image_BufImgSurfaceData_getSurfaceData;
--- a/jdk/make/mapfiles/libawt_xawt/mapfile-vers	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/make/mapfiles/libawt_xawt/mapfile-vers	Wed Jul 05 20:42:36 2017 +0200
@@ -337,7 +337,6 @@
         Java_sun_java2d_opengl_GLXGraphicsConfig_initConfig;
         Java_sun_java2d_opengl_GLXGraphicsConfig_getOGLCapabilities;
         Java_sun_java2d_opengl_GLXSurfaceData_initOps;
-        Java_sun_java2d_opengl_GLXSurfaceData_initPbuffer;
 
         Java_sun_java2d_x11_X11PMBlitBgLoops_nativeBlitBg;
         Java_sun_java2d_x11_X11PMBlitLoops_nativeBlit;
--- a/jdk/make/mapfiles/libjava/mapfile-vers	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/make/mapfiles/libjava/mapfile-vers	Wed Jul 05 20:42:36 2017 +0200
@@ -166,11 +166,12 @@
 		Java_java_lang_Package_getSystemPackage0;
 		Java_java_lang_Package_getSystemPackages0;
 		Java_java_lang_ProcessEnvironment_environ;
+		Java_java_lang_ProcessHandleImpl_destroy0;
 		Java_java_lang_ProcessHandleImpl_getCurrentPid0;
-		Java_java_lang_ProcessHandleImpl_parent0;
+		Java_java_lang_ProcessHandleImpl_getProcessPids0;
+		Java_java_lang_ProcessHandleImpl_initNative;
 		Java_java_lang_ProcessHandleImpl_isAlive0;
-		Java_java_lang_ProcessHandleImpl_getProcessPids0;
-		Java_java_lang_ProcessHandleImpl_destroy0;
+		Java_java_lang_ProcessHandleImpl_parent0;
 		Java_java_lang_ProcessHandleImpl_waitForProcessExit0;
 		Java_java_lang_ProcessHandleImpl_00024Info_initIDs;
 		Java_java_lang_ProcessHandleImpl_00024Info_info0;
@@ -239,6 +240,16 @@
 		Java_java_util_TimeZone_getSystemTimeZoneID;
 		Java_java_util_TimeZone_getSystemGMTOffsetID;
 		Java_java_util_concurrent_atomic_AtomicLong_VMSupportsCS8;
+                Java_jdk_internal_jimage_ImageNativeSubstrate_openImage;
+                Java_jdk_internal_jimage_ImageNativeSubstrate_closeImage;
+                Java_jdk_internal_jimage_ImageNativeSubstrate_getIndexAddress;
+                Java_jdk_internal_jimage_ImageNativeSubstrate_getDataAddress;
+                Java_jdk_internal_jimage_ImageNativeSubstrate_read;
+                Java_jdk_internal_jimage_ImageNativeSubstrate_readCompressed;
+                Java_jdk_internal_jimage_ImageNativeSubstrate_getStringBytes;
+                Java_jdk_internal_jimage_ImageNativeSubstrate_getAttributes;
+                Java_jdk_internal_jimage_ImageNativeSubstrate_findAttributes;
+                Java_jdk_internal_jimage_ImageNativeSubstrate_attributeOffsets;
 		Java_sun_misc_MessageUtils_toStderr;
 		Java_sun_misc_MessageUtils_toStdout;
 		Java_sun_misc_NativeSignalHandler_handle0;
@@ -281,9 +292,6 @@
 		Java_sun_misc_VMSupport_initAgentProperties;
 		Java_sun_misc_VMSupport_getVMTemporaryDirectory;
 
-                Java_jdk_internal_jimage_concurrent_ConcurrentPReader_initIDs;
-                Java_jdk_internal_jimage_concurrent_ConcurrentPReader_pread;
-
                 # ZipFile.c needs this one
 		throwFileNotFoundException;
                 # zip_util.c needs this one
--- a/jdk/make/mapfiles/libzip/mapfile-vers	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/make/mapfiles/libzip/mapfile-vers	Wed Jul 05 20:42:36 2017 +0200
@@ -32,8 +32,8 @@
 		Java_java_util_zip_Adler32_updateBytes;
 		Java_java_util_zip_Adler32_updateByteBuffer;
 		Java_java_util_zip_CRC32_update;
-		Java_java_util_zip_CRC32_updateBytes;
-		Java_java_util_zip_CRC32_updateByteBuffer;
+		Java_java_util_zip_CRC32_updateBytes0;
+		Java_java_util_zip_CRC32_updateByteBuffer0;
 		Java_java_util_zip_Deflater_deflateBytes;
 		Java_java_util_zip_Deflater_end;
 		Java_java_util_zip_Deflater_getAdler;
--- a/jdk/make/src/classes/build/tools/generatecharacter/GenerateCharacter.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/make/src/classes/build/tools/generatecharacter/GenerateCharacter.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2002, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2002, 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
@@ -906,6 +906,14 @@
             return Integer.toString(UnicodeSpec.DIRECTIONALITY_WHITESPACE);
         if (x.equals(UnicodeSpec.bidiCategoryList[UnicodeSpec.DIRECTIONALITY_OTHER_NEUTRALS][UnicodeSpec.LONG]))
             return Integer.toString(UnicodeSpec.DIRECTIONALITY_OTHER_NEUTRALS);
+        if (x.equals(UnicodeSpec.bidiCategoryList[UnicodeSpec.DIRECTIONALITY_LEFT_TO_RIGHT_ISOLATE][UnicodeSpec.LONG]))
+            return Integer.toString(UnicodeSpec.DIRECTIONALITY_LEFT_TO_RIGHT_ISOLATE);
+        if (x.equals(UnicodeSpec.bidiCategoryList[UnicodeSpec.DIRECTIONALITY_RIGHT_TO_LEFT_ISOLATE][UnicodeSpec.LONG]))
+            return Integer.toString(UnicodeSpec.DIRECTIONALITY_RIGHT_TO_LEFT_ISOLATE);
+        if (x.equals(UnicodeSpec.bidiCategoryList[UnicodeSpec.DIRECTIONALITY_FIRST_STRONG_ISOLATE][UnicodeSpec.LONG]))
+            return Integer.toString(UnicodeSpec.DIRECTIONALITY_FIRST_STRONG_ISOLATE);
+        if (x.equals(UnicodeSpec.bidiCategoryList[UnicodeSpec.DIRECTIONALITY_POP_DIRECTIONAL_ISOLATE][UnicodeSpec.LONG]))
+            return Integer.toString(UnicodeSpec.DIRECTIONALITY_POP_DIRECTIONAL_ISOLATE);
         FAIL("Unknown text substitution marker " + commandMarker + x);
         return commandMarker + x;
     }
--- a/jdk/make/src/classes/build/tools/generatecharacter/UnicodeSpec.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/make/src/classes/build/tools/generatecharacter/UnicodeSpec.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2002, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2002, 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
@@ -121,7 +121,7 @@
         String[] tokens = null;
 
         try {
-                        tokens = tokenSeparator.split(s, REQUIRED_FIELDS);
+            tokens = tokenSeparator.split(s, REQUIRED_FIELDS);
             spec = new UnicodeSpec();
             spec.setCodePoint(parseCodePoint(tokens[FIELD_VALUE]));
             spec.setName(parseName(tokens[FIELD_NAME]));
@@ -672,7 +672,8 @@
      * Bidirectional categories
      */
     public static final byte
-                DIRECTIONALITY_UNDEFINED                  = -1,
+        DIRECTIONALITY_UNDEFINED                  = -1,
+
         // Strong category
         DIRECTIONALITY_LEFT_TO_RIGHT              =  0, // L
         DIRECTIONALITY_RIGHT_TO_LEFT              =  1, // R
@@ -689,15 +690,19 @@
         DIRECTIONALITY_PARAGRAPH_SEPARATOR        = 10, // B
         DIRECTIONALITY_SEGMENT_SEPARATOR          = 11, // S
         DIRECTIONALITY_WHITESPACE                 = 12, // WS
-        DIRECTIONALITY_OTHER_NEUTRALS              = 13, // ON
-
+        DIRECTIONALITY_OTHER_NEUTRALS             = 13, // ON
+        // Explicit Formatting category
         DIRECTIONALITY_LEFT_TO_RIGHT_EMBEDDING    = 14, // LRE
         DIRECTIONALITY_LEFT_TO_RIGHT_OVERRIDE     = 15, // LRO
         DIRECTIONALITY_RIGHT_TO_LEFT_EMBEDDING    = 16, // RLE
         DIRECTIONALITY_RIGHT_TO_LEFT_OVERRIDE     = 17, // RLO
         DIRECTIONALITY_POP_DIRECTIONAL_FORMAT     = 18, // PDF
+        DIRECTIONALITY_LEFT_TO_RIGHT_ISOLATE      = 19, // LRI
+        DIRECTIONALITY_RIGHT_TO_LEFT_ISOLATE      = 20, // RLI
+        DIRECTIONALITY_FIRST_STRONG_ISOLATE       = 21, // FSI
+        DIRECTIONALITY_POP_DIRECTIONAL_ISOLATE    = 22, // PDI
 
-        DIRECTIONALITY_CATEGORY_COUNT             = 19; // sentinel value
+        DIRECTIONALITY_CATEGORY_COUNT             = 23; // sentinel value
 
     // If changes are made to the above bidi category assignments, this
     // list of bidi category names must be changed to keep their order in synch.
@@ -722,7 +727,10 @@
         {"RLE", "DIRECTIONALITY_RIGHT_TO_LEFT_EMBEDDING"},
         {"RLO", "DIRECTIONALITY_RIGHT_TO_LEFT_OVERRIDE"},
         {"PDF", "DIRECTIONALITY_POP_DIRECTIONAL_FORMAT"},
-
+        {"LRI", "DIRECTIONALITY_LEFT_TO_RIGHT_ISOLATE"},
+        {"RLI", "DIRECTIONALITY_RIGHT_TO_LEFT_ISOLATE"},
+        {"FSI", "DIRECTIONALITY_FIRST_STRONG_ISOLATE"},
+        {"PDI", "DIRECTIONALITY_POP_DIRECTIONAL_ISOLATE"},
     };
 
     // Unicode specification lines have fields in this order.
--- a/jdk/make/src/classes/build/tools/module/ImageBuilder.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/make/src/classes/build/tools/module/ImageBuilder.java	Wed Jul 05 20:42:36 2017 +0200
@@ -26,8 +26,6 @@
 package build.tools.module;
 
 import jdk.internal.jimage.Archive;
-import jdk.internal.jimage.ImageFile;
-import jdk.internal.jimage.ImageModules;
 
 import java.io.BufferedReader;
 import java.io.File;
@@ -35,13 +33,11 @@
 import java.io.InputStream;
 import java.io.InputStreamReader;
 import java.io.PrintWriter;
-import java.io.UncheckedIOException;
 import java.nio.ByteOrder;
 import java.nio.file.Files;
 import java.nio.file.InvalidPathException;
 import java.nio.file.Path;
 import java.nio.file.Paths;
-import java.nio.file.attribute.PosixFilePermission;
 import java.util.ArrayList;
 import java.util.Collection;
 import java.util.HashMap;
@@ -52,6 +48,7 @@
 import java.util.Optional;
 import java.util.Set;
 import java.util.stream.Collectors;
+import jdk.internal.jimage.ImageFileCreator;
 
 /**
  * A tool for building a runtime image.
@@ -84,11 +81,23 @@
         boolean showUsage;
     }
 
-    static abstract class Option {
+    static class Option {
+
+        interface Processing {
+
+            void process(ImageBuilder task, String opt, String arg) throws BadArgs;
+        }
+
         final boolean hasArg;
         final String[] aliases;
-        Option(boolean hasArg, String... aliases) {
+        final String description;
+        final Processing processing;
+
+        Option(boolean hasArg, String description, Processing processing,
+                String... aliases) {
             this.hasArg = hasArg;
+            this.description = description;
+            this.processing = processing;
             this.aliases = aliases;
         }
         boolean isHidden() {
@@ -107,8 +116,12 @@
         boolean ignoreRest() {
             return false;
         }
-        abstract void process(ImageBuilder task, String opt, String arg) throws BadArgs;
-        abstract String description();
+        void process(ImageBuilder task, String opt, String arg) throws BadArgs {
+            processing.process(task, opt, arg);
+        }
+        String description() {
+            return description;
+        }
     }
 
     private static Path CWD = Paths.get("");
@@ -133,64 +146,44 @@
     }
 
     static Option[] recognizedOptions = {
-        new Option(true, "--cmds") {
-            void process(ImageBuilder task, String opt, String arg) throws BadArgs {
-                task.options.cmds = splitPath(arg, File.pathSeparator);
-            }
-            String description() { return "Location of native commands"; }
-        },
-        new Option(true, "--configs") {
-            void process(ImageBuilder task, String opt, String arg) throws BadArgs {
-                task.options.configs = splitPath(arg, File.pathSeparator);
-            }
-            String description() { return "Location of config files"; }
-        },
-        new Option(false, "--help") {
-            void process(ImageBuilder task, String opt, String arg) {
-                task.options.help = true;
-            }
-            String description() { return "Print this usage message"; }
-        },
-        new Option(true, "--classes") {
-            void process(ImageBuilder task, String opt, String arg) throws BadArgs {
-                task.options.classes = splitPath(arg, File.pathSeparator);
-            }
-            String description() { return "Location of module classes files"; }
-        },
-        new Option(true, "--libs") {
-            void process(ImageBuilder task, String opt, String arg) throws BadArgs {
-                task.options.libs = splitPath(arg, File.pathSeparator);
+        new Option(true, "Location of native commands", (task, opt, arg) -> {
+            task.options.cmds = splitPath(arg, File.pathSeparator);
+        }, "--cmds"),
+        new Option(true, "Location of config files", (task, opt, arg) -> {
+            task.options.configs = splitPath(arg, File.pathSeparator);
+        }, "--configs"),
+        new Option(false, "Print this usage message", (task, opt, arg) -> {
+            task.options.help = true;
+        }, "--help"),
+        new Option(true, "Location of module classes files", (task, opt, arg) -> {
+            task.options.classes = splitPath(arg, File.pathSeparator);
+        }, "--classes"),
+        new Option(true, "Location of native libraries", (task, opt, arg) -> {
+            task.options.libs = splitPath(arg, File.pathSeparator);
+        }, "--libs"),
+        new Option(true, "Comma separated list of module names",
+        (task, opt, arg) -> {
+            for (String mn : arg.split(",")) {
+                if (mn.isEmpty()) {
+                    throw new BadArgs("Module not found", mn);
+                }
+                task.options.mods.add(mn);
             }
-            String description() { return "Location of native libraries"; }
-        },
-        new Option(true, "--mods") {
-            void process(ImageBuilder task, String opt, String arg) throws BadArgs {
-                for (String mn : arg.split(",")) {
-                    if (mn.isEmpty())
-                        throw new BadArgs("Module not found", mn);
-                    task.options.mods.add(mn);
-                }
+        }, "--mods"),
+        new Option(true, "Location of the output path", (task, opt, arg) -> {
+            Path path = Paths.get(arg);
+            task.options.output = path;
+        }, "--output"),
+        new Option(true, "Byte order of the target runtime; {little,big}",
+        (task, opt, arg) -> {
+            if (arg.equals("little")) {
+                task.options.endian = ByteOrder.LITTLE_ENDIAN;
+            } else if (arg.equals("big")) {
+                task.options.endian = ByteOrder.BIG_ENDIAN;
+            } else {
+                throw new BadArgs("Unknown byte order " + arg);
             }
-            String description() { return "Comma separated list of module names"; }
-        },
-        new Option(true, "--output") {
-            void process(ImageBuilder task, String opt, String arg) throws BadArgs {
-                Path path = Paths.get(arg);
-                task.options.output = path;
-            }
-            String description() { return "Location of the output path"; }
-        },
-        new Option(true, "--endian") {
-            void process(ImageBuilder task, String opt, String arg) throws BadArgs {
-                if (arg.equals("little"))
-                    task.options.endian = ByteOrder.LITTLE_ENDIAN;
-                else if (arg.equals("big"))
-                    task.options.endian = ByteOrder.BIG_ENDIAN;
-                else
-                    throw new BadArgs("Unknown byte order " + arg);
-            }
-            String description() { return "Byte order of the target runtime; {little,big}"; }
-        }
+        }, "--endian")
     };
 
     private final Options options = new Options();
@@ -370,28 +363,35 @@
         final Set<String> bootModules;
         final Set<String> extModules;
         final Set<String> appModules;
-        final ImageModules imf;
 
         ImageFileHelper(Collection<String> modules) throws IOException {
             this.modules = modules;
             this.bootModules = modulesFor(BOOT_MODULES).stream()
-                     .filter(modules::contains)
-                     .collect(Collectors.toSet());
+                    .filter(modules::contains)
+                    .collect(Collectors.toSet());
             this.extModules = modulesFor(EXT_MODULES).stream()
                     .filter(modules::contains)
                     .collect(Collectors.toSet());
             this.appModules = modules.stream()
-                    .filter(m -> !bootModules.contains(m) && !extModules.contains(m))
+                    .filter(m -> m.length() != 0 &&
+                                 !bootModules.contains(m) &&
+                                 !extModules.contains(m))
                     .collect(Collectors.toSet());
-
-            this.imf = new ImageModules(bootModules, extModules, appModules);
         }
 
         void createModularImage(Path output) throws IOException {
-            Set<Archive> archives = modules.stream()
-                                            .map(this::toModuleArchive)
-                                            .collect(Collectors.toSet());
-            ImageFile.create(output, archives, imf, options.endian);
+            Set<Archive> bootArchives = bootModules.stream()
+                    .map(this::toModuleArchive)
+                    .collect(Collectors.toSet());
+            Set<Archive> extArchives = extModules.stream()
+                    .map(this::toModuleArchive)
+                    .collect(Collectors.toSet());
+            Set<Archive> appArchives = appModules.stream()
+                    .map(this::toModuleArchive)
+                    .collect(Collectors.toSet());
+            ImageFileCreator.create(output, "bootmodules", bootArchives, options.endian);
+            ImageFileCreator.create(output, "extmodules", extArchives, options.endian);
+            ImageFileCreator.create(output, "appmodules", appArchives, options.endian);
         }
 
         ModuleArchive toModuleArchive(String mn) {
--- a/jdk/make/src/classes/build/tools/module/ModuleArchive.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/make/src/classes/build/tools/module/ModuleArchive.java	Wed Jul 05 20:42:36 2017 +0200
@@ -26,15 +26,17 @@
 package build.tools.module;
 
 import jdk.internal.jimage.Archive;
-import jdk.internal.jimage.Resource;
 
 import java.io.IOException;
 import java.io.InputStream;
-import java.io.OutputStream;
 import java.io.UncheckedIOException;
 import java.nio.file.Files;
 import java.nio.file.Path;
-import java.util.function.Consumer;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.stream.Collectors;
+import java.util.stream.Stream;
+import jdk.internal.jimage.Archive.Entry.EntryType;
 
 /**
  * An Archive backed by an exploded representation on disk.
@@ -46,6 +48,8 @@
     private final Path configs;
     private final String moduleName;
 
+    private final List<InputStream> opened = new ArrayList<>();
+
     public ModuleArchive(String moduleName, Path classes, Path cmds,
                          Path libs, Path configs) {
         this.moduleName = moduleName;
@@ -61,183 +65,119 @@
     }
 
     @Override
-    public void visitResources(Consumer<Resource> consumer) {
-        if (classes == null)
-            return;
-        try{
-            Files.walk(classes)
-                    .sorted()
-                    .filter(p -> !Files.isDirectory(p)
-                            && !classes.relativize(p).toString().startsWith("_the.")
-                            && !classes.relativize(p).toString().equals("javac_state"))
-                    .map(this::toResource)
-                    .forEach(consumer::accept);
-        } catch (IOException ioe) {
-            throw new UncheckedIOException(ioe);
-        }
+    public void open() throws IOException {
+        // NOOP
     }
 
-    private Resource toResource(Path path) {
-        try {
-            return new Resource(classes.relativize(path).toString().replace('\\','/'),
-                                Files.size(path),
-                                0 /* no compression support yet */);
-        } catch (IOException ioe) {
-            throw new UncheckedIOException(ioe);
+    @Override
+    public void close() throws IOException {
+        IOException e = null;
+        for (InputStream stream : opened) {
+            try {
+                stream.close();
+            } catch (IOException ex) {
+                if (e == null) {
+                    e = ex;
+                } else {
+                    e.addSuppressed(ex);
+                }
+            }
         }
-    }
-
-    private enum Section {
-        CLASSES,
-        CMDS,
-        LIBS,
-        CONFIGS
+        if (e != null) {
+            throw e;
+        }
     }
 
     @Override
-    public void visitEntries(Consumer<Entry> consumer) {
-        try{
-            if (classes != null)
-                Files.walk(classes)
-                        .sorted()
-                        .filter(p -> !Files.isDirectory(p)
-                                && !classes.relativize(p).toString().startsWith("_the.")
-                                && !classes.relativize(p).toString().equals("javac_state"))
-                        .map(p -> toEntry(p, classes, Section.CLASSES))
-                        .forEach(consumer::accept);
-            if (cmds != null)
-                Files.walk(cmds)
+    public Stream<Entry> entries() {
+        List<Entry> entries = new ArrayList<>();
+        try {
+            /*
+             * This code should be revisited to avoid buffering of the entries.
+             * 1) Do we really need sorting classes? This force buffering of entries.
+             *    libs, cmds and configs are not sorted.
+             * 2) I/O streams should be concatenated instead of buffering into
+             *    entries list.
+             * 3) Close I/O streams in a close handler.
+             */
+            if (classes != null) {
+                try (Stream<Path> stream = Files.walk(classes)) {
+                    entries.addAll(stream
+                            .filter(p -> !Files.isDirectory(p)
+                                    && !classes.relativize(p).toString().startsWith("_the.")
+                                    && !classes.relativize(p).toString().equals("javac_state"))
+                            .sorted()
+                            .map(p -> toEntry(p, classes, EntryType.CLASS_OR_RESOURCE))
+                            .collect(Collectors.toList()));
+                }
+            }
+            if (cmds != null) {
+                try (Stream<Path> stream = Files.walk(cmds)) {
+                    entries.addAll(stream
+                            .filter(p -> !Files.isDirectory(p))
+                            .map(p -> toEntry(p, cmds, EntryType.NATIVE_CMD))
+                            .collect(Collectors.toList()));
+                }
+            }
+            if (libs != null) {
+                try (Stream<Path> stream = Files.walk(libs)) {
+                    entries.addAll(stream
+                            .filter(p -> !Files.isDirectory(p))
+                            .map(p -> toEntry(p, libs, EntryType.NATIVE_LIB))
+                            .collect(Collectors.toList()));
+                }
+            }
+            if (configs != null) {
+                try (Stream<Path> stream = Files.walk(configs)) {
+                entries.addAll(stream
                         .filter(p -> !Files.isDirectory(p))
-                        .map(p -> toEntry(p, cmds, Section.CMDS))
-                        .forEach(consumer::accept);
-            if (libs != null)
-                Files.walk(libs)
-                        .filter(p -> !Files.isDirectory(p))
-                        .map(p -> toEntry(p, libs, Section.LIBS))
-                        .forEach(consumer::accept);
-            if (configs != null)
-                Files.walk(configs)
-                        .filter(p -> !Files.isDirectory(p))
-                        .map(p -> toEntry(p, configs, Section.CONFIGS))
-                        .forEach(consumer::accept);
+                        .map(p -> toEntry(p, configs, EntryType.CONFIG))
+                        .collect(Collectors.toList()));
+                }
+            }
         } catch (IOException ioe) {
             throw new UncheckedIOException(ioe);
         }
+        return entries.stream();
+    }
+
+    private class FileEntry extends Entry {
+        private final boolean isDirectory;
+        private final long size;
+        private final Path entryPath;
+        FileEntry(Path entryPath, String path, EntryType type,
+                  boolean isDirectory, long size) {
+            super(ModuleArchive.this, path, path, type);
+            this.entryPath = entryPath;
+            this.isDirectory = isDirectory;
+            this.size = size;
+        }
+
+        public boolean isDirectory() {
+            return isDirectory;
+        }
+
+        @Override
+        public long size() {
+            return size;
+        }
+
+        @Override
+        public InputStream stream() throws IOException {
+            InputStream stream = Files.newInputStream(entryPath);
+            opened.add(stream);
+            return stream;
+        }
     }
 
-    private static class FileEntry implements Entry {
-        private final String name;
-        private final InputStream is;
-        private final boolean isDirectory;
-        private final Section section;
-        FileEntry(String name, InputStream is,
-                  boolean isDirectory, Section section) {
-            this.name = name;
-            this.is = is;
-            this.isDirectory = isDirectory;
-            this.section = section;
-        }
-        public String getName() {
-            return name;
-        }
-        public Section getSection() {
-            return section;
-        }
-        public InputStream getInputStream() {
-            return is;
-        }
-        public boolean isDirectory() {
-            return isDirectory;
-        }
-    }
-
-    private Entry toEntry(Path entryPath, Path basePath, Section section) {
+    private Entry toEntry(Path entryPath, Path basePath, EntryType section) {
         try {
-            return new FileEntry(basePath.relativize(entryPath).toString().replace('\\', '/'),
-                                 Files.newInputStream(entryPath), false,
-                                 section);
+            String path = basePath.relativize(entryPath).toString().replace('\\', '/');
+            return new FileEntry(entryPath, path, section,
+                    false, Files.size(entryPath));
         } catch (IOException e) {
             throw new UncheckedIOException(e);
         }
     }
-
-    @Override
-    public Consumer<Entry> defaultImageWriter(Path path, OutputStream out) {
-        return new DefaultEntryWriter(path, out);
-    }
-
-    private static class DefaultEntryWriter implements Consumer<Archive.Entry> {
-        private final Path root;
-        private final OutputStream out;
-
-        DefaultEntryWriter(Path root, OutputStream out) {
-            this.root = root;
-            this.out = out;
-        }
-
-        @Override
-        public void accept(Archive.Entry entry) {
-            try {
-                FileEntry e = (FileEntry)entry;
-                Section section = e.getSection();
-                String filename = e.getName();
-
-                try (InputStream in = entry.getInputStream()) {
-                    switch (section) {
-                        case CLASSES:
-                            if (!filename.startsWith("_the.") && !filename.equals("javac_state"))
-                                writeEntry(in);
-                            break;
-                        case LIBS:
-                            writeEntry(in, destFile(nativeDir(filename), filename));
-                            break;
-                        case CMDS:
-                            Path path = destFile("bin", filename);
-                            writeEntry(in, path);
-                            path.toFile().setExecutable(true, false);
-                            break;
-                        case CONFIGS:
-                            writeEntry(in, destFile("conf", filename));
-                            break;
-                        default:
-                            throw new InternalError("unexpected entry: " + filename);
-                    }
-                }
-            } catch (IOException x) {
-                throw new UncheckedIOException(x);
-            }
-        }
-
-        private Path destFile(String dir, String filename) {
-            return root.resolve(dir).resolve(filename);
-        }
-
-        private static void writeEntry(InputStream in, Path dstFile) throws IOException {
-            if (Files.notExists(dstFile.getParent()))
-                Files.createDirectories(dstFile.getParent());
-            Files.copy(in, dstFile);
-        }
-
-        private void writeEntry(InputStream in) throws IOException {
-            byte[] buf = new byte[8192];
-            int n;
-            while ((n = in.read(buf)) > 0)
-                out.write(buf, 0, n);
-        }
-
-        private static String nativeDir(String filename) {
-            if (System.getProperty("os.name").startsWith("Windows")) {
-                if (filename.endsWith(".dll") || filename.endsWith(".diz")
-                    || filename.endsWith(".pdb") || filename.endsWith(".map")
-                    || filename.endsWith(".cpl")) {
-                    return "bin";
-                } else {
-                    return "lib";
-                }
-            } else {
-                return "lib";
-            }
-        }
-    }
 }
 
--- a/jdk/src/java.base/macosx/native/libjava/ProcessHandleImpl_macosx.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/macosx/native/libjava/ProcessHandleImpl_macosx.c	Wed Jul 05 20:42:36 2017 +0200
@@ -75,9 +75,8 @@
  * Method:    initIDs
  * Signature: ()V
  */
-JNIEXPORT void JNICALL Java_java_lang_ProcessHandleImpl_00024Info_initIDs
-  (JNIEnv *env, jclass clazz) {
-
+JNIEXPORT void JNICALL
+Java_java_lang_ProcessHandleImpl_00024Info_initIDs(JNIEnv *env, jclass clazz) {
     CHECK_NULL(ProcessHandleImpl_Info_commandID =
             (*env)->GetFieldID(env, clazz, "command", "Ljava/lang/String;"));
     CHECK_NULL(ProcessHandleImpl_Info_argumentsID =
@@ -88,7 +87,45 @@
             (*env)->GetFieldID(env, clazz, "startTime", "J"));
     CHECK_NULL(ProcessHandleImpl_Info_userID =
             (*env)->GetFieldID(env, clazz, "user", "Ljava/lang/String;"));
-    clock_ticks_per_second = sysconf(_SC_CLK_TCK);
+}
+/**************************************************************
+ * Static method to initialize the ticks per second rate.
+ *
+ * Class:     java_lang_ProcessHandleImpl
+ * Method:    initNative
+ * Signature: ()V
+ */
+JNIEXPORT void JNICALL
+Java_java_lang_ProcessHandleImpl_initNative(JNIEnv *env, jclass clazz) {
+      clock_ticks_per_second = sysconf(_SC_CLK_TCK);
+}
+
+/*
+ * Check if a process is alive.
+ * Return the start time (ms since 1970) if it is available.
+ * If the start time is not available return 0.
+ * If the pid is invalid, return -1.
+ *
+ * Class:     java_lang_ProcessHandleImpl
+ * Method:    isAlive0
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL
+Java_java_lang_ProcessHandleImpl_isAlive0(JNIEnv *env, jobject obj, jlong jpid) {
+    pid_t pid = (pid_t) jpid;
+    struct kinfo_proc kp;
+    size_t bufSize = sizeof kp;
+
+    // Read the process info for the specific pid
+    int mib[4] = {CTL_KERN, KERN_PROC, KERN_PROC_PID, pid};
+
+    if (sysctl(mib, 4, &kp, &bufSize, NULL, 0) < 0) {
+        return  (errno == EINVAL) ? -1 : 0;
+    } else {
+        return (bufSize == 0) ?  -1 :
+                                 (jlong) (kp.kp_proc.p_starttime.tv_sec * 1000
+                                        + kp.kp_proc.p_starttime.tv_usec / 1000);
+    }
 }
 
 /*
@@ -98,8 +135,11 @@
  * Method:    parent0
  * Signature: (J)J
  */
-JNIEXPORT jlong JNICALL Java_java_lang_ProcessHandleImpl_parent0
-(JNIEnv *env, jobject obj, jlong jpid) {
+JNIEXPORT jlong JNICALL
+Java_java_lang_ProcessHandleImpl_parent0(JNIEnv *env,
+                                         jobject obj,
+                                         jlong jpid,
+                                         jlong startTime) {
     pid_t pid = (pid_t) jpid;
     pid_t ppid = -1;
 
@@ -117,7 +157,14 @@
                 "java/lang/RuntimeException", "sysctl failed");
             return -1;
         }
-        ppid = (bufSize > 0 && kp.kp_proc.p_pid == pid) ? kp.kp_eproc.e_ppid : -1;
+        // If the buffer is full and for the pid requested then check the start
+        if (bufSize > 0 && kp.kp_proc.p_pid == pid) {
+            jlong start = (jlong) (kp.kp_proc.p_starttime.tv_sec * 1000
+                                   + kp.kp_proc.p_starttime.tv_usec / 1000);
+            if (start == startTime || start == 0 || startTime == 0) {
+                ppid = kp.kp_eproc.e_ppid;
+            }
+        }
     }
     return (jlong) ppid;
 }
@@ -136,15 +183,20 @@
  * If the array is too short, excess pids are not stored and
  * the desired length is returned.
  */
-JNIEXPORT jint JNICALL Java_java_lang_ProcessHandleImpl_getProcessPids0
-(JNIEnv *env, jclass clazz, jlong jpid,
-    jlongArray jarray, jlongArray jparentArray)
-{
-    size_t count = 0;
+JNIEXPORT jint JNICALL
+Java_java_lang_ProcessHandleImpl_getProcessPids0(JNIEnv *env,
+                                                 jclass clazz,
+                                                 jlong jpid,
+                                                 jlongArray jarray,
+                                                 jlongArray jparentArray,
+                                                 jlongArray jstimesArray) {
     jlong* pids = NULL;
     jlong* ppids = NULL;
-    size_t parentArraySize = 0;
-    size_t arraySize = 0;
+    jlong* stimes = NULL;
+    jsize parentArraySize = 0;
+    jsize arraySize = 0;
+    jsize stimesSize = 0;
+    jsize count = 0;
     size_t bufSize = 0;
     pid_t pid = (pid_t) jpid;
 
@@ -159,6 +211,15 @@
             return 0;
         }
     }
+    if (jstimesArray != NULL) {
+        stimesSize = (*env)->GetArrayLength(env, jstimesArray);
+        JNU_CHECK_EXCEPTION_RETURN(env, -1);
+
+        if (arraySize != stimesSize) {
+            JNU_ThrowIllegalArgumentException(env, "array sizes not equal");
+            return 0;
+        }
+    }
 
     // Get buffer size needed to read all processes
     int mib[4] = {CTL_KERN, KERN_PROC, KERN_PROC_ALL, 0};
@@ -198,6 +259,12 @@
                 break;
             }
         }
+        if (jstimesArray != NULL) {
+            stimes  = (*env)->GetLongArrayElements(env, jstimesArray, NULL);
+            if (stimes == NULL) {
+                break;
+            }
+        }
 
         // Process each entry in the buffer
         for (i = nentries; --i >= 0; ++kp) {
@@ -209,6 +276,12 @@
                         // Store the parentPid
                         ppids[count] = (jlong) kp->kp_eproc.e_ppid;
                     }
+                    if (stimes != NULL) {
+                        // Store the process start time
+                        jlong startTime = kp->kp_proc.p_starttime.tv_sec * 1000 +
+                                          kp->kp_proc.p_starttime.tv_usec / 1000;
+                        stimes[count] = startTime;
+                    }
                 }
                 count++; // Count to tabulate size needed
             }
@@ -221,6 +294,9 @@
     if (ppids != NULL) {
         (*env)->ReleaseLongArrayElements(env, jparentArray, ppids, 0);
     }
+    if (stimes != NULL) {
+        (*env)->ReleaseLongArrayElements(env, jstimesArray, stimes, 0);
+    }
 
     free(buffer);
     // If more pids than array had size for; count will be greater than array size
@@ -238,8 +314,10 @@
  * Method:    info0
  * Signature: (J)I
  */
-JNIEXPORT void JNICALL Java_java_lang_ProcessHandleImpl_00024Info_info0
-  (JNIEnv *env, jobject jinfo, jlong jpid) {
+JNIEXPORT void JNICALL
+Java_java_lang_ProcessHandleImpl_00024Info_info0(JNIEnv *env,
+                                                 jobject jinfo,
+                                                 jlong jpid) {
     pid_t pid = (pid_t) jpid;
     getStatInfo(env, jinfo, pid);
     getCmdlineInfo(env, jinfo, pid);
@@ -251,7 +329,7 @@
  */
 static void getStatInfo(JNIEnv *env, jobject jinfo, pid_t jpid) {
     jlong totalTime;                    // nanoseconds
-    unsigned long long startTime;       // microseconds
+    unsigned long long startTime;       // milliseconds
 
     const pid_t pid = (pid_t) jpid;
     struct kinfo_proc kp;
--- a/jdk/src/java.base/macosx/native/libjli/java_md_macosx.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/macosx/native/libjli/java_md_macosx.c	Wed Jul 05 20:42:36 2017 +0200
@@ -611,7 +611,11 @@
         if (access(libjava, F_OK) == 0) {
             return JNI_TRUE;
         }
-
+        /* ensure storage for path + /jre + NULL */
+        if ((JLI_StrLen(path) + 4 + 1) > (size_t) pathsize) {
+            JLI_TraceLauncher("Insufficient space to store JRE path\n");
+            return JNI_FALSE;
+        }
         /* Does the app ship a private JRE in <apphome>/jre directory? */
         JLI_Snprintf(libjava, sizeof(libjava), "%s/jre/lib/" JAVA_DLL, path);
         if (access(libjava, F_OK) == 0) {
--- a/jdk/src/java.base/share/classes/com/sun/crypto/provider/AESCrypt.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/com/sun/crypto/provider/AESCrypt.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2002, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2002, 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
@@ -37,7 +37,11 @@
 package com.sun.crypto.provider;
 
 import java.security.InvalidKeyException;
+import java.security.MessageDigest;
 import java.util.Arrays;
+import java.util.Objects;
+
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 /**
  * Rijndael --pronounced Reindaal-- is a symmetric cipher with a 128-bit
@@ -88,7 +92,7 @@
                 key.length + " bytes");
         }
 
-        if (!Arrays.equals(key, lastKey)) {
+        if (!MessageDigest.isEqual(key, lastKey)) {
             // re-generate session key 'sessionK' when cipher key changes
             makeSessionKey(key);
             lastKey = key.clone();  // save cipher key
@@ -346,7 +350,16 @@
      * Encrypt exactly one block of plaintext.
      */
     void encryptBlock(byte[] in, int inOffset,
-                              byte[] out, int outOffset)
+                      byte[] out, int outOffset) {
+        cryptBlockCheck(in, inOffset);
+        cryptBlockCheck(out, outOffset);
+        implEncryptBlock(in, inOffset, out, outOffset);
+    }
+
+    // Encryption operation. Possibly replaced with a compiler intrinsic.
+    @HotSpotIntrinsicCandidate
+    private void implEncryptBlock(byte[] in, int inOffset,
+                                  byte[] out, int outOffset)
     {
         int keyOffset = 0;
         int t0   = ((in[inOffset++]       ) << 24 |
@@ -412,12 +425,20 @@
         out[outOffset  ] = (byte)(S[(t2       ) & 0xFF] ^ (tt       ));
     }
 
-
     /**
      * Decrypt exactly one block of plaintext.
      */
     void decryptBlock(byte[] in, int inOffset,
-                              byte[] out, int outOffset)
+                      byte[] out, int outOffset) {
+        cryptBlockCheck(in, inOffset);
+        cryptBlockCheck(out, outOffset);
+        implDecryptBlock(in, inOffset, out, outOffset);
+    }
+
+    // Decrypt operation. Possibly replaced with a compiler intrinsic.
+    @HotSpotIntrinsicCandidate
+    private void implDecryptBlock(byte[] in, int inOffset,
+                                  byte[] out, int outOffset)
     {
         int keyOffset = 4;
         int t0 = ((in[inOffset++]       ) << 24 |
@@ -572,6 +593,25 @@
         out[outOffset  ] = (byte)(Si[(a0       ) & 0xFF] ^ (t1       ));
     }
 
+    // Used to perform all checks required by the Java semantics
+    // (i.e., null checks and bounds checks) on the input parameters
+    // to encryptBlock and to decryptBlock.
+    // Normally, the Java Runtime performs these checks, however, as
+    // encryptBlock and decryptBlock are possibly replaced with
+    // compiler intrinsics, the JDK performs the required checks instead.
+    // Does not check accesses to class-internal (private) arrays.
+    private static void cryptBlockCheck(byte[] array, int offset) {
+        Objects.requireNonNull(array);
+
+        if (offset < 0 || offset >= array.length) {
+            throw new ArrayIndexOutOfBoundsException(offset);
+        }
+
+        int largestIndex = offset + AES_BLOCK_SIZE - 1;
+        if (largestIndex < 0 || largestIndex >= array.length) {
+            throw new ArrayIndexOutOfBoundsException(largestIndex);
+        }
+    }
 
     /**
      * Expand a user-supplied key material into a session key.
--- a/jdk/src/java.base/share/classes/com/sun/crypto/provider/CipherBlockChaining.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/com/sun/crypto/provider/CipherBlockChaining.java	Wed Jul 05 20:42:36 2017 +0200
@@ -27,6 +27,9 @@
 
 import java.security.InvalidKeyException;
 import java.security.ProviderException;
+import java.util.Objects;
+
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 
 /**
@@ -138,15 +141,22 @@
      * @return the length of the encrypted data
      */
     int encrypt(byte[] plain, int plainOffset, int plainLen,
-                byte[] cipher, int cipherOffset)
+                byte[] cipher, int cipherOffset) {
+        cryptBlockSizeCheck(plainLen);
+        cryptNullAndBoundsCheck(plain, plainOffset, plainLen);
+        cryptNullAndBoundsCheck(cipher, cipherOffset, plainLen);
+        return implEncrypt(plain, plainOffset, plainLen,
+                           cipher, cipherOffset);
+    }
+
+    @HotSpotIntrinsicCandidate
+    private int implEncrypt(byte[] plain, int plainOffset, int plainLen,
+                            byte[] cipher, int cipherOffset)
     {
-        if ((plainLen % blockSize) != 0) {
-            throw new ProviderException("Internal error in input buffering");
-        }
         int endIndex = plainOffset + plainLen;
 
         for (; plainOffset < endIndex;
-             plainOffset+=blockSize, cipherOffset += blockSize) {
+             plainOffset += blockSize, cipherOffset += blockSize) {
             for (int i = 0; i < blockSize; i++) {
                 k[i] = (byte)(plain[i + plainOffset] ^ r[i]);
             }
@@ -179,11 +189,17 @@
      * @return the length of the decrypted data
      */
     int decrypt(byte[] cipher, int cipherOffset, int cipherLen,
-                byte[] plain, int plainOffset)
+                byte[] plain, int plainOffset) {
+        cryptBlockSizeCheck(cipherLen);
+        cryptNullAndBoundsCheck(cipher, cipherOffset, cipherLen);
+        cryptNullAndBoundsCheck(plain, plainOffset, cipherLen);
+        return implDecrypt(cipher, cipherOffset, cipherLen, plain, plainOffset);
+    }
+
+    @HotSpotIntrinsicCandidate
+    private int implDecrypt(byte[] cipher, int cipherOffset, int cipherLen,
+                            byte[] plain, int plainOffset)
     {
-        if ((cipherLen % blockSize) != 0) {
-            throw new ProviderException("Internal error in input buffering");
-        }
         int endIndex = cipherOffset + cipherLen;
 
         for (; cipherOffset < endIndex;
@@ -196,4 +212,27 @@
         }
         return cipherLen;
     }
+
+    private void cryptBlockSizeCheck(int len) {
+        if ((len % blockSize) != 0) {
+            throw new ProviderException("Internal error in input buffering");
+        }
+    }
+
+    private static void cryptNullAndBoundsCheck(byte[] array, int offset, int len) {
+        if (len <= 0) {
+            return; // not an error because cryptImpl/decryptImpl won't execute if len <= 0
+        }
+
+        Objects.requireNonNull(array);
+
+        if (offset < 0 || offset >= array.length) {
+            throw new ArrayIndexOutOfBoundsException(offset);
+        }
+
+        int endIndex = offset + len - 1;
+        if (endIndex < 0 || endIndex >= array.length) {
+            throw new ArrayIndexOutOfBoundsException(endIndex);
+        }
+    }
 }
--- a/jdk/src/java.base/share/classes/com/sun/crypto/provider/CipherCore.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/com/sun/crypto/provider/CipherCore.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2002, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2002, 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
@@ -568,7 +568,7 @@
                 // check key+iv for encryption in GCM mode
                 requireReinit =
                     Arrays.equals(ivBytes, lastEncIv) &&
-                    Arrays.equals(keyBytes, lastEncKey);
+                    MessageDigest.isEqual(keyBytes, lastEncKey);
                 if (requireReinit) {
                     throw new InvalidAlgorithmParameterException
                         ("Cannot reuse iv for GCM encryption");
--- a/jdk/src/java.base/share/classes/com/sun/crypto/provider/DESKey.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/com/sun/crypto/provider/DESKey.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 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
@@ -25,6 +25,7 @@
 
 package com.sun.crypto.provider;
 
+import java.security.MessageDigest;
 import java.security.KeyRep;
 import java.security.InvalidKeyException;
 import javax.crypto.SecretKey;
@@ -113,7 +114,7 @@
             return false;
 
         byte[] thatKey = ((SecretKey)obj).getEncoded();
-        boolean ret = java.util.Arrays.equals(this.key, thatKey);
+        boolean ret = MessageDigest.isEqual(this.key, thatKey);
         java.util.Arrays.fill(thatKey, (byte)0x00);
         return ret;
     }
--- a/jdk/src/java.base/share/classes/com/sun/crypto/provider/DESedeKey.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/com/sun/crypto/provider/DESedeKey.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 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
@@ -25,6 +25,7 @@
 
 package com.sun.crypto.provider;
 
+import java.security.MessageDigest;
 import java.security.KeyRep;
 import java.security.InvalidKeyException;
 import javax.crypto.SecretKey;
@@ -114,7 +115,7 @@
             return false;
 
         byte[] thatKey = ((SecretKey)obj).getEncoded();
-        boolean ret = java.util.Arrays.equals(this.key, thatKey);
+        boolean ret = MessageDigest.isEqual(this.key, thatKey);
         java.util.Arrays.fill(thatKey, (byte)0x00);
         return ret;
     }
--- a/jdk/src/java.base/share/classes/com/sun/crypto/provider/GHASH.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/com/sun/crypto/provider/GHASH.java	Wed Jul 05 20:42:36 2017 +0200
@@ -31,6 +31,8 @@
 
 import java.security.ProviderException;
 
+import jdk.internal.HotSpotIntrinsicCandidate;
+
 /**
  * This class represents the GHASH function defined in NIST 800-38D
  * under section 6.4. It needs to be constructed w/ a hash subkey, i.e.
@@ -227,6 +229,7 @@
      * the hotspot signature.  This method and methods called by it, cannot
      * throw exceptions or allocate arrays as it will breaking intrinsics
      */
+    @HotSpotIntrinsicCandidate
     private static void processBlocks(byte[] data, int inOfs, int blocks, long[] st, long[] subH) {
         int offset = inOfs;
         while (blocks > 0) {
--- a/jdk/src/java.base/share/classes/com/sun/crypto/provider/PBEKey.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/com/sun/crypto/provider/PBEKey.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 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
@@ -25,6 +25,7 @@
 
 package com.sun.crypto.provider;
 
+import java.security.MessageDigest;
 import java.security.KeyRep;
 import java.security.spec.InvalidKeySpecException;
 import java.util.Locale;
@@ -108,7 +109,7 @@
             return false;
 
         byte[] thatEncoded = that.getEncoded();
-        boolean ret = java.util.Arrays.equals(this.key, thatEncoded);
+        boolean ret = MessageDigest.isEqual(this.key, thatEncoded);
         java.util.Arrays.fill(thatEncoded, (byte)0x00);
         return ret;
     }
--- a/jdk/src/java.base/share/classes/com/sun/crypto/provider/PBKDF2KeyImpl.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/com/sun/crypto/provider/PBKDF2KeyImpl.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -31,6 +31,7 @@
 import java.nio.charset.Charset;
 import java.util.Arrays;
 import java.util.Locale;
+import java.security.MessageDigest;
 import java.security.KeyRep;
 import java.security.GeneralSecurityException;
 import java.security.NoSuchAlgorithmException;
@@ -153,7 +154,7 @@
                     SecretKey sk = (SecretKey)obj;
                     return prf.getAlgorithm().equalsIgnoreCase(
                         sk.getAlgorithm()) &&
-                        Arrays.equals(password, sk.getEncoded());
+                        MessageDigest.isEqual(password, sk.getEncoded());
                 }
             };
             prf.init(macKey);
@@ -239,7 +240,7 @@
         if (!(that.getFormat().equalsIgnoreCase("RAW")))
             return false;
         byte[] thatEncoded = that.getEncoded();
-        boolean ret = Arrays.equals(key, that.getEncoded());
+        boolean ret = MessageDigest.isEqual(key, that.getEncoded());
         java.util.Arrays.fill(thatEncoded, (byte)0x00);
         return ret;
     }
--- a/jdk/src/java.base/share/classes/java/io/ObjectInputStream.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/io/ObjectInputStream.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1832,6 +1832,8 @@
         throws IOException
     {
         SerialCallbackContext oldContext = curContext;
+        if (oldContext != null)
+            oldContext.check();
         curContext = null;
         try {
             boolean blocked = desc.hasBlockExternalData();
@@ -1856,6 +1858,8 @@
                 skipCustomData();
             }
         } finally {
+            if (oldContext != null)
+                oldContext.check();
             curContext = oldContext;
         }
         /*
@@ -1906,12 +1910,12 @@
             ObjectStreamClass slotDesc = slots[i].desc;
 
             if (slots[i].hasData) {
-                if (obj != null &&
-                    slotDesc.hasReadObjectMethod() &&
-                    handles.lookupException(passHandle) == null)
-                {
+                if (obj == null || handles.lookupException(passHandle) != null) {
+                    defaultReadFields(null, slotDesc); // skip field values
+                } else if (slotDesc.hasReadObjectMethod()) {
                     SerialCallbackContext oldContext = curContext;
-
+                    if (oldContext != null)
+                        oldContext.check();
                     try {
                         curContext = new SerialCallbackContext(obj, slotDesc);
 
@@ -1928,6 +1932,8 @@
                         handles.markException(passHandle, ex);
                     } finally {
                         curContext.setUsed();
+                        if (oldContext!= null)
+                            oldContext.check();
                         curContext = oldContext;
                     }
 
@@ -1946,6 +1952,7 @@
                         defaultSetFieldValues(obj, slotDesc, vals);
                     }
                 }
+
                 if (slotDesc.hasWriteObjectData()) {
                     skipCustomData();
                 } else {
--- a/jdk/src/java.base/share/classes/java/io/SerialCallbackContext.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/io/SerialCallbackContext.java	Wed Jul 05 20:42:36 2017 +0200
@@ -60,6 +60,13 @@
         return desc;
     }
 
+    public void check() throws NotActiveException {
+        if (thread != null && thread != Thread.currentThread()) {
+            throw new NotActiveException(
+                "expected thread: " + thread + ", but got: " + Thread.currentThread());
+        }
+    }
+
     public void checkAndSetUsed() throws NotActiveException {
         if (thread != Thread.currentThread()) {
              throw new NotActiveException(
--- a/jdk/src/java.base/share/classes/java/lang/Boolean.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/Boolean.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,6 +25,8 @@
 
 package java.lang;
 
+import jdk.internal.HotSpotIntrinsicCandidate;
+
 /**
  * The Boolean class wraps a value of the primitive type
  * {@code boolean} in an object. An object of type
@@ -128,6 +130,7 @@
      *
      * @return  the primitive {@code boolean} value of this object.
      */
+    @HotSpotIntrinsicCandidate
     public boolean booleanValue() {
         return value;
     }
@@ -146,6 +149,7 @@
      * @return a {@code Boolean} instance representing {@code b}.
      * @since  1.4
      */
+    @HotSpotIntrinsicCandidate
     public static Boolean valueOf(boolean b) {
         return (b ? TRUE : FALSE);
     }
--- a/jdk/src/java.base/share/classes/java/lang/Byte.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/Byte.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,6 +25,8 @@
 
 package java.lang;
 
+import jdk.internal.HotSpotIntrinsicCandidate;
+
 /**
  *
  * The {@code Byte} class wraps a value of primitive type {@code byte}
@@ -98,6 +100,7 @@
      * @return a {@code Byte} instance representing {@code b}.
      * @since  1.5
      */
+    @HotSpotIntrinsicCandidate
     public static Byte valueOf(byte b) {
         final int offset = 128;
         return ByteCache.cache[(int)b + offset];
@@ -320,6 +323,7 @@
      * Returns the value of this {@code Byte} as a
      * {@code byte}.
      */
+    @HotSpotIntrinsicCandidate
     public byte byteValue() {
         return value;
     }
--- a/jdk/src/java.base/share/classes/java/lang/Character.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/Character.java	Wed Jul 05 20:42:36 2017 +0200
@@ -30,6 +30,8 @@
 import java.util.HashMap;
 import java.util.Locale;
 
+import jdk.internal.HotSpotIntrinsicCandidate;
+
 /**
  * The {@code Character} class wraps a value of the primitive
  * type {@code char} in an object. An object of type
@@ -40,7 +42,7 @@
  * a character's category (lowercase letter, digit, etc.) and for converting
  * characters from uppercase to lowercase and vice versa.
  * <p>
- * Character information is based on the Unicode Standard, version 6.2.0.
+ * Character information is based on the Unicode Standard, version 7.0.0.
  * <p>
  * The methods and data of class {@code Character} are defined by
  * the information in the <i>UnicodeData</i> file that is part of the
@@ -490,6 +492,30 @@
     public static final byte DIRECTIONALITY_POP_DIRECTIONAL_FORMAT = 18;
 
     /**
+     * Weak bidirectional character type "LRI" in the Unicode specification.
+     * @since 1.9
+     */
+    public static final byte DIRECTIONALITY_LEFT_TO_RIGHT_ISOLATE = 19;
+
+    /**
+     * Weak bidirectional character type "RLI" in the Unicode specification.
+     * @since 1.9
+     */
+    public static final byte DIRECTIONALITY_RIGHT_TO_LEFT_ISOLATE = 20;
+
+    /**
+     * Weak bidirectional character type "FSI" in the Unicode specification.
+     * @since 1.9
+     */
+    public static final byte DIRECTIONALITY_FIRST_STRONG_ISOLATE = 21;
+
+    /**
+     * Weak bidirectional character type "PDI" in the Unicode specification.
+     * @since 1.9
+     */
+    public static final byte DIRECTIONALITY_POP_DIRECTIONAL_ISOLATE = 22;
+
+    /**
      * The minimum value of a
      * <a href="http://www.unicode.org/glossary/#high_surrogate_code_unit">
      * Unicode high-surrogate code unit</a>
@@ -2561,6 +2587,269 @@
                              "ARABIC MATHEMATICAL ALPHABETIC SYMBOLS",
                              "ARABICMATHEMATICALALPHABETICSYMBOLS");
 
+        /**
+         * Constant for the "Combining Diacritical Marks Extended" Unicode
+         * character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock COMBINING_DIACRITICAL_MARKS_EXTENDED =
+            new UnicodeBlock("COMBINING_DIACRITICAL_MARKS_EXTENDED",
+                             "COMBINING DIACRITICAL MARKS EXTENDED",
+                             "COMBININGDIACRITICALMARKSEXTENDED");
+
+        /**
+         * Constant for the "Myanmar Extended-B" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock MYANMAR_EXTENDED_B =
+            new UnicodeBlock("MYANMAR_EXTENDED_B",
+                             "MYANMAR EXTENDED-B",
+                             "MYANMAREXTENDED-B");
+
+        /**
+         * Constant for the "Latin Extended-E" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock LATIN_EXTENDED_E =
+            new UnicodeBlock("LATIN_EXTENDED_E",
+                             "LATIN EXTENDED-E",
+                             "LATINEXTENDED-E");
+
+        /**
+         * Constant for the "Coptic Epact Numbers" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock COPTIC_EPACT_NUMBERS =
+            new UnicodeBlock("COPTIC_EPACT_NUMBERS",
+                             "COPTIC EPACT NUMBERS",
+                             "COPTICEPACTNUMBERS");
+
+        /**
+         * Constant for the "Old Permic" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock OLD_PERMIC =
+            new UnicodeBlock("OLD_PERMIC",
+                             "OLD PERMIC",
+                             "OLDPERMIC");
+
+        /**
+         * Constant for the "Elbasan" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock ELBASAN =
+            new UnicodeBlock("ELBASAN");
+
+        /**
+         * Constant for the "Caucasian Albanian" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock CAUCASIAN_ALBANIAN =
+            new UnicodeBlock("CAUCASIAN_ALBANIAN",
+                             "CAUCASIAN ALBANIAN",
+                             "CAUCASIANALBANIAN");
+
+        /**
+         * Constant for the "Linear A" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock LINEAR_A =
+            new UnicodeBlock("LINEAR_A",
+                             "LINEAR A",
+                             "LINEARA");
+
+        /**
+         * Constant for the "Palmyrene" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock PALMYRENE =
+            new UnicodeBlock("PALMYRENE");
+
+        /**
+         * Constant for the "Nabataean" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock NABATAEAN =
+            new UnicodeBlock("NABATAEAN");
+
+        /**
+         * Constant for the "Old North Arabian" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock OLD_NORTH_ARABIAN =
+            new UnicodeBlock("OLD_NORTH_ARABIAN",
+                             "OLD NORTH ARABIAN",
+                             "OLDNORTHARABIAN");
+
+        /**
+         * Constant for the "Manichaean" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock MANICHAEAN =
+            new UnicodeBlock("MANICHAEAN");
+
+        /**
+         * Constant for the "Psalter Pahlavi" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock PSALTER_PAHLAVI =
+            new UnicodeBlock("PSALTER_PAHLAVI",
+                             "PSALTER PAHLAVI",
+                             "PSALTERPAHLAVI");
+
+        /**
+         * Constant for the "Mahajani" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock MAHAJANI =
+            new UnicodeBlock("MAHAJANI");
+
+        /**
+         * Constant for the "Sinhala Archaic Numbers" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock SINHALA_ARCHAIC_NUMBERS =
+            new UnicodeBlock("SINHALA_ARCHAIC_NUMBERS",
+                             "SINHALA ARCHAIC NUMBERS",
+                             "SINHALAARCHAICNUMBERS");
+
+        /**
+         * Constant for the "Khojki" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock KHOJKI =
+            new UnicodeBlock("KHOJKI");
+
+        /**
+         * Constant for the "Khudawadi" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock KHUDAWADI =
+            new UnicodeBlock("KHUDAWADI");
+
+        /**
+         * Constant for the "Grantha" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock GRANTHA =
+            new UnicodeBlock("GRANTHA");
+
+        /**
+         * Constant for the "Tirhuta" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock TIRHUTA =
+            new UnicodeBlock("TIRHUTA");
+
+        /**
+         * Constant for the "Siddham" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock SIDDHAM =
+            new UnicodeBlock("SIDDHAM");
+
+        /**
+         * Constant for the "Modi" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock MODI =
+            new UnicodeBlock("MODI");
+
+        /**
+         * Constant for the "Warang Citi" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock WARANG_CITI =
+            new UnicodeBlock("WARANG_CITI",
+                             "WARANG CITI",
+                             "WARANGCITI");
+
+        /**
+         * Constant for the "Pau Cin Hau" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock PAU_CIN_HAU =
+            new UnicodeBlock("PAU_CIN_HAU",
+                             "PAU CIN HAU",
+                             "PAUCINHAU");
+
+        /**
+         * Constant for the "Mro" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock MRO =
+            new UnicodeBlock("MRO");
+
+        /**
+         * Constant for the "Bassa Vah" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock BASSA_VAH =
+            new UnicodeBlock("BASSA_VAH",
+                             "BASSA VAH",
+                             "BASSAVAH");
+
+        /**
+         * Constant for the "Pahawh Hmong" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock PAHAWH_HMONG =
+            new UnicodeBlock("PAHAWH_HMONG",
+                             "PAHAWH HMONG",
+                             "PAHAWHHMONG");
+
+        /**
+         * Constant for the "Duployan" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock DUPLOYAN =
+            new UnicodeBlock("DUPLOYAN");
+
+        /**
+         * Constant for the "Shorthand Format Controls" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock SHORTHAND_FORMAT_CONTROLS =
+            new UnicodeBlock("SHORTHAND_FORMAT_CONTROLS",
+                             "SHORTHAND FORMAT CONTROLS",
+                             "SHORTHANDFORMATCONTROLS");
+
+        /**
+         * Constant for the "Mende Kikakui" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock MENDE_KIKAKUI =
+            new UnicodeBlock("MENDE_KIKAKUI",
+                             "MENDE KIKAKUI",
+                             "MENDEKIKAKUI");
+
+        /**
+         * Constant for the "Ornamental Dingbats" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock ORNAMENTAL_DINGBATS =
+            new UnicodeBlock("ORNAMENTAL_DINGBATS",
+                             "ORNAMENTAL DINGBATS",
+                             "ORNAMENTALDINGBATS");
+
+        /**
+         * Constant for the "Geometric Shapes Extended" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock GEOMETRIC_SHAPES_EXTENDED =
+            new UnicodeBlock("GEOMETRIC_SHAPES_EXTENDED",
+                             "GEOMETRIC SHAPES EXTENDED",
+                             "GEOMETRICSHAPESEXTENDED");
+
+        /**
+         * Constant for the "Supplemental Arrows-C" Unicode character block.
+         * @since 1.9
+         */
+        public static final UnicodeBlock SUPPLEMENTAL_ARROWS_C =
+            new UnicodeBlock("SUPPLEMENTAL_ARROWS_C",
+                             "SUPPLEMENTAL ARROWS-C",
+                             "SUPPLEMENTALARROWS-C");
+
         private static final int blockStarts[] = {
             0x0000,   // 0000..007F; Basic Latin
             0x0080,   // 0080..00FF; Latin-1 Supplement
@@ -2618,7 +2907,7 @@
             0x19E0,   // 19E0..19FF; Khmer Symbols
             0x1A00,   // 1A00..1A1F; Buginese
             0x1A20,   // 1A20..1AAF; Tai Tham
-            0x1AB0,   //             unassigned
+            0x1AB0,   // 1AB0..1AFF; Combining Diacritical Marks Extended
             0x1B00,   // 1B00..1B7F; Balinese
             0x1B80,   // 1B80..1BBF; Sundanese
             0x1BC0,   // 1BC0..1BFF; Batak
@@ -2699,13 +2988,14 @@
             0xA930,   // A930..A95F; Rejang
             0xA960,   // A960..A97F; Hangul Jamo Extended-A
             0xA980,   // A980..A9DF; Javanese
-            0xA9E0,   //             unassigned
+            0xA9E0,   // A9E0..A9FF; Myanmar Extended-B
             0xAA00,   // AA00..AA5F; Cham
             0xAA60,   // AA60..AA7F; Myanmar Extended-A
             0xAA80,   // AA80..AADF; Tai Viet
             0xAAE0,   // AAE0..AAFF; Meetei Mayek Extensions
             0xAB00,   // AB00..AB2F; Ethiopic Extended-A
-            0xAB30,   //             unassigned
+            0xAB30,   // AB30..AB6F; Latin Extended-E
+            0xAB70,   //             unassigned
             0xABC0,   // ABC0..ABFF; Meetei Mayek
             0xAC00,   // AC00..D7AF; Hangul Syllables
             0xD7B0,   // D7B0..D7FF; Hangul Jamo Extended-B
@@ -2733,10 +3023,10 @@
             0x10200,  //               unassigned
             0x10280,  // 10280..1029F; Lycian
             0x102A0,  // 102A0..102DF; Carian
-            0x102E0,  //               unassigned
+            0x102E0,  // 102E0..102FF; Coptic Epact Numbers
             0x10300,  // 10300..1032F; Old Italic
             0x10330,  // 10330..1034F; Gothic
-            0x10350,  //               unassigned
+            0x10350,  // 10350..1037F; Old Permic
             0x10380,  // 10380..1039F; Ugaritic
             0x103A0,  // 103A0..103DF; Old Persian
             0x103E0,  //               unassigned
@@ -2744,9 +3034,16 @@
             0x10450,  // 10450..1047F; Shavian
             0x10480,  // 10480..104AF; Osmanya
             0x104B0,  //               unassigned
+            0x10500,  // 10500..1052F; Elbasan
+            0x10530,  // 10530..1056F; Caucasian Albanian
+            0x10570,  //               unassigned
+            0x10600,  // 10600..1077F; Linear A
+            0x10780,  //               unassigned
             0x10800,  // 10800..1083F; Cypriot Syllabary
             0x10840,  // 10840..1085F; Imperial Aramaic
-            0x10860,  //               unassigned
+            0x10860,  // 10860..1087F; Palmyrene
+            0x10880,  // 10880..108AF; Nabataean
+            0x108B0,  //               unassigned
             0x10900,  // 10900..1091F; Phoenician
             0x10920,  // 10920..1093F; Lydian
             0x10940,  //               unassigned
@@ -2754,11 +3051,14 @@
             0x109A0,  // 109A0..109FF; Meroitic Cursive
             0x10A00,  // 10A00..10A5F; Kharoshthi
             0x10A60,  // 10A60..10A7F; Old South Arabian
-            0x10A80,  //               unassigned
+            0x10A80,  // 10A80..10A9F; Old North Arabian
+            0x10AA0,  //               unassigned
+            0x10AC0,  // 10AC0..10AFF; Manichaean
             0x10B00,  // 10B00..10B3F; Avestan
             0x10B40,  // 10B40..10B5F; Inscriptional Parthian
             0x10B60,  // 10B60..10B7F; Inscriptional Pahlavi
-            0x10B80,  //               unassigned
+            0x10B80,  // 10B80..10BAF; Psalter Pahlavi
+            0x10BB0,  //               unassigned
             0x10C00,  // 10C00..10C4F; Old Turkic
             0x10C50,  //               unassigned
             0x10E60,  // 10E60..10E7F; Rumi Numeral Symbols
@@ -2767,22 +3067,43 @@
             0x11080,  // 11080..110CF; Kaithi
             0x110D0,  // 110D0..110FF; Sora Sompeng
             0x11100,  // 11100..1114F; Chakma
-            0x11150,  //               unassigned
+            0x11150,  // 11150..1117F; Mahajani
             0x11180,  // 11180..111DF; Sharada
-            0x111E0,  //               unassigned
+            0x111E0,  // 111E0..111FF; Sinhala Archaic Numbers
+            0x11200,  // 11200..1124F; Khojki
+            0x11250,  //               unassigned
+            0x112B0,  // 112B0..112FF; Khudawadi
+            0x11300,  // 11300..1137F; Grantha
+            0x11380,  //               unassigned
+            0x11480,  // 11480..114DF; Tirhuta
+            0x114E0,  //               unassigned
+            0x11580,  // 11580..115FF; Siddham
+            0x11600,  // 11600..1165F; Modi
+            0x11660,  //               unassigned
             0x11680,  // 11680..116CF; Takri
             0x116D0,  //               unassigned
+            0x118A0,  // 118A0..118FF; Warang Citi
+            0x11900,  //               unassigned
+            0x11AC0,  // 11AC0..11AFF; Pau Cin Hau
+            0x11B00,  //               unassigned
             0x12000,  // 12000..123FF; Cuneiform
             0x12400,  // 12400..1247F; Cuneiform Numbers and Punctuation
             0x12480,  //               unassigned
             0x13000,  // 13000..1342F; Egyptian Hieroglyphs
             0x13430,  //               unassigned
             0x16800,  // 16800..16A3F; Bamum Supplement
-            0x16A40,  //               unassigned
+            0x16A40,  // 16A40..16A6F; Mro
+            0x16A70,  //               unassigned
+            0x16AD0,  // 16AD0..16AFF; Bassa Vah
+            0x16B00,  // 16B00..16B8F; Pahawh Hmong
+            0x16B90,  //               unassigned
             0x16F00,  // 16F00..16F9F; Miao
             0x16FA0,  //               unassigned
             0x1B000,  // 1B000..1B0FF; Kana Supplement
             0x1B100,  //               unassigned
+            0x1BC00,  // 1BC00..1BC9F; Duployan
+            0x1BCA0,  // 1BCA0..1BCAF; Shorthand Format Controls
+            0x1BCB0,  //               unassigned
             0x1D000,  // 1D000..1D0FF; Byzantine Musical Symbols
             0x1D100,  // 1D100..1D1FF; Musical Symbols
             0x1D200,  // 1D200..1D24F; Ancient Greek Musical Notation
@@ -2792,6 +3113,8 @@
             0x1D380,  //               unassigned
             0x1D400,  // 1D400..1D7FF; Mathematical Alphanumeric Symbols
             0x1D800,  //               unassigned
+            0x1E800,  // 1E800..1E8DF; Mende Kikakui
+            0x1E8E0,  //               unassigned
             0x1EE00,  // 1EE00..1EEFF; Arabic Mathematical Alphabetic Symbols
             0x1EF00,  //               unassigned
             0x1F000,  // 1F000..1F02F; Mahjong Tiles
@@ -2801,10 +3124,12 @@
             0x1F200,  // 1F200..1F2FF; Enclosed Ideographic Supplement
             0x1F300,  // 1F300..1F5FF; Miscellaneous Symbols And Pictographs
             0x1F600,  // 1F600..1F64F; Emoticons
-            0x1F650,  //               unassigned
+            0x1F650,  // 1F650..1F67F; Ornamental Dingbats
             0x1F680,  // 1F680..1F6FF; Transport And Map Symbols
             0x1F700,  // 1F700..1F77F; Alchemical Symbols
-            0x1F780,  //               unassigned
+            0x1F780,  // 1F780..1F7FF; Geometric Shapes Extended
+            0x1F800,  // 1F800..1F8FF; Supplemental Arrows-C
+            0x1F900,  //               unassigned
             0x20000,  // 20000..2A6DF; CJK Unified Ideographs Extension B
             0x2A6E0,  //               unassigned
             0x2A700,  // 2A700..2B73F; CJK Unified Ideographs Extension C
@@ -2877,7 +3202,7 @@
             KHMER_SYMBOLS,
             BUGINESE,
             TAI_THAM,
-            null,
+            COMBINING_DIACRITICAL_MARKS_EXTENDED,
             BALINESE,
             SUNDANESE,
             BATAK,
@@ -2958,12 +3283,13 @@
             REJANG,
             HANGUL_JAMO_EXTENDED_A,
             JAVANESE,
-            null,
+            MYANMAR_EXTENDED_B,
             CHAM,
             MYANMAR_EXTENDED_A,
             TAI_VIET,
             MEETEI_MAYEK_EXTENSIONS,
             ETHIOPIC_EXTENDED_A,
+            LATIN_EXTENDED_E,
             null,
             MEETEI_MAYEK,
             HANGUL_SYLLABLES,
@@ -2992,10 +3318,10 @@
             null,
             LYCIAN,
             CARIAN,
-            null,
+            COPTIC_EPACT_NUMBERS,
             OLD_ITALIC,
             GOTHIC,
-            null,
+            OLD_PERMIC,
             UGARITIC,
             OLD_PERSIAN,
             null,
@@ -3003,8 +3329,15 @@
             SHAVIAN,
             OSMANYA,
             null,
+            ELBASAN,
+            CAUCASIAN_ALBANIAN,
+            null,
+            LINEAR_A,
+            null,
             CYPRIOT_SYLLABARY,
             IMPERIAL_ARAMAIC,
+            PALMYRENE,
+            NABATAEAN,
             null,
             PHOENICIAN,
             LYDIAN,
@@ -3013,10 +3346,13 @@
             MEROITIC_CURSIVE,
             KHAROSHTHI,
             OLD_SOUTH_ARABIAN,
+            OLD_NORTH_ARABIAN,
             null,
+            MANICHAEAN,
             AVESTAN,
             INSCRIPTIONAL_PARTHIAN,
             INSCRIPTIONAL_PAHLAVI,
+            PSALTER_PAHLAVI,
             null,
             OLD_TURKIC,
             null,
@@ -3026,22 +3362,43 @@
             KAITHI,
             SORA_SOMPENG,
             CHAKMA,
+            MAHAJANI,
+            SHARADA,
+            SINHALA_ARCHAIC_NUMBERS,
+            KHOJKI,
             null,
-            SHARADA,
+            KHUDAWADI,
+            GRANTHA,
+            null,
+            TIRHUTA,
+            null,
+            SIDDHAM,
+            MODI,
             null,
             TAKRI,
             null,
+            WARANG_CITI,
+            null,
+            PAU_CIN_HAU,
+            null,
             CUNEIFORM,
             CUNEIFORM_NUMBERS_AND_PUNCTUATION,
             null,
             EGYPTIAN_HIEROGLYPHS,
             null,
             BAMUM_SUPPLEMENT,
+            MRO,
+            null,
+            BASSA_VAH,
+            PAHAWH_HMONG,
             null,
             MIAO,
             null,
             KANA_SUPPLEMENT,
             null,
+            DUPLOYAN,
+            SHORTHAND_FORMAT_CONTROLS,
+            null,
             BYZANTINE_MUSICAL_SYMBOLS,
             MUSICAL_SYMBOLS,
             ANCIENT_GREEK_MUSICAL_NOTATION,
@@ -3051,6 +3408,8 @@
             null,
             MATHEMATICAL_ALPHANUMERIC_SYMBOLS,
             null,
+            MENDE_KIKAKUI,
+            null,
             ARABIC_MATHEMATICAL_ALPHABETIC_SYMBOLS,
             null,
             MAHJONG_TILES,
@@ -3060,9 +3419,11 @@
             ENCLOSED_IDEOGRAPHIC_SUPPLEMENT,
             MISCELLANEOUS_SYMBOLS_AND_PICTOGRAPHS,
             EMOTICONS,
-            null,
+            ORNAMENTAL_DINGBATS,
             TRANSPORT_AND_MAP_SYMBOLS,
             ALCHEMICAL_SYMBOLS,
+            GEOMETRIC_SHAPES_EXTENDED,
+            SUPPLEMENTAL_ARROWS_C,
             null,
             CJK_UNIFIED_IDEOGRAPHS_EXTENSION_B,
             null,
@@ -3675,40 +4036,185 @@
 
         /**
          * Unicode script "Meroitic Hieroglyphs".
+         * @since 1.8
          */
         MEROITIC_HIEROGLYPHS,
 
         /**
          * Unicode script "Meroitic Cursive".
+         * @since 1.8
          */
         MEROITIC_CURSIVE,
 
         /**
          * Unicode script "Sora Sompeng".
+         * @since 1.8
          */
         SORA_SOMPENG,
 
         /**
          * Unicode script "Chakma".
+         * @since 1.8
          */
         CHAKMA,
 
         /**
          * Unicode script "Sharada".
+         * @since 1.8
          */
         SHARADA,
 
         /**
          * Unicode script "Takri".
+         * @since 1.8
          */
         TAKRI,
 
         /**
          * Unicode script "Miao".
+         * @since 1.8
          */
         MIAO,
 
         /**
+         * Unicode script "Caucasian Albanian".
+         * @since 1.9
+         */
+        CAUCASIAN_ALBANIAN,
+
+        /**
+         * Unicode script "Bassa Vah".
+         * @since 1.9
+         */
+        BASSA_VAH,
+
+        /**
+         * Unicode script "Duployan".
+         * @since 1.9
+         */
+        DUPLOYAN,
+
+        /**
+         * Unicode script "Elbasan".
+         * @since 1.9
+         */
+        ELBASAN,
+
+        /**
+         * Unicode script "Grantha".
+         * @since 1.9
+         */
+        GRANTHA,
+
+        /**
+         * Unicode script "Pahawh Hmong".
+         * @since 1.9
+         */
+        PAHAWH_HMONG,
+
+        /**
+         * Unicode script "Khojki".
+         * @since 1.9
+         */
+        KHOJKI,
+
+        /**
+         * Unicode script "Linear A".
+         * @since 1.9
+         */
+        LINEAR_A,
+
+        /**
+         * Unicode script "Mahajani".
+         * @since 1.9
+         */
+        MAHAJANI,
+
+        /**
+         * Unicode script "Manichaean".
+         * @since 1.9
+         */
+        MANICHAEAN,
+
+        /**
+         * Unicode script "Mende Kikakui".
+         * @since 1.9
+         */
+        MENDE_KIKAKUI,
+
+        /**
+         * Unicode script "Modi".
+         * @since 1.9
+         */
+        MODI,
+
+        /**
+         * Unicode script "Mro".
+         * @since 1.9
+         */
+        MRO,
+
+        /**
+         * Unicode script "Old North Arabian".
+         * @since 1.9
+         */
+        OLD_NORTH_ARABIAN,
+
+        /**
+         * Unicode script "Nabataean".
+         * @since 1.9
+         */
+        NABATAEAN,
+
+        /**
+         * Unicode script "Palmyrene".
+         * @since 1.9
+         */
+        PALMYRENE,
+
+        /**
+         * Unicode script "Pau Cin Hau".
+         * @since 1.9
+         */
+        PAU_CIN_HAU,
+
+        /**
+         * Unicode script "Old Permic".
+         * @since 1.9
+         */
+        OLD_PERMIC,
+
+        /**
+         * Unicode script "Psalter Pahlavi".
+         * @since 1.9
+         */
+        PSALTER_PAHLAVI,
+
+        /**
+         * Unicode script "Siddham".
+         * @since 1.9
+         */
+        SIDDHAM,
+
+        /**
+         * Unicode script "Khudawadi".
+         * @since 1.9
+         */
+        KHUDAWADI,
+
+        /**
+         * Unicode script "Tirhuta".
+         * @since 1.9
+         */
+        TIRHUTA,
+
+        /**
+         * Unicode script "Warang Citi".
+         * @since 1.9
+         */
+        WARANG_CITI,
+
+        /**
          * Unicode script "Unknown".
          */
         UNKNOWN;
@@ -3719,14 +4225,14 @@
             0x005B,   // 005B..0060; COMMON
             0x0061,   // 0061..007A; LATIN
             0x007B,   // 007B..00A9; COMMON
-            0x00AA,   // 00AA..00AA; LATIN
+            0x00AA,   // 00AA      ; LATIN
             0x00AB,   // 00AB..00B9; COMMON
-            0x00BA,   // 00BA..00BA; LATIN
+            0x00BA,   // 00BA      ; LATIN
             0x00BB,   // 00BB..00BF; COMMON
             0x00C0,   // 00C0..00D6; LATIN
-            0x00D7,   // 00D7..00D7; COMMON
+            0x00D7,   // 00D7      ; COMMON
             0x00D8,   // 00D8..00F6; LATIN
-            0x00F7,   // 00F7..00F7; COMMON
+            0x00F7,   // 00F7      ; COMMON
             0x00F8,   // 00F8..02B8; LATIN
             0x02B9,   // 02B9..02DF; COMMON
             0x02E0,   // 02E0..02E4; LATIN
@@ -3735,284 +4241,1178 @@
             0x02EC,   // 02EC..02FF; COMMON
             0x0300,   // 0300..036F; INHERITED
             0x0370,   // 0370..0373; GREEK
-            0x0374,   // 0374..0374; COMMON
-            0x0375,   // 0375..037D; GREEK
-            0x037E,   // 037E..0383; COMMON
-            0x0384,   // 0384..0384; GREEK
-            0x0385,   // 0385..0385; COMMON
-            0x0386,   // 0386..0386; GREEK
-            0x0387,   // 0387..0387; COMMON
-            0x0388,   // 0388..03E1; GREEK
+            0x0374,   // 0374      ; COMMON
+            0x0375,   // 0375..0377; GREEK
+            0x0378,   // 0378..0379; UNKNOWN
+            0x037A,   // 037A..037D; GREEK
+            0x037E,   // 037E      ; COMMON
+            0x037F,   // 037F      ; GREEK
+            0x0380,   // 0380..0383; UNKNOWN
+            0x0384,   // 0384      ; GREEK
+            0x0385,   // 0385      ; COMMON
+            0x0386,   // 0386      ; GREEK
+            0x0387,   // 0387      ; COMMON
+            0x0388,   // 0388..038A; GREEK
+            0x038B,   // 038B      ; UNKNOWN
+            0x038C,   // 038C      ; GREEK
+            0x038D,   // 038D      ; UNKNOWN
+            0x038E,   // 038E..03A1; GREEK
+            0x03A2,   // 03A2      ; UNKNOWN
+            0x03A3,   // 03A3..03E1; GREEK
             0x03E2,   // 03E2..03EF; COPTIC
             0x03F0,   // 03F0..03FF; GREEK
             0x0400,   // 0400..0484; CYRILLIC
             0x0485,   // 0485..0486; INHERITED
-            0x0487,   // 0487..0530; CYRILLIC
-            0x0531,   // 0531..0588; ARMENIAN
-            0x0589,   // 0589..0589; COMMON
-            0x058A,   // 058A..0590; ARMENIAN
-            0x0591,   // 0591..05FF; HEBREW
-            0x0600,   // 0600..060B; ARABIC
-            0x060C,   // 060C..060C; COMMON
+            0x0487,   // 0487..052F; CYRILLIC
+            0x0530,   // 0530      ; UNKNOWN
+            0x0531,   // 0531..0556; ARMENIAN
+            0x0557,   // 0557..0558; UNKNOWN
+            0x0559,   // 0559..055F; ARMENIAN
+            0x0560,   // 0560      ; UNKNOWN
+            0x0561,   // 0561..0587; ARMENIAN
+            0x0588,   // 0588      ; UNKNOWN
+            0x0589,   // 0589      ; COMMON
+            0x058A,   // 058A      ; ARMENIAN
+            0x058B,   // 058B..058C; UNKNOWN
+            0x058D,   // 058D..058F; ARMENIAN
+            0x0590,   // 0590      ; UNKNOWN
+            0x0591,   // 0591..05C7; HEBREW
+            0x05C8,   // 05C8..05CF; UNKNOWN
+            0x05D0,   // 05D0..05EA; HEBREW
+            0x05EB,   // 05EB..05EF; UNKNOWN
+            0x05F0,   // 05F0..05F4; HEBREW
+            0x05F5,   // 05F5..05FF; UNKNOWN
+            0x0600,   // 0600..0604; ARABIC
+            0x0605,   // 0605      ; COMMON
+            0x0606,   // 0606..060B; ARABIC
+            0x060C,   // 060C      ; COMMON
             0x060D,   // 060D..061A; ARABIC
-            0x061B,   // 061B..061D; COMMON
-            0x061E,   // 061E..061E; ARABIC
-            0x061F,   // 061F..061F; COMMON
+            0x061B,   // 061B..061C; COMMON
+            0x061D,   // 061D      ; UNKNOWN
+            0x061E,   // 061E      ; ARABIC
+            0x061F,   // 061F      ; COMMON
             0x0620,   // 0620..063F; ARABIC
-            0x0640,   // 0640..0640; COMMON
+            0x0640,   // 0640      ; COMMON
             0x0641,   // 0641..064A; ARABIC
             0x064B,   // 064B..0655; INHERITED
             0x0656,   // 0656..065F; ARABIC
             0x0660,   // 0660..0669; COMMON
             0x066A,   // 066A..066F; ARABIC
-            0x0670,   // 0670..0670; INHERITED
+            0x0670,   // 0670      ; INHERITED
             0x0671,   // 0671..06DC; ARABIC
-            0x06DD,   // 06DD..06DD; COMMON
+            0x06DD,   // 06DD      ; COMMON
             0x06DE,   // 06DE..06FF; ARABIC
-            0x0700,   // 0700..074F; SYRIAC
+            0x0700,   // 0700..070D; SYRIAC
+            0x070E,   // 070E      ; UNKNOWN
+            0x070F,   // 070F..074A; SYRIAC
+            0x074B,   // 074B..074C; UNKNOWN
+            0x074D,   // 074D..074F; SYRIAC
             0x0750,   // 0750..077F; ARABIC
-            0x0780,   // 0780..07BF; THAANA
-            0x07C0,   // 07C0..07FF; NKO
-            0x0800,   // 0800..083F; SAMARITAN
-            0x0840,   // 0840..089F; MANDAIC
-            0x08A0,   // 08A0..08FF; ARABIC
+            0x0780,   // 0780..07B1; THAANA
+            0x07B2,   // 07B2..07BF; UNKNOWN
+            0x07C0,   // 07C0..07FA; NKO
+            0x07FB,   // 07FB..07FF; UNKNOWN
+            0x0800,   // 0800..082D; SAMARITAN
+            0x082E,   // 082E..082F; UNKNOWN
+            0x0830,   // 0830..083E; SAMARITAN
+            0x083F,   // 083F      ; UNKNOWN
+            0x0840,   // 0840..085B; MANDAIC
+            0x085C,   // 085C..085D; UNKNOWN
+            0x085E,   // 085E      ; MANDAIC
+            0x085F,   // 085F..089F; UNKNOWN
+            0x08A0,   // 08A0..08B2; ARABIC
+            0x08B3,   // 08B3..08E3; UNKNOWN
+            0x08E4,   // 08E4..08FF; ARABIC
             0x0900,   // 0900..0950; DEVANAGARI
             0x0951,   // 0951..0952; INHERITED
             0x0953,   // 0953..0963; DEVANAGARI
             0x0964,   // 0964..0965; COMMON
-            0x0966,   // 0966..0980; DEVANAGARI
-            0x0981,   // 0981..0A00; BENGALI
-            0x0A01,   // 0A01..0A80; GURMUKHI
-            0x0A81,   // 0A81..0B00; GUJARATI
-            0x0B01,   // 0B01..0B81; ORIYA
-            0x0B82,   // 0B82..0C00; TAMIL
-            0x0C01,   // 0C01..0C81; TELUGU
-            0x0C82,   // 0C82..0CF0; KANNADA
-            0x0D02,   // 0D02..0D81; MALAYALAM
-            0x0D82,   // 0D82..0E00; SINHALA
-            0x0E01,   // 0E01..0E3E; THAI
-            0x0E3F,   // 0E3F..0E3F; COMMON
-            0x0E40,   // 0E40..0E80; THAI
-            0x0E81,   // 0E81..0EFF; LAO
-            0x0F00,   // 0F00..0FD4; TIBETAN
+            0x0966,   // 0966..097F; DEVANAGARI
+            0x0980,   // 0980..0983; BENGALI
+            0x0984,   // 0984      ; UNKNOWN
+            0x0985,   // 0985..098C; BENGALI
+            0x098D,   // 098D..098E; UNKNOWN
+            0x098F,   // 098F..0990; BENGALI
+            0x0991,   // 0991..0992; UNKNOWN
+            0x0993,   // 0993..09A8; BENGALI
+            0x09A9,   // 09A9      ; UNKNOWN
+            0x09AA,   // 09AA..09B0; BENGALI
+            0x09B1,   // 09B1      ; UNKNOWN
+            0x09B2,   // 09B2      ; BENGALI
+            0x09B3,   // 09B3..09B5; UNKNOWN
+            0x09B6,   // 09B6..09B9; BENGALI
+            0x09BA,   // 09BA..09BB; UNKNOWN
+            0x09BC,   // 09BC..09C4; BENGALI
+            0x09C5,   // 09C5..09C6; UNKNOWN
+            0x09C7,   // 09C7..09C8; BENGALI
+            0x09C9,   // 09C9..09CA; UNKNOWN
+            0x09CB,   // 09CB..09CE; BENGALI
+            0x09CF,   // 09CF..09D6; UNKNOWN
+            0x09D7,   // 09D7      ; BENGALI
+            0x09D8,   // 09D8..09DB; UNKNOWN
+            0x09DC,   // 09DC..09DD; BENGALI
+            0x09DE,   // 09DE      ; UNKNOWN
+            0x09DF,   // 09DF..09E3; BENGALI
+            0x09E4,   // 09E4..09E5; UNKNOWN
+            0x09E6,   // 09E6..09FB; BENGALI
+            0x09FC,   // 09FC..0A00; UNKNOWN
+            0x0A01,   // 0A01..0A03; GURMUKHI
+            0x0A04,   // 0A04      ; UNKNOWN
+            0x0A05,   // 0A05..0A0A; GURMUKHI
+            0x0A0B,   // 0A0B..0A0E; UNKNOWN
+            0x0A0F,   // 0A0F..0A10; GURMUKHI
+            0x0A11,   // 0A11..0A12; UNKNOWN
+            0x0A13,   // 0A13..0A28; GURMUKHI
+            0x0A29,   // 0A29      ; UNKNOWN
+            0x0A2A,   // 0A2A..0A30; GURMUKHI
+            0x0A31,   // 0A31      ; UNKNOWN
+            0x0A32,   // 0A32..0A33; GURMUKHI
+            0x0A34,   // 0A34      ; UNKNOWN
+            0x0A35,   // 0A35..0A36; GURMUKHI
+            0x0A37,   // 0A37      ; UNKNOWN
+            0x0A38,   // 0A38..0A39; GURMUKHI
+            0x0A3A,   // 0A3A..0A3B; UNKNOWN
+            0x0A3C,   // 0A3C      ; GURMUKHI
+            0x0A3D,   // 0A3D      ; UNKNOWN
+            0x0A3E,   // 0A3E..0A42; GURMUKHI
+            0x0A43,   // 0A43..0A46; UNKNOWN
+            0x0A47,   // 0A47..0A48; GURMUKHI
+            0x0A49,   // 0A49..0A4A; UNKNOWN
+            0x0A4B,   // 0A4B..0A4D; GURMUKHI
+            0x0A4E,   // 0A4E..0A50; UNKNOWN
+            0x0A51,   // 0A51      ; GURMUKHI
+            0x0A52,   // 0A52..0A58; UNKNOWN
+            0x0A59,   // 0A59..0A5C; GURMUKHI
+            0x0A5D,   // 0A5D      ; UNKNOWN
+            0x0A5E,   // 0A5E      ; GURMUKHI
+            0x0A5F,   // 0A5F..0A65; UNKNOWN
+            0x0A66,   // 0A66..0A75; GURMUKHI
+            0x0A76,   // 0A76..0A80; UNKNOWN
+            0x0A81,   // 0A81..0A83; GUJARATI
+            0x0A84,   // 0A84      ; UNKNOWN
+            0x0A85,   // 0A85..0A8D; GUJARATI
+            0x0A8E,   // 0A8E      ; UNKNOWN
+            0x0A8F,   // 0A8F..0A91; GUJARATI
+            0x0A92,   // 0A92      ; UNKNOWN
+            0x0A93,   // 0A93..0AA8; GUJARATI
+            0x0AA9,   // 0AA9      ; UNKNOWN
+            0x0AAA,   // 0AAA..0AB0; GUJARATI
+            0x0AB1,   // 0AB1      ; UNKNOWN
+            0x0AB2,   // 0AB2..0AB3; GUJARATI
+            0x0AB4,   // 0AB4      ; UNKNOWN
+            0x0AB5,   // 0AB5..0AB9; GUJARATI
+            0x0ABA,   // 0ABA..0ABB; UNKNOWN
+            0x0ABC,   // 0ABC..0AC5; GUJARATI
+            0x0AC6,   // 0AC6      ; UNKNOWN
+            0x0AC7,   // 0AC7..0AC9; GUJARATI
+            0x0ACA,   // 0ACA      ; UNKNOWN
+            0x0ACB,   // 0ACB..0ACD; GUJARATI
+            0x0ACE,   // 0ACE..0ACF; UNKNOWN
+            0x0AD0,   // 0AD0      ; GUJARATI
+            0x0AD1,   // 0AD1..0ADF; UNKNOWN
+            0x0AE0,   // 0AE0..0AE3; GUJARATI
+            0x0AE4,   // 0AE4..0AE5; UNKNOWN
+            0x0AE6,   // 0AE6..0AF1; GUJARATI
+            0x0AF2,   // 0AF2..0B00; UNKNOWN
+            0x0B01,   // 0B01..0B03; ORIYA
+            0x0B04,   // 0B04      ; UNKNOWN
+            0x0B05,   // 0B05..0B0C; ORIYA
+            0x0B0D,   // 0B0D..0B0E; UNKNOWN
+            0x0B0F,   // 0B0F..0B10; ORIYA
+            0x0B11,   // 0B11..0B12; UNKNOWN
+            0x0B13,   // 0B13..0B28; ORIYA
+            0x0B29,   // 0B29      ; UNKNOWN
+            0x0B2A,   // 0B2A..0B30; ORIYA
+            0x0B31,   // 0B31      ; UNKNOWN
+            0x0B32,   // 0B32..0B33; ORIYA
+            0x0B34,   // 0B34      ; UNKNOWN
+            0x0B35,   // 0B35..0B39; ORIYA
+            0x0B3A,   // 0B3A..0B3B; UNKNOWN
+            0x0B3C,   // 0B3C..0B44; ORIYA
+            0x0B45,   // 0B45..0B46; UNKNOWN
+            0x0B47,   // 0B47..0B48; ORIYA
+            0x0B49,   // 0B49..0B4A; UNKNOWN
+            0x0B4B,   // 0B4B..0B4D; ORIYA
+            0x0B4E,   // 0B4E..0B55; UNKNOWN
+            0x0B56,   // 0B56..0B57; ORIYA
+            0x0B58,   // 0B58..0B5B; UNKNOWN
+            0x0B5C,   // 0B5C..0B5D; ORIYA
+            0x0B5E,   // 0B5E      ; UNKNOWN
+            0x0B5F,   // 0B5F..0B63; ORIYA
+            0x0B64,   // 0B64..0B65; UNKNOWN
+            0x0B66,   // 0B66..0B77; ORIYA
+            0x0B78,   // 0B78..0B81; UNKNOWN
+            0x0B82,   // 0B82..0B83; TAMIL
+            0x0B84,   // 0B84      ; UNKNOWN
+            0x0B85,   // 0B85..0B8A; TAMIL
+            0x0B8B,   // 0B8B..0B8D; UNKNOWN
+            0x0B8E,   // 0B8E..0B90; TAMIL
+            0x0B91,   // 0B91      ; UNKNOWN
+            0x0B92,   // 0B92..0B95; TAMIL
+            0x0B96,   // 0B96..0B98; UNKNOWN
+            0x0B99,   // 0B99..0B9A; TAMIL
+            0x0B9B,   // 0B9B      ; UNKNOWN
+            0x0B9C,   // 0B9C      ; TAMIL
+            0x0B9D,   // 0B9D      ; UNKNOWN
+            0x0B9E,   // 0B9E..0B9F; TAMIL
+            0x0BA0,   // 0BA0..0BA2; UNKNOWN
+            0x0BA3,   // 0BA3..0BA4; TAMIL
+            0x0BA5,   // 0BA5..0BA7; UNKNOWN
+            0x0BA8,   // 0BA8..0BAA; TAMIL
+            0x0BAB,   // 0BAB..0BAD; UNKNOWN
+            0x0BAE,   // 0BAE..0BB9; TAMIL
+            0x0BBA,   // 0BBA..0BBD; UNKNOWN
+            0x0BBE,   // 0BBE..0BC2; TAMIL
+            0x0BC3,   // 0BC3..0BC5; UNKNOWN
+            0x0BC6,   // 0BC6..0BC8; TAMIL
+            0x0BC9,   // 0BC9      ; UNKNOWN
+            0x0BCA,   // 0BCA..0BCD; TAMIL
+            0x0BCE,   // 0BCE..0BCF; UNKNOWN
+            0x0BD0,   // 0BD0      ; TAMIL
+            0x0BD1,   // 0BD1..0BD6; UNKNOWN
+            0x0BD7,   // 0BD7      ; TAMIL
+            0x0BD8,   // 0BD8..0BE5; UNKNOWN
+            0x0BE6,   // 0BE6..0BFA; TAMIL
+            0x0BFB,   // 0BFB..0BFF; UNKNOWN
+            0x0C00,   // 0C00..0C03; TELUGU
+            0x0C04,   // 0C04      ; UNKNOWN
+            0x0C05,   // 0C05..0C0C; TELUGU
+            0x0C0D,   // 0C0D      ; UNKNOWN
+            0x0C0E,   // 0C0E..0C10; TELUGU
+            0x0C11,   // 0C11      ; UNKNOWN
+            0x0C12,   // 0C12..0C28; TELUGU
+            0x0C29,   // 0C29      ; UNKNOWN
+            0x0C2A,   // 0C2A..0C39; TELUGU
+            0x0C3A,   // 0C3A..0C3C; UNKNOWN
+            0x0C3D,   // 0C3D..0C44; TELUGU
+            0x0C45,   // 0C45      ; UNKNOWN
+            0x0C46,   // 0C46..0C48; TELUGU
+            0x0C49,   // 0C49      ; UNKNOWN
+            0x0C4A,   // 0C4A..0C4D; TELUGU
+            0x0C4E,   // 0C4E..0C54; UNKNOWN
+            0x0C55,   // 0C55..0C56; TELUGU
+            0x0C57,   // 0C57      ; UNKNOWN
+            0x0C58,   // 0C58..0C59; TELUGU
+            0x0C5A,   // 0C5A..0C5F; UNKNOWN
+            0x0C60,   // 0C60..0C63; TELUGU
+            0x0C64,   // 0C64..0C65; UNKNOWN
+            0x0C66,   // 0C66..0C6F; TELUGU
+            0x0C70,   // 0C70..0C77; UNKNOWN
+            0x0C78,   // 0C78..0C7F; TELUGU
+            0x0C80,   // 0C80      ; UNKNOWN
+            0x0C81,   // 0C81..0C83; KANNADA
+            0x0C84,   // 0C84      ; UNKNOWN
+            0x0C85,   // 0C85..0C8C; KANNADA
+            0x0C8D,   // 0C8D      ; UNKNOWN
+            0x0C8E,   // 0C8E..0C90; KANNADA
+            0x0C91,   // 0C91      ; UNKNOWN
+            0x0C92,   // 0C92..0CA8; KANNADA
+            0x0CA9,   // 0CA9      ; UNKNOWN
+            0x0CAA,   // 0CAA..0CB3; KANNADA
+            0x0CB4,   // 0CB4      ; UNKNOWN
+            0x0CB5,   // 0CB5..0CB9; KANNADA
+            0x0CBA,   // 0CBA..0CBB; UNKNOWN
+            0x0CBC,   // 0CBC..0CC4; KANNADA
+            0x0CC5,   // 0CC5      ; UNKNOWN
+            0x0CC6,   // 0CC6..0CC8; KANNADA
+            0x0CC9,   // 0CC9      ; UNKNOWN
+            0x0CCA,   // 0CCA..0CCD; KANNADA
+            0x0CCE,   // 0CCE..0CD4; UNKNOWN
+            0x0CD5,   // 0CD5..0CD6; KANNADA
+            0x0CD7,   // 0CD7..0CDD; UNKNOWN
+            0x0CDE,   // 0CDE      ; KANNADA
+            0x0CDF,   // 0CDF      ; UNKNOWN
+            0x0CE0,   // 0CE0..0CE3; KANNADA
+            0x0CE4,   // 0CE4..0CE5; UNKNOWN
+            0x0CE6,   // 0CE6..0CEF; KANNADA
+            0x0CF0,   // 0CF0      ; UNKNOWN
+            0x0CF1,   // 0CF1..0CF2; KANNADA
+            0x0CF3,   // 0CF3..0D00; UNKNOWN
+            0x0D01,   // 0D01..0D03; MALAYALAM
+            0x0D04,   // 0D04      ; UNKNOWN
+            0x0D05,   // 0D05..0D0C; MALAYALAM
+            0x0D0D,   // 0D0D      ; UNKNOWN
+            0x0D0E,   // 0D0E..0D10; MALAYALAM
+            0x0D11,   // 0D11      ; UNKNOWN
+            0x0D12,   // 0D12..0D3A; MALAYALAM
+            0x0D3B,   // 0D3B..0D3C; UNKNOWN
+            0x0D3D,   // 0D3D..0D44; MALAYALAM
+            0x0D45,   // 0D45      ; UNKNOWN
+            0x0D46,   // 0D46..0D48; MALAYALAM
+            0x0D49,   // 0D49      ; UNKNOWN
+            0x0D4A,   // 0D4A..0D4E; MALAYALAM
+            0x0D4F,   // 0D4F..0D56; UNKNOWN
+            0x0D57,   // 0D57      ; MALAYALAM
+            0x0D58,   // 0D58..0D5F; UNKNOWN
+            0x0D60,   // 0D60..0D63; MALAYALAM
+            0x0D64,   // 0D64..0D65; UNKNOWN
+            0x0D66,   // 0D66..0D75; MALAYALAM
+            0x0D76,   // 0D76..0D78; UNKNOWN
+            0x0D79,   // 0D79..0D7F; MALAYALAM
+            0x0D80,   // 0D80..0D81; UNKNOWN
+            0x0D82,   // 0D82..0D83; SINHALA
+            0x0D84,   // 0D84      ; UNKNOWN
+            0x0D85,   // 0D85..0D96; SINHALA
+            0x0D97,   // 0D97..0D99; UNKNOWN
+            0x0D9A,   // 0D9A..0DB1; SINHALA
+            0x0DB2,   // 0DB2      ; UNKNOWN
+            0x0DB3,   // 0DB3..0DBB; SINHALA
+            0x0DBC,   // 0DBC      ; UNKNOWN
+            0x0DBD,   // 0DBD      ; SINHALA
+            0x0DBE,   // 0DBE..0DBF; UNKNOWN
+            0x0DC0,   // 0DC0..0DC6; SINHALA
+            0x0DC7,   // 0DC7..0DC9; UNKNOWN
+            0x0DCA,   // 0DCA      ; SINHALA
+            0x0DCB,   // 0DCB..0DCE; UNKNOWN
+            0x0DCF,   // 0DCF..0DD4; SINHALA
+            0x0DD5,   // 0DD5      ; UNKNOWN
+            0x0DD6,   // 0DD6      ; SINHALA
+            0x0DD7,   // 0DD7      ; UNKNOWN
+            0x0DD8,   // 0DD8..0DDF; SINHALA
+            0x0DE0,   // 0DE0..0DE5; UNKNOWN
+            0x0DE6,   // 0DE6..0DEF; SINHALA
+            0x0DF0,   // 0DF0..0DF1; UNKNOWN
+            0x0DF2,   // 0DF2..0DF4; SINHALA
+            0x0DF5,   // 0DF5..0E00; UNKNOWN
+            0x0E01,   // 0E01..0E3A; THAI
+            0x0E3B,   // 0E3B..0E3E; UNKNOWN
+            0x0E3F,   // 0E3F      ; COMMON
+            0x0E40,   // 0E40..0E5B; THAI
+            0x0E5C,   // 0E5C..0E80; UNKNOWN
+            0x0E81,   // 0E81..0E82; LAO
+            0x0E83,   // 0E83      ; UNKNOWN
+            0x0E84,   // 0E84      ; LAO
+            0x0E85,   // 0E85..0E86; UNKNOWN
+            0x0E87,   // 0E87..0E88; LAO
+            0x0E89,   // 0E89      ; UNKNOWN
+            0x0E8A,   // 0E8A      ; LAO
+            0x0E8B,   // 0E8B..0E8C; UNKNOWN
+            0x0E8D,   // 0E8D      ; LAO
+            0x0E8E,   // 0E8E..0E93; UNKNOWN
+            0x0E94,   // 0E94..0E97; LAO
+            0x0E98,   // 0E98      ; UNKNOWN
+            0x0E99,   // 0E99..0E9F; LAO
+            0x0EA0,   // 0EA0      ; UNKNOWN
+            0x0EA1,   // 0EA1..0EA3; LAO
+            0x0EA4,   // 0EA4      ; UNKNOWN
+            0x0EA5,   // 0EA5      ; LAO
+            0x0EA6,   // 0EA6      ; UNKNOWN
+            0x0EA7,   // 0EA7      ; LAO
+            0x0EA8,   // 0EA8..0EA9; UNKNOWN
+            0x0EAA,   // 0EAA..0EAB; LAO
+            0x0EAC,   // 0EAC      ; UNKNOWN
+            0x0EAD,   // 0EAD..0EB9; LAO
+            0x0EBA,   // 0EBA      ; UNKNOWN
+            0x0EBB,   // 0EBB..0EBD; LAO
+            0x0EBE,   // 0EBE..0EBF; UNKNOWN
+            0x0EC0,   // 0EC0..0EC4; LAO
+            0x0EC5,   // 0EC5      ; UNKNOWN
+            0x0EC6,   // 0EC6      ; LAO
+            0x0EC7,   // 0EC7      ; UNKNOWN
+            0x0EC8,   // 0EC8..0ECD; LAO
+            0x0ECE,   // 0ECE..0ECF; UNKNOWN
+            0x0ED0,   // 0ED0..0ED9; LAO
+            0x0EDA,   // 0EDA..0EDB; UNKNOWN
+            0x0EDC,   // 0EDC..0EDF; LAO
+            0x0EE0,   // 0EE0..0EFF; UNKNOWN
+            0x0F00,   // 0F00..0F47; TIBETAN
+            0x0F48,   // 0F48      ; UNKNOWN
+            0x0F49,   // 0F49..0F6C; TIBETAN
+            0x0F6D,   // 0F6D..0F70; UNKNOWN
+            0x0F71,   // 0F71..0F97; TIBETAN
+            0x0F98,   // 0F98      ; UNKNOWN
+            0x0F99,   // 0F99..0FBC; TIBETAN
+            0x0FBD,   // 0FBD      ; UNKNOWN
+            0x0FBE,   // 0FBE..0FCC; TIBETAN
+            0x0FCD,   // 0FCD      ; UNKNOWN
+            0x0FCE,   // 0FCE..0FD4; TIBETAN
             0x0FD5,   // 0FD5..0FD8; COMMON
-            0x0FD9,   // 0FD9..0FFF; TIBETAN
+            0x0FD9,   // 0FD9..0FDA; TIBETAN
+            0x0FDB,   // 0FDB..FFF; UNKNOWN
             0x1000,   // 1000..109F; MYANMAR
-            0x10A0,   // 10A0..10FA; GEORGIAN
-            0x10FB,   // 10FB..10FB; COMMON
+            0x10A0,   // 10A0..10C5; GEORGIAN
+            0x10C6,   // 10C6      ; UNKNOWN
+            0x10C7,   // 10C7      ; GEORGIAN
+            0x10C8,   // 10C8..10CC; UNKNOWN
+            0x10CD,   // 10CD      ; GEORGIAN
+            0x10CE,   // 10CE..10CF; UNKNOWN
+            0x10D0,   // 10D0..10FA; GEORGIAN
+            0x10FB,   // 10FB      ; COMMON
             0x10FC,   // 10FC..10FF; GEORGIAN
             0x1100,   // 1100..11FF; HANGUL
-            0x1200,   // 1200..139F; ETHIOPIC
-            0x13A0,   // 13A0..13FF; CHEROKEE
+            0x1200,   // 1200..1248; ETHIOPIC
+            0x1249,   // 1249      ; UNKNOWN
+            0x124A,   // 124A..124D; ETHIOPIC
+            0x124E,   // 124E..124F; UNKNOWN
+            0x1250,   // 1250..1256; ETHIOPIC
+            0x1257,   // 1257      ; UNKNOWN
+            0x1258,   // 1258      ; ETHIOPIC
+            0x1259,   // 1259      ; UNKNOWN
+            0x125A,   // 125A..125D; ETHIOPIC
+            0x125E,   // 125E..125F; UNKNOWN
+            0x1260,   // 1260..1288; ETHIOPIC
+            0x1289,   // 1289      ; UNKNOWN
+            0x128A,   // 128A..128D; ETHIOPIC
+            0x128E,   // 128E..128F; UNKNOWN
+            0x1290,   // 1290..12B0; ETHIOPIC
+            0x12B1,   // 12B1      ; UNKNOWN
+            0x12B2,   // 12B2..12B5; ETHIOPIC
+            0x12B6,   // 12B6..12B7; UNKNOWN
+            0x12B8,   // 12B8..12BE; ETHIOPIC
+            0x12BF,   // 12BF      ; UNKNOWN
+            0x12C0,   // 12C0      ; ETHIOPIC
+            0x12C1,   // 12C1      ; UNKNOWN
+            0x12C2,   // 12C2..12C5; ETHIOPIC
+            0x12C6,   // 12C6..12C7; UNKNOWN
+            0x12C8,   // 12C8..12D6; ETHIOPIC
+            0x12D7,   // 12D7      ; UNKNOWN
+            0x12D8,   // 12D8..1310; ETHIOPIC
+            0x1311,   // 1311      ; UNKNOWN
+            0x1312,   // 1312..1315; ETHIOPIC
+            0x1316,   // 1316..1317; UNKNOWN
+            0x1318,   // 1318..135A; ETHIOPIC
+            0x135B,   // 135B..135C; UNKNOWN
+            0x135D,   // 135D..137C; ETHIOPIC
+            0x137D,   // 137D..137F; UNKNOWN
+            0x1380,   // 1380..1399; ETHIOPIC
+            0x139A,   // 139A..139F; UNKNOWN
+            0x13A0,   // 13A0..13F4; CHEROKEE
+            0x13F5,   // 13F5..13FF; UNKNOWN
             0x1400,   // 1400..167F; CANADIAN_ABORIGINAL
-            0x1680,   // 1680..169F; OGHAM
+            0x1680,   // 1680..169C; OGHAM
+            0x169D,   // 169D..169F; UNKNOWN
             0x16A0,   // 16A0..16EA; RUNIC
             0x16EB,   // 16EB..16ED; COMMON
-            0x16EE,   // 16EE..16FF; RUNIC
-            0x1700,   // 1700..171F; TAGALOG
+            0x16EE,   // 16EE..16F8; RUNIC
+            0x16F9,   // 16F9..16FF; UNKNOWN
+            0x1700,   // 1700..170C; TAGALOG
+            0x170D,   // 170D      ; UNKNOWN
+            0x170E,   // 170E..1714; TAGALOG
+            0x1715,   // 1715..171F; UNKNOWN
             0x1720,   // 1720..1734; HANUNOO
-            0x1735,   // 1735..173F; COMMON
-            0x1740,   // 1740..175F; BUHID
-            0x1760,   // 1760..177F; TAGBANWA
-            0x1780,   // 1780..17FF; KHMER
+            0x1735,   // 1735..1736; COMMON
+            0x1737,   // 1737..173F; UNKNOWN
+            0x1740,   // 1740..1753; BUHID
+            0x1754,   // 1754..175F; UNKNOWN
+            0x1760,   // 1760..176C; TAGBANWA
+            0x176D,   // 176D      ; UNKNOWN
+            0x176E,   // 176E..1770; TAGBANWA
+            0x1771,   // 1771      ; UNKNOWN
+            0x1772,   // 1772..1773; TAGBANWA
+            0x1774,   // 1774..177F; UNKNOWN
+            0x1780,   // 1780..17DD; KHMER
+            0x17DE,   // 17DE..17DF; UNKNOWN
+            0x17E0,   // 17E0..17E9; KHMER
+            0x17EA,   // 17EA..17EF; UNKNOWN
+            0x17F0,   // 17F0..17F9; KHMER
+            0x17FA,   // 17FA..17FF; UNKNOWN
             0x1800,   // 1800..1801; MONGOLIAN
             0x1802,   // 1802..1803; COMMON
-            0x1804,   // 1804..1804; MONGOLIAN
-            0x1805,   // 1805..1805; COMMON
-            0x1806,   // 1806..18AF; MONGOLIAN
-            0x18B0,   // 18B0..18FF; CANADIAN_ABORIGINAL
-            0x1900,   // 1900..194F; LIMBU
-            0x1950,   // 1950..197F; TAI_LE
-            0x1980,   // 1980..19DF; NEW_TAI_LUE
+            0x1804,   // 1804      ; MONGOLIAN
+            0x1805,   // 1805      ; COMMON
+            0x1806,   // 1806..180E; MONGOLIAN
+            0x180F,   // 180F      ; UNKNOWN
+            0x1810,   // 1810..1819; MONGOLIAN
+            0x181A,   // 181A..181F; UNKNOWN
+            0x1820,   // 1820..1877; MONGOLIAN
+            0x1878,   // 1878..187F; UNKNOWN
+            0x1880,   // 1880..18AA; MONGOLIAN
+            0x18AB,   // 18AB..18AF; UNKNOWN
+            0x18B0,   // 18B0..18F5; CANADIAN_ABORIGINAL
+            0x18F6,   // 18F6..18FF; UNKNOWN
+            0x1900,   // 1900..191E; LIMBU
+            0x191F,   // 191F      ; UNKNOWN
+            0x1920,   // 1920..192B; LIMBU
+            0x192C,   // 192C..192F; UNKNOWN
+            0x1930,   // 1930..193B; LIMBU
+            0x193C,   // 193C..193F; UNKNOWN
+            0x1940,   // 1940      ; LIMBU
+            0x1941,   // 1941..1943; UNKNOWN
+            0x1944,   // 1944..194F; LIMBU
+            0x1950,   // 1950..196D; TAI_LE
+            0x196E,   // 196E..196F; UNKNOWN
+            0x1970,   // 1970..1974; TAI_LE
+            0x1975,   // 1975..197F; UNKNOWN
+            0x1980,   // 1980..19AB; NEW_TAI_LUE
+            0x19AC,   // 19AC..19AF; UNKNOWN
+            0x19B0,   // 19B0..19C9; NEW_TAI_LUE
+            0x19CA,   // 19CA..19CF; UNKNOWN
+            0x19D0,   // 19D0..19DA; NEW_TAI_LUE
+            0x19DB,   // 19DB..19DD; UNKNOWN
+            0x19DE,   // 19DE..19DF; NEW_TAI_LUE
             0x19E0,   // 19E0..19FF; KHMER
-            0x1A00,   // 1A00..1A1F; BUGINESE
-            0x1A20,   // 1A20..1AFF; TAI_THAM
-            0x1B00,   // 1B00..1B7F; BALINESE
+            0x1A00,   // 1A00..1A1B; BUGINESE
+            0x1A1C,   // 1A1C..1A1D; UNKNOWN
+            0x1A1E,   // 1A1E..1A1F; BUGINESE
+            0x1A20,   // 1A20..1A5E; TAI_THAM
+            0x1A5F,   // 1A5F      ; UNKNOWN
+            0x1A60,   // 1A60..1A7C; TAI_THAM
+            0x1A7D,   // 1A7D..1A7E; UNKNOWN
+            0x1A7F,   // 1A7F..1A89; TAI_THAM
+            0x1A8A,   // 1A8A..1A8F; UNKNOWN
+            0x1A90,   // 1A90..1A99; TAI_THAM
+            0x1A9A,   // 1A9A..1A9F; UNKNOWN
+            0x1AA0,   // 1AA0..1AAD; TAI_THAM
+            0x1AAE,   // 1AAE..1AAF; UNKNOWN
+            0x1AB0,   // 1AB0..1ABE; INHERITED
+            0x1ABF,   // 1ABF..1AFF; UNKNOWN
+            0x1B00,   // 1B00..1B4B; BALINESE
+            0x1B4C,   // 1B4C..1B4F; UNKNOWN
+            0x1B50,   // 1B50..1B7C; BALINESE
+            0x1B7D,   // 1B7D..1B7F; UNKNOWN
             0x1B80,   // 1B80..1BBF; SUNDANESE
-            0x1BC0,   // 1BC0..1BFF; BATAK
-            0x1C00,   // 1C00..1C4F; LEPCHA
-            0x1C50,   // 1C50..1CBF; OL_CHIKI
-            0x1CC0,   // 1CC0..1CCF; SUNDANESE
+            0x1BC0,   // 1BC0..1BF3; BATAK
+            0x1BF4,   // 1BF4..1BFB; UNKNOWN
+            0x1BFC,   // 1BFC..1BFF; BATAK
+            0x1C00,   // 1C00..1C37; LEPCHA
+            0x1C38,   // 1C38..1C3A; UNKNOWN
+            0x1C3B,   // 1C3B..1C49; LEPCHA
+            0x1C4A,   // 1C4A..1C4C; UNKNOWN
+            0x1C4D,   // 1C4D..1C4F; LEPCHA
+            0x1C50,   // 1C50..1C7F; OL_CHIKI
+            0x1C80,   // 1C80..1CBF; UNKNOWN
+            0x1CC0,   // 1CC0..1CC7; SUNDANESE
+            0x1CC8,   // 1CC8..1CCF; UNKNOWN
             0x1CD0,   // 1CD0..1CD2; INHERITED
-            0x1CD3,   // 1CD3..1CD3; COMMON
+            0x1CD3,   // 1CD3      ; COMMON
             0x1CD4,   // 1CD4..1CE0; INHERITED
-            0x1CE1,   // 1CE1..1CE1; COMMON
+            0x1CE1,   // 1CE1      ; COMMON
             0x1CE2,   // 1CE2..1CE8; INHERITED
             0x1CE9,   // 1CE9..1CEC; COMMON
-            0x1CED,   // 1CED..1CED; INHERITED
+            0x1CED,   // 1CED      ; INHERITED
             0x1CEE,   // 1CEE..1CF3; COMMON
-            0x1CF4,   // 1CF4..1CF4; INHERITED
-            0x1CF5,   // 1CF5..1CFF; COMMON
+            0x1CF4,   // 1CF4      ; INHERITED
+            0x1CF5,   // 1CF5..1CF6; COMMON
+            0x1CF7,   // 1CF7      ; UNKNOWN
+            0x1CF8,   // 1CF8..1CF9; INHERITED
+            0x1CFA,   // 1CFA..1CFF; UNKNOWN
             0x1D00,   // 1D00..1D25; LATIN
             0x1D26,   // 1D26..1D2A; GREEK
-            0x1D2B,   // 1D2B..1D2B; CYRILLIC
+            0x1D2B,   // 1D2B      ; CYRILLIC
             0x1D2C,   // 1D2C..1D5C; LATIN
             0x1D5D,   // 1D5D..1D61; GREEK
             0x1D62,   // 1D62..1D65; LATIN
             0x1D66,   // 1D66..1D6A; GREEK
             0x1D6B,   // 1D6B..1D77; LATIN
-            0x1D78,   // 1D78..1D78; CYRILLIC
+            0x1D78,   // 1D78      ; CYRILLIC
             0x1D79,   // 1D79..1DBE; LATIN
-            0x1DBF,   // 1DBF..1DBF; GREEK
-            0x1DC0,   // 1DC0..1DFF; INHERITED
+            0x1DBF,   // 1DBF      ; GREEK
+            0x1DC0,   // 1DC0..1DF5; INHERITED
+            0x1DF6,   // 1DF6..1DFB; UNKNOWN
+            0x1DFC,   // 1DFC..1DFF; INHERITED
             0x1E00,   // 1E00..1EFF; LATIN
-            0x1F00,   // 1F00..1FFF; GREEK
+            0x1F00,   // 1F00..1F15; GREEK
+            0x1F16,   // 1F16..1F17; UNKNOWN
+            0x1F18,   // 1F18..1F1D; GREEK
+            0x1F1E,   // 1F1E..1F1F; UNKNOWN
+            0x1F20,   // 1F20..1F45; GREEK
+            0x1F46,   // 1F46..1F47; UNKNOWN
+            0x1F48,   // 1F48..1F4D; GREEK
+            0x1F4E,   // 1F4E..1F4F; UNKNOWN
+            0x1F50,   // 1F50..1F57; GREEK
+            0x1F58,   // 1F58      ; UNKNOWN
+            0x1F59,   // 1F59      ; GREEK
+            0x1F5A,   // 1F5A      ; UNKNOWN
+            0x1F5B,   // 1F5B      ; GREEK
+            0x1F5C,   // 1F5C      ; UNKNOWN
+            0x1F5D,   // 1F5D      ; GREEK
+            0x1F5E,   // 1F5E      ; UNKNOWN
+            0x1F5F,   // 1F5F..1F7D; GREEK
+            0x1F7E,   // 1F7E..1F7F; UNKNOWN
+            0x1F80,   // 1F80..1FB4; GREEK
+            0x1FB5,   // 1FB5      ; UNKNOWN
+            0x1FB6,   // 1FB6..1FC4; GREEK
+            0x1FC5,   // 1FC5      ; UNKNOWN
+            0x1FC6,   // 1FC6..1FD3; GREEK
+            0x1FD4,   // 1FD4..1FD5; UNKNOWN
+            0x1FD6,   // 1FD6..1FDB; GREEK
+            0x1FDC,   // 1FDC      ; UNKNOWN
+            0x1FDD,   // 1FDD..1FEF; GREEK
+            0x1FF0,   // 1FF0..1FF1; UNKNOWN
+            0x1FF2,   // 1FF2..1FF4; GREEK
+            0x1FF5,   // 1FF5      ; UNKNOWN
+            0x1FF6,   // 1FF6..1FFE; GREEK
+            0x1FFF,   // 1FFF      ; UNKNOWN
             0x2000,   // 2000..200B; COMMON
             0x200C,   // 200C..200D; INHERITED
-            0x200E,   // 200E..2070; COMMON
-            0x2071,   // 2071..2073; LATIN
+            0x200E,   // 200E..2064; COMMON
+            0x2065,   // 2065      ; UNKNOWN
+            0x2066,   // 2066..2070; COMMON
+            0x2071,   // 2071      ; LATIN
+            0x2072,   // 2072..2073; UNKNOWN
             0x2074,   // 2074..207E; COMMON
-            0x207F,   // 207F..207F; LATIN
-            0x2080,   // 2080..208F; COMMON
-            0x2090,   // 2090..209F; LATIN
-            0x20A0,   // 20A0..20CF; COMMON
-            0x20D0,   // 20D0..20FF; INHERITED
+            0x207F,   // 207F      ; LATIN
+            0x2080,   // 2080..208E; COMMON
+            0x208F,   // 208F      ; UNKNOWN
+            0x2090,   // 2090..209C; LATIN
+            0x209D,   // 209D..209F; UNKNOWN
+            0x20A0,   // 20A0..20BD; COMMON
+            0x20BE,   // 20BE..20CF; UNKNOWN
+            0x20D0,   // 20D0..20F0; INHERITED
+            0x20F1,   // 20F1..20FF; UNKNOWN
             0x2100,   // 2100..2125; COMMON
-            0x2126,   // 2126..2126; GREEK
+            0x2126,   // 2126      ; GREEK
             0x2127,   // 2127..2129; COMMON
             0x212A,   // 212A..212B; LATIN
             0x212C,   // 212C..2131; COMMON
-            0x2132,   // 2132..2132; LATIN
+            0x2132,   // 2132      ; LATIN
             0x2133,   // 2133..214D; COMMON
-            0x214E,   // 214E..214E; LATIN
+            0x214E,   // 214E      ; LATIN
             0x214F,   // 214F..215F; COMMON
             0x2160,   // 2160..2188; LATIN
-            0x2189,   // 2189..27FF; COMMON
+            0x2189,   // 2189      ; COMMON
+            0x218A,   // 218A..218F; UNKNOWN
+            0x2190,   // 2190..23FA; COMMON
+            0x23FB,   // 23FB..23FF; UNKNOWN
+            0x2400,   // 2400..2426; COMMON
+            0x2427,   // 2427..243F; UNKNOWN
+            0x2440,   // 2440..244A; COMMON
+            0x244B,   // 244B..245F; UNKNOWN
+            0x2460,   // 2460..27FF; COMMON
             0x2800,   // 2800..28FF; BRAILLE
-            0x2900,   // 2900..2BFF; COMMON
-            0x2C00,   // 2C00..2C5F; GLAGOLITIC
+            0x2900,   // 2900..2B73; COMMON
+            0x2B74,   // 2B74..2B75; UNKNOWN
+            0x2B76,   // 2B76..2B95; COMMON
+            0x2B96,   // 2B96..2B97; UNKNOWN
+            0x2B98,   // 2B98..2BB9; COMMON
+            0x2BBA,   // 2BBA..2BBC; UNKNOWN
+            0x2BBD,   // 2BBD..2BC8; COMMON
+            0x2BC9,   // 2BC9      ; UNKNOWN
+            0x2BCA,   // 2BCA..2BD1; COMMON
+            0x2BD2,   // 2BD2..2BFF; UNKNOWN
+            0x2C00,   // 2C00..2C2E; GLAGOLITIC
+            0x2C2F,   // 2C2F      ; UNKNOWN
+            0x2C30,   // 2C30..2C5E; GLAGOLITIC
+            0x2C5F,   // 2C5F      ; UNKNOWN
             0x2C60,   // 2C60..2C7F; LATIN
-            0x2C80,   // 2C80..2CFF; COPTIC
-            0x2D00,   // 2D00..2D2F; GEORGIAN
-            0x2D30,   // 2D30..2D7F; TIFINAGH
-            0x2D80,   // 2D80..2DDF; ETHIOPIC
+            0x2C80,   // 2C80..2CF3; COPTIC
+            0x2CF4,   // 2CF4..2CF8; UNKNOWN
+            0x2CF9,   // 2CF9..2CFF; COPTIC
+            0x2D00,   // 2D00..2D25; GEORGIAN
+            0x2D26,   // 2D26      ; UNKNOWN
+            0x2D27,   // 2D27      ; GEORGIAN
+            0x2D28,   // 2D28..2D2C; UNKNOWN
+            0x2D2D,   // 2D2D      ; GEORGIAN
+            0x2D2E,   // 2D2E..2D2F; UNKNOWN
+            0x2D30,   // 2D30..2D67; TIFINAGH
+            0x2D68,   // 2D68..2D6E; UNKNOWN
+            0x2D6F,   // 2D6F..2D70; TIFINAGH
+            0x2D71,   // 2D71..2D7E; UNKNOWN
+            0x2D7F,   // 2D7F      ; TIFINAGH
+            0x2D80,   // 2D80..2D96; ETHIOPIC
+            0x2D97,   // 2D97..2D9F; UNKNOWN
+            0x2DA0,   // 2DA0..2DA6; ETHIOPIC
+            0x2DA7,   // 2DA7      ; UNKNOWN
+            0x2DA8,   // 2DA8..2DAE; ETHIOPIC
+            0x2DAF,   // 2DAF      ; UNKNOWN
+            0x2DB0,   // 2DB0..2DB6; ETHIOPIC
+            0x2DB7,   // 2DB7      ; UNKNOWN
+            0x2DB8,   // 2DB8..2DBE; ETHIOPIC
+            0x2DBF,   // 2DBF      ; UNKNOWN
+            0x2DC0,   // 2DC0..2DC6; ETHIOPIC
+            0x2DC7,   // 2DC7      ; UNKNOWN
+            0x2DC8,   // 2DC8..2DCE; ETHIOPIC
+            0x2DCF,   // 2DCF      ; UNKNOWN
+            0x2DD0,   // 2DD0..2DD6; ETHIOPIC
+            0x2DD7,   // 2DD7      ; UNKNOWN
+            0x2DD8,   // 2DD8..2DDE; ETHIOPIC
+            0x2DDF,   // 2DDF      ; UNKNOWN
             0x2DE0,   // 2DE0..2DFF; CYRILLIC
-            0x2E00,   // 2E00..2E7F; COMMON
-            0x2E80,   // 2E80..2FEF; HAN
-            0x2FF0,   // 2FF0..3004; COMMON
-            0x3005,   // 3005..3005; HAN
-            0x3006,   // 3006..3006; COMMON
-            0x3007,   // 3007..3007; HAN
+            0x2E00,   // 2E00..2E42; COMMON
+            0x2E43,   // 2E43..2E7F; UNKNOWN
+            0x2E80,   // 2E80..2E99; HAN
+            0x2E9A,   // 2E9A      ; UNKNOWN
+            0x2E9B,   // 2E9B..2EF3; HAN
+            0x2EF4,   // 2EF4..2EFF; UNKNOWN
+            0x2F00,   // 2F00..2FD5; HAN
+            0x2FD6,   // 2FD6..2FEF; UNKNOWN
+            0x2FF0,   // 2FF0..2FFB; COMMON
+            0x2FFC,   // 2FFC..2FFF; UNKNOWN
+            0x3000,   // 3000..3004; COMMON
+            0x3005,   // 3005      ; HAN
+            0x3006,   // 3006      ; COMMON
+            0x3007,   // 3007      ; HAN
             0x3008,   // 3008..3020; COMMON
             0x3021,   // 3021..3029; HAN
             0x302A,   // 302A..302D; INHERITED
             0x302E,   // 302E..302F; HANGUL
             0x3030,   // 3030..3037; COMMON
             0x3038,   // 3038..303B; HAN
-            0x303C,   // 303C..3040; COMMON
-            0x3041,   // 3041..3098; HIRAGANA
+            0x303C,   // 303C..303F; COMMON
+            0x3040,   // 3040      ; UNKNOWN
+            0x3041,   // 3041..3096; HIRAGANA
+            0x3097,   // 3097..3098; UNKNOWN
             0x3099,   // 3099..309A; INHERITED
             0x309B,   // 309B..309C; COMMON
             0x309D,   // 309D..309F; HIRAGANA
-            0x30A0,   // 30A0..30A0; COMMON
+            0x30A0,   // 30A0      ; COMMON
             0x30A1,   // 30A1..30FA; KATAKANA
             0x30FB,   // 30FB..30FC; COMMON
-            0x30FD,   // 30FD..3104; KATAKANA
-            0x3105,   // 3105..3130; BOPOMOFO
-            0x3131,   // 3131..318F; HANGUL
+            0x30FD,   // 30FD..30FF; KATAKANA
+            0x3100,   // 3100..3104; UNKNOWN
+            0x3105,   // 3105..312D; BOPOMOFO
+            0x312E,   // 312E..3130; UNKNOWN
+            0x3131,   // 3131..318E; HANGUL
+            0x318F,   // 318F      ; UNKNOWN
             0x3190,   // 3190..319F; COMMON
-            0x31A0,   // 31A0..31BF; BOPOMOFO
-            0x31C0,   // 31C0..31EF; COMMON
+            0x31A0,   // 31A0..31BA; BOPOMOFO
+            0x31BB,   // 31BB..31BF; UNKNOWN
+            0x31C0,   // 31C0..31E3; COMMON
+            0x31E4,   // 31E4..31EF; UNKNOWN
             0x31F0,   // 31F0..31FF; KATAKANA
-            0x3200,   // 3200..321F; HANGUL
+            0x3200,   // 3200..321E; HANGUL
+            0x321F,   // 321F      ; UNKNOWN
             0x3220,   // 3220..325F; COMMON
             0x3260,   // 3260..327E; HANGUL
             0x327F,   // 327F..32CF; COMMON
-            0x32D0,   // 32D0..3357; KATAKANA
+            0x32D0,   // 32D0..32FE; KATAKANA
+            0x32FF,   // 32FF      ; UNKNOWN
+            0x3300,   // 3300..3357; KATAKANA
             0x3358,   // 3358..33FF; COMMON
-            0x3400,   // 3400..4DBF; HAN
+            0x3400,   // 3400..4DB5; HAN
+            0x4DB6,   // 4DB6..4DBF; UNKNOWN
             0x4DC0,   // 4DC0..4DFF; COMMON
-            0x4E00,   // 4E00..9FFF; HAN
-            0xA000,   // A000..A4CF; YI
+            0x4E00,   // 4E00..9FCC; HAN
+            0x9FCD,   // 9FCD..9FFF; UNKNOWN
+            0xA000,   // A000..A48C; YI
+            0xA48D,   // A48D..A48F; UNKNOWN
+            0xA490,   // A490..A4C6; YI
+            0xA4C7,   // A4C7..A4CF; UNKNOWN
             0xA4D0,   // A4D0..A4FF; LISU
-            0xA500,   // A500..A63F; VAI
-            0xA640,   // A640..A69F; CYRILLIC
-            0xA6A0,   // A6A0..A6FF; BAMUM
+            0xA500,   // A500..A62B; VAI
+            0xA62C,   // A62C..A63F; UNKNOWN
+            0xA640,   // A640..A69D; CYRILLIC
+            0xA69E,   // A69E      ; UNKNOWN
+            0xA69F,   // A69F      ; CYRILLIC
+            0xA6A0,   // A6A0..A6F7; BAMUM
+            0xA6F8,   // A6F8..A6FF; UNKNOWN
             0xA700,   // A700..A721; COMMON
             0xA722,   // A722..A787; LATIN
             0xA788,   // A788..A78A; COMMON
-            0xA78B,   // A78B..A7FF; LATIN
-            0xA800,   // A800..A82F; SYLOTI_NAGRI
-            0xA830,   // A830..A83F; COMMON
-            0xA840,   // A840..A87F; PHAGS_PA
-            0xA880,   // A880..A8DF; SAURASHTRA
-            0xA8E0,   // A8E0..A8FF; DEVANAGARI
-            0xA900,   // A900..A92F; KAYAH_LI
-            0xA930,   // A930..A95F; REJANG
-            0xA960,   // A960..A97F; HANGUL
-            0xA980,   // A980..A9FF; JAVANESE
-            0xAA00,   // AA00..AA5F; CHAM
+            0xA78B,   // A78B..A78E; LATIN
+            0xA78F,   // A78F      ; UNKNOWN
+            0xA790,   // A790..A7AD; LATIN
+            0xA7AE,   // A7AE..A7AF; UNKNOWN
+            0xA7B0,   // A7B0..A7B1; LATIN
+            0xA7B2,   // A7B2..A7F6; UNKNOWN
+            0xA7F7,   // A7F7..A7FF; LATIN
+            0xA800,   // A800..A82B; SYLOTI_NAGRI
+            0xA82C,   // A82C..A82F; UNKNOWN
+            0xA830,   // A830..A839; COMMON
+            0xA83A,   // A83A..A83F; UNKNOWN
+            0xA840,   // A840..A877; PHAGS_PA
+            0xA878,   // A878..A87F; UNKNOWN
+            0xA880,   // A880..A8C4; SAURASHTRA
+            0xA8C5,   // A8C5..A8CD; UNKNOWN
+            0xA8CE,   // A8CE..A8D9; SAURASHTRA
+            0xA8DA,   // A8DA..A8DF; UNKNOWN
+            0xA8E0,   // A8E0..A8FB; DEVANAGARI
+            0xA8FC,   // A8FC..A8FF; UNKNOWN
+            0xA900,   // A900..A92D; KAYAH_LI
+            0xA92E,   // A92E      ; COMMON
+            0xA92F,   // A92F      ; KAYAH_LI
+            0xA930,   // A930..A953; REJANG
+            0xA954,   // A954..A95E; UNKNOWN
+            0xA95F,   // A95F      ; REJANG
+            0xA960,   // A960..A97C; HANGUL
+            0xA97D,   // A97D..A97F; UNKNOWN
+            0xA980,   // A980..A9CD; JAVANESE
+            0xA9CE,   // A9CE      ; UNKNOWN
+            0xA9CF,   // A9CF      ; COMMON
+            0xA9D0,   // A9D0..A9D9; JAVANESE
+            0xA9DA,   // A9DA..A9DD; UNKNOWN
+            0xA9DE,   // A9DE..A9DF; JAVANESE
+            0xA9E0,   // A9E0..A9FE; MYANMAR
+            0xA9FF,   // A9FF      ; UNKNOWN
+            0xAA00,   // AA00..AA36; CHAM
+            0xAA37,   // AA37..AA3F; UNKNOWN
+            0xAA40,   // AA40..AA4D; CHAM
+            0xAA4E,   // AA4E..AA4F; UNKNOWN
+            0xAA50,   // AA50..AA59; CHAM
+            0xAA5A,   // AA5A..AA5B; UNKNOWN
+            0xAA5C,   // AA5C..AA5F; CHAM
             0xAA60,   // AA60..AA7F; MYANMAR
-            0xAA80,   // AA80..AADF; TAI_VIET
-            0xAAE0,   // AAE0..AB00; MEETEI_MAYEK
-            0xAB01,   // AB01..ABBF; ETHIOPIC
-            0xABC0,   // ABC0..ABFF; MEETEI_MAYEK
-            0xAC00,   // AC00..D7FB; HANGUL
+            0xAA80,   // AA80..AAC2; TAI_VIET
+            0xAAC3,   // AAC3..AADA; UNKNOWN
+            0xAADB,   // AADB..AADF; TAI_VIET
+            0xAAE0,   // AAE0..AAF6; MEETEI_MAYEK
+            0xAAF7,   // AAF7..AB00; UNKNOWN
+            0xAB01,   // AB01..AB06; ETHIOPIC
+            0xAB07,   // AB07..AB08; UNKNOWN
+            0xAB09,   // AB09..AB0E; ETHIOPIC
+            0xAB0F,   // AB0F..AB10; UNKNOWN
+            0xAB11,   // AB11..AB16; ETHIOPIC
+            0xAB17,   // AB17..AB1F; UNKNOWN
+            0xAB20,   // AB20..AB26; ETHIOPIC
+            0xAB27,   // AB27      ; UNKNOWN
+            0xAB28,   // AB28..AB2E; ETHIOPIC
+            0xAB2F,   // AB2F      ; UNKNOWN
+            0xAB30,   // AB30..AB5A; LATIN
+            0xAB5B,   // AB5B      ; COMMON
+            0xAB5C,   // AB5C..AB5F; LATIN
+            0xAB60,   // AB60..AB63; UNKNOWN
+            0xAB64,   // AB64      ; LATIN
+            0xAB65,   // AB65      ; GREEK
+            0xAB66,   // AB66..ABBF; UNKNOWN
+            0xABC0,   // ABC0..ABED; MEETEI_MAYEK
+            0xABEE,   // ABEE..ABEF; UNKNOWN
+            0xABF0,   // ABF0..ABF9; MEETEI_MAYEK
+            0xABFA,   // ABFA..ABFF; UNKNOWN
+            0xAC00,   // AC00..D7A3; HANGUL
+            0xD7A4,   // D7A4..D7AF; UNKNOWN
+            0xD7B0,   // D7B0..D7C6; HANGUL
+            0xD7C7,   // D7C7..D7CA; UNKNOWN
+            0xD7CB,   // D7CB..D7FB; HANGUL
             0xD7FC,   // D7FC..F8FF; UNKNOWN
-            0xF900,   // F900..FAFF; HAN
-            0xFB00,   // FB00..FB12; LATIN
-            0xFB13,   // FB13..FB1C; ARMENIAN
-            0xFB1D,   // FB1D..FB4F; HEBREW
-            0xFB50,   // FB50..FD3D; ARABIC
-            0xFD3E,   // FD3E..FD4F; COMMON
-            0xFD50,   // FD50..FDFC; ARABIC
-            0xFDFD,   // FDFD..FDFF; COMMON
+            0xF900,   // F900..FA6D; HAN
+            0xFA6E,   // FA6E..FA6F; UNKNOWN
+            0xFA70,   // FA70..FAD9; HAN
+            0xFADA,   // FADA..FAFF; UNKNOWN
+            0xFB00,   // FB00..FB06; LATIN
+            0xFB07,   // FB07..FB12; UNKNOWN
+            0xFB13,   // FB13..FB17; ARMENIAN
+            0xFB18,   // FB18..FB1C; UNKNOWN
+            0xFB1D,   // FB1D..FB36; HEBREW
+            0xFB37,   // FB37      ; UNKNOWN
+            0xFB38,   // FB38..FB3C; HEBREW
+            0xFB3D,   // FB3D      ; UNKNOWN
+            0xFB3E,   // FB3E      ; HEBREW
+            0xFB3F,   // FB3F      ; UNKNOWN
+            0xFB40,   // FB40..FB41; HEBREW
+            0xFB42,   // FB42      ; UNKNOWN
+            0xFB43,   // FB43..FB44; HEBREW
+            0xFB45,   // FB45      ; UNKNOWN
+            0xFB46,   // FB46..FB4F; HEBREW
+            0xFB50,   // FB50..FBC1; ARABIC
+            0xFBC2,   // FBC2..FBD2; UNKNOWN
+            0xFBD3,   // FBD3..FD3D; ARABIC
+            0xFD3E,   // FD3E..FD3F; COMMON
+            0xFD40,   // FD40..FD4F; UNKNOWN
+            0xFD50,   // FD50..FD8F; ARABIC
+            0xFD90,   // FD90..FD91; UNKNOWN
+            0xFD92,   // FD92..FDC7; ARABIC
+            0xFDC8,   // FDC8..FDEF; UNKNOWN
+            0xFDF0,   // FDF0..FDFD; ARABIC
+            0xFDFE,   // FDFE..FDFF; UNKNOWN
             0xFE00,   // FE00..FE0F; INHERITED
-            0xFE10,   // FE10..FE1F; COMMON
-            0xFE20,   // FE20..FE2F; INHERITED
-            0xFE30,   // FE30..FE6F; COMMON
-            0xFE70,   // FE70..FEFE; ARABIC
-            0xFEFF,   // FEFF..FF20; COMMON
+            0xFE10,   // FE10..FE19; COMMON
+            0xFE1A,   // FE1A..FE1F; UNKNOWN
+            0xFE20,   // FE20..FE2D; INHERITED
+            0xFE2E,   // FE2E..FE2F; UNKNOWN
+            0xFE30,   // FE30..FE52; COMMON
+            0xFE53,   // FE53      ; UNKNOWN
+            0xFE54,   // FE54..FE66; COMMON
+            0xFE67,   // FE67      ; UNKNOWN
+            0xFE68,   // FE68..FE6B; COMMON
+            0xFE6C,   // FE6C..FE6F; UNKNOWN
+            0xFE70,   // FE70..FE74; ARABIC
+            0xFE75,   // FE75      ; UNKNOWN
+            0xFE76,   // FE76..FEFC; ARABIC
+            0xFEFD,   // FEFD..FEFE; UNKNOWN
+            0xFEFF,   // FEFF      ; COMMON
+            0xFF00,   // FF00      ; UNKNOWN
+            0xFF01,   // FF01..FF20; COMMON
             0xFF21,   // FF21..FF3A; LATIN
             0xFF3B,   // FF3B..FF40; COMMON
             0xFF41,   // FF41..FF5A; LATIN
             0xFF5B,   // FF5B..FF65; COMMON
             0xFF66,   // FF66..FF6F; KATAKANA
-            0xFF70,   // FF70..FF70; COMMON
+            0xFF70,   // FF70      ; COMMON
             0xFF71,   // FF71..FF9D; KATAKANA
             0xFF9E,   // FF9E..FF9F; COMMON
-            0xFFA0,   // FFA0..FFDF; HANGUL
-            0xFFE0,   // FFE0..FFFF; COMMON
-            0x10000,  // 10000..100FF; LINEAR_B
-            0x10100,  // 10100..1013F; COMMON
-            0x10140,  // 10140..1018F; GREEK
-            0x10190,  // 10190..101FC; COMMON
-            0x101FD,  // 101FD..1027F; INHERITED
-            0x10280,  // 10280..1029F; LYCIAN
-            0x102A0,  // 102A0..102FF; CARIAN
-            0x10300,  // 10300..1032F; OLD_ITALIC
-            0x10330,  // 10330..1037F; GOTHIC
-            0x10380,  // 10380..1039F; UGARITIC
-            0x103A0,  // 103A0..103FF; OLD_PERSIAN
+            0xFFA0,   // FFA0..FFBE; HANGUL
+            0xFFBF,   // FFBF..FFC1; UNKNOWN
+            0xFFC2,   // FFC2..FFC7; HANGUL
+            0xFFC8,   // FFC8..FFC9; UNKNOWN
+            0xFFCA,   // FFCA..FFCF; HANGUL
+            0xFFD0,   // FFD0..FFD1; UNKNOWN
+            0xFFD2,   // FFD2..FFD7; HANGUL
+            0xFFD8,   // FFD8..FFD9; UNKNOWN
+            0xFFDA,   // FFDA..FFDC; HANGUL
+            0xFFDD,   // FFDD..FFDF; UNKNOWN
+            0xFFE0,   // FFE0..FFE6; COMMON
+            0xFFE7,   // FFE7      ; UNKNOWN
+            0xFFE8,   // FFE8..FFEE; COMMON
+            0xFFEF,   // FFEF..FFF8; UNKNOWN
+            0xFFF9,   // FFF9..FFFD; COMMON
+            0xFFFE,   // FFFE..FFFF; UNKNOWN
+            0x10000,  // 10000..1000B; LINEAR_B
+            0x1000C,  // 1000C       ; UNKNOWN
+            0x1000D,  // 1000D..10026; LINEAR_B
+            0x10027,  // 10027       ; UNKNOWN
+            0x10028,  // 10028..1003A; LINEAR_B
+            0x1003B,  // 1003B       ; UNKNOWN
+            0x1003C,  // 1003C..1003D; LINEAR_B
+            0x1003E,  // 1003E       ; UNKNOWN
+            0x1003F,  // 1003F..1004D; LINEAR_B
+            0x1004E,  // 1004E..1004F; UNKNOWN
+            0x10050,  // 10050..1005D; LINEAR_B
+            0x1005E,  // 1005E..1007F; UNKNOWN
+            0x10080,  // 10080..100FA; LINEAR_B
+            0x100FB,  // 100FB..100FF; UNKNOWN
+            0x10100,  // 10100..10102; COMMON
+            0x10103,  // 10103..10106; UNKNOWN
+            0x10107,  // 10107..10133; COMMON
+            0x10134,  // 10134..10136; UNKNOWN
+            0x10137,  // 10137..1013F; COMMON
+            0x10140,  // 10140..1018C; GREEK
+            0x1018D,  // 1018D..1018F; UNKNOWN
+            0x10190,  // 10190..1019B; COMMON
+            0x1019C,  // 1019C..1019F; UNKNOWN
+            0x101A0,  // 101A0       ; GREEK
+            0x101A1,  // 101A1..101CF; UNKNOWN
+            0x101D0,  // 101D0..101FC; COMMON
+            0x101FD,  // 101FD       ; INHERITED
+            0x101FE,  // 101FE..1027F; UNKNOWN
+            0x10280,  // 10280..1029C; LYCIAN
+            0x1029D,  // 1029D..1029F; UNKNOWN
+            0x102A0,  // 102A0..102D0; CARIAN
+            0x102D1,  // 102D1..102DF; UNKNOWN
+            0x102E0,  // 102E0       ; INHERITED
+            0x102E1,  // 102E1..102FB; COMMON
+            0x102FC,  // 102FC..102FF; UNKNOWN
+            0x10300,  // 10300..10323; OLD_ITALIC
+            0x10324,  // 10324..1032F; UNKNOWN
+            0x10330,  // 10330..1034A; GOTHIC
+            0x1034B,  // 1034B..1034F; UNKNOWN
+            0x10350,  // 10350..1037A; OLD_PERMIC
+            0x1037B,  // 1037B..1037F; UNKNOWN
+            0x10380,  // 10380..1039D; UGARITIC
+            0x1039E,  // 1039E       ; UNKNOWN
+            0x1039F,  // 1039F       ; UGARITIC
+            0x103A0,  // 103A0..103C3; OLD_PERSIAN
+            0x103C4,  // 103C4..103C7; UNKNOWN
+            0x103C8,  // 103C8..103D5; OLD_PERSIAN
+            0x103D6,  // 103D6..103FF; UNKNOWN
             0x10400,  // 10400..1044F; DESERET
             0x10450,  // 10450..1047F; SHAVIAN
-            0x10480,  // 10480..107FF; OSMANYA
-            0x10800,  // 10800..1083F; CYPRIOT
-            0x10840,  // 10840..108FF; IMPERIAL_ARAMAIC
-            0x10900,  // 10900..1091F; PHOENICIAN
-            0x10920,  // 10920..1097F; LYDIAN
+            0x10480,  // 10480..1049D; OSMANYA
+            0x1049E,  // 1049E..1049F; UNKNOWN
+            0x104A0,  // 104A0..104A9; OSMANYA
+            0x104AA,  // 104AA..104FF; UNKNOWN
+            0x10500,  // 10500..10527; ELBASAN
+            0x10528,  // 10528..1052F; UNKNOWN
+            0x10530,  // 10530..10563; CAUCASIAN_ALBANIAN
+            0x10564,  // 10564..1056E; UNKNOWN
+            0x1056F,  // 1056F       ; CAUCASIAN_ALBANIAN
+            0x10570,  // 10570..105FF; UNKNOWN
+            0x10600,  // 10600..10736; LINEAR_A
+            0x10737,  // 10737..1073F; UNKNOWN
+            0x10740,  // 10740..10755; LINEAR_A
+            0x10756,  // 10756..1075F; UNKNOWN
+            0x10760,  // 10760..10767; LINEAR_A
+            0x10768,  // 10768..107FF; UNKNOWN
+            0x10800,  // 10800..10805; CYPRIOT
+            0x10806,  // 10806..10807; UNKNOWN
+            0x10808,  // 10808       ; CYPRIOT
+            0x10809,  // 10809       ; UNKNOWN
+            0x1080A,  // 1080A..10835; CYPRIOT
+            0x10836,  // 10836       ; UNKNOWN
+            0x10837,  // 10837..10838; CYPRIOT
+            0x10839,  // 10839..1083B; UNKNOWN
+            0x1083C,  // 1083C       ; CYPRIOT
+            0x1083D,  // 1083D..1083E; UNKNOWN
+            0x1083F,  // 1083F       ; CYPRIOT
+            0x10840,  // 10840..10855; IMPERIAL_ARAMAIC
+            0x10856,  // 10856       ; UNKNOWN
+            0x10857,  // 10857..1085F; IMPERIAL_ARAMAIC
+            0x10860,  // 10860..1087F; PALMYRENE
+            0x10880,  // 10880..1089E; NABATAEAN
+            0x1089F,  // 1089F..108A6; UNKNOWN
+            0x108A7,  // 108A7..108AF; NABATAEAN
+            0x108B0,  // 108B0..108FF; UNKNOWN
+            0x10900,  // 10900..1091B; PHOENICIAN
+            0x1091C,  // 1091C..1091E; UNKNOWN
+            0x1091F,  // 1091F       ; PHOENICIAN
+            0x10920,  // 10920..10939; LYDIAN
+            0x1093A,  // 1093A..1093E; UNKNOWN
+            0x1093F,  // 1093F       ; LYDIAN
+            0x10940,  // 10940..1097F; UNKNOWN
             0x10980,  // 10980..1099F; MEROITIC_HIEROGLYPHS
-            0x109A0,  // 109A0..109FF; MEROITIC_CURSIVE
-            0x10A00,  // 10A00..10A5F; KHAROSHTHI
-            0x10A60,  // 10A60..10AFF; OLD_SOUTH_ARABIAN
-            0x10B00,  // 10B00..10B3F; AVESTAN
-            0x10B40,  // 10B40..10B5F; INSCRIPTIONAL_PARTHIAN
-            0x10B60,  // 10B60..10BFF; INSCRIPTIONAL_PAHLAVI
-            0x10C00,  // 10C00..10E5F; OLD_TURKIC
-            0x10E60,  // 10E60..10FFF; ARABIC
-            0x11000,  // 11000..1107F; BRAHMI
-            0x11080,  // 11080..110CF; KAITHI
-            0x110D0,  // 110D0..110FF; SORA_SOMPENG
-            0x11100,  // 11100..1117F; CHAKMA
-            0x11180,  // 11180..1167F; SHARADA
-            0x11680,  // 11680..116CF; TAKRI
-            0x12000,  // 12000..12FFF; CUNEIFORM
-            0x13000,  // 13000..167FF; EGYPTIAN_HIEROGLYPHS
+            0x109A0,  // 109A0..109B7; MEROITIC_CURSIVE
+            0x109B8,  // 109B8..109BD; UNKNOWN
+            0x109BE,  // 109BE..109BF; MEROITIC_CURSIVE
+            0x109C0,  // 109C0..109FF; UNKNOWN
+            0x10A00,  // 10A00..10A03; KHAROSHTHI
+            0x10A04,  // 10A04       ; UNKNOWN
+            0x10A05,  // 10A05..10A06; KHAROSHTHI
+            0x10A07,  // 10A07..10A0B; UNKNOWN
+            0x10A0C,  // 10A0C..10A13; KHAROSHTHI
+            0x10A14,  // 10A14       ; UNKNOWN
+            0x10A15,  // 10A15..10A17; KHAROSHTHI
+            0x10A18,  // 10A18       ; UNKNOWN
+            0x10A19,  // 10A19..10A33; KHAROSHTHI
+            0x10A34,  // 10A34..10A37; UNKNOWN
+            0x10A38,  // 10A38..10A3A; KHAROSHTHI
+            0x10A3B,  // 10A3B..10A3E; UNKNOWN
+            0x10A3F,  // 10A3F..10A47; KHAROSHTHI
+            0x10A48,  // 10A48..10A4F; UNKNOWN
+            0x10A50,  // 10A50..10A58; KHAROSHTHI
+            0x10A59,  // 10A59..10A5F; UNKNOWN
+            0x10A60,  // 10A60..10A7F; OLD_SOUTH_ARABIAN
+            0x10A80,  // 10A80..10A9F; OLD_NORTH_ARABIAN
+            0x10AA0,  // 10AA0..10ABF; UNKNOWN
+            0x10AC0,  // 10AC0..10AE6; MANICHAEAN
+            0x10AE7,  // 10AE7..10AEA; UNKNOWN
+            0x10AEB,  // 10AEB..10AF6; MANICHAEAN
+            0x10AF7,  // 10AF7..10AFF; UNKNOWN
+            0x10B00,  // 10B00..10B35; AVESTAN
+            0x10B36,  // 10B36..10B38; UNKNOWN
+            0x10B39,  // 10B39..10B3F; AVESTAN
+            0x10B40,  // 10B40..10B55; INSCRIPTIONAL_PARTHIAN
+            0x10B56,  // 10B56..10B57; UNKNOWN
+            0x10B58,  // 10B58..10B5F; INSCRIPTIONAL_PARTHIAN
+            0x10B60,  // 10B60..10B72; INSCRIPTIONAL_PAHLAVI
+            0x10B73,  // 10B73..10B77; UNKNOWN
+            0x10B78,  // 10B78..10B7F; INSCRIPTIONAL_PAHLAVI
+            0x10B80,  // 10B80..10B91; PSALTER_PAHLAVI
+            0x10B92,  // 10B92..10B98; UNKNOWN
+            0x10B99,  // 10B99..10B9C; PSALTER_PAHLAVI
+            0x10B9D,  // 10B9D..10BA8; UNKNOWN
+            0x10BA9,  // 10BA9..10BAF; PSALTER_PAHLAVI
+            0x10BB0,  // 10BB0..10BFF; UNKNOWN
+            0x10C00,  // 10C00..10C48; OLD_TURKIC
+            0x10C49,  // 10C49..10E5F; UNKNOWN
+            0x10E60,  // 10E60..10E7E; ARABIC
+            0x10E7F,  // 10E7F..10FFF; UNKNOWN
+            0x11000,  // 11000..1104D; BRAHMI
+            0x1104E,  // 1104E..11051; UNKNOWN
+            0x11052,  // 11052..1106F; BRAHMI
+            0x11070,  // 11070..1107E; UNKNOWN
+            0x1107F,  // 1107F       ; BRAHMI
+            0x11080,  // 11080..110C1; KAITHI
+            0x110C2,  // 110C2..110CF; UNKNOWN
+            0x110D0,  // 110D0..110E8; SORA_SOMPENG
+            0x110E9,  // 110E9..110EF; UNKNOWN
+            0x110F0,  // 110F0..110F9; SORA_SOMPENG
+            0x110FA,  // 110FA..110FF; UNKNOWN
+            0x11100,  // 11100..11134; CHAKMA
+            0x11135,  // 11135       ; UNKNOWN
+            0x11136,  // 11136..11143; CHAKMA
+            0x11144,  // 11144..1114F; UNKNOWN
+            0x11150,  // 11150..11176; MAHAJANI
+            0x11177,  // 11177..1117F; UNKNOWN
+            0x11180,  // 11180..111C8; SHARADA
+            0x111C9,  // 111C9..111CC; UNKNOWN
+            0x111CD,  // 111CD       ; SHARADA
+            0x111CE,  // 111CE..111CF; UNKNOWN
+            0x111D0,  // 111D0..111DA; SHARADA
+            0x111DB,  // 111DB..111E0; UNKNOWN
+            0x111E1,  // 111E1..111F4; SINHALA
+            0x111F5,  // 111F5..111FF; UNKNOWN
+            0x11200,  // 11200..11211; KHOJKI
+            0x11212,  // 11212       ; UNKNOWN
+            0x11213,  // 11213..1123D; KHOJKI
+            0x1123E,  // 1123E..112AF; UNKNOWN
+            0x112B0,  // 112B0..112EA; KHUDAWADI
+            0x112EB,  // 112EB..112EF; UNKNOWN
+            0x112F0,  // 112F0..112F9; KHUDAWADI
+            0x112FA,  // 112FA..11300; UNKNOWN
+            0x11301,  // 11301..11303; GRANTHA
+            0x11304,  // 11304       ; UNKNOWN
+            0x11305,  // 11305..1130C; GRANTHA
+            0x1130D,  // 1130D..1130E; UNKNOWN
+            0x1130F,  // 1130F..11310; GRANTHA
+            0x11311,  // 11311..11312; UNKNOWN
+            0x11313,  // 11313..11328; GRANTHA
+            0x11329,  // 11329       ; UNKNOWN
+            0x1132A,  // 1132A..11330; GRANTHA
+            0x11331,  // 11331       ; UNKNOWN
+            0x11332,  // 11332..11333; GRANTHA
+            0x11334,  // 11334       ; UNKNOWN
+            0x11335,  // 11335..11339; GRANTHA
+            0x1133A,  // 1133A..1133B; UNKNOWN
+            0x1133C,  // 1133C..11344; GRANTHA
+            0x11345,  // 11345..11346; UNKNOWN
+            0x11347,  // 11347..11348; GRANTHA
+            0x11349,  // 11349..1134A; UNKNOWN
+            0x1134B,  // 1134B..1134D; GRANTHA
+            0x1134E,  // 1134E..11356; UNKNOWN
+            0x11357,  // 11357       ; GRANTHA
+            0x11358,  // 11358..1135C; UNKNOWN
+            0x1135D,  // 1135D..11363; GRANTHA
+            0x11364,  // 11364..11365; UNKNOWN
+            0x11366,  // 11366..1136C; GRANTHA
+            0x1136D,  // 1136D..1136F; UNKNOWN
+            0x11370,  // 11370..11374; GRANTHA
+            0x11375,  // 11375..1147F; UNKNOWN
+            0x11480,  // 11480..114C7; TIRHUTA
+            0x114C8,  // 114C8..114CF; UNKNOWN
+            0x114D0,  // 114D0..114D9; TIRHUTA
+            0x114DA,  // 114DA..1157F; UNKNOWN
+            0x11580,  // 11580..115B5; SIDDHAM
+            0x115B6,  // 115B6..115B7; UNKNOWN
+            0x115B8,  // 115B8..115C9; SIDDHAM
+            0x115CA,  // 115CA..115FF; UNKNOWN
+            0x11600,  // 11600..11644; MODI
+            0x11645,  // 11645..1164F; UNKNOWN
+            0x11650,  // 11650..11659; MODI
+            0x1165A,  // 1165A..1167F; UNKNOWN
+            0x11680,  // 11680..116B7; TAKRI
+            0x116B8,  // 116B8..116BF; UNKNOWN
+            0x116C0,  // 116C0..116C9; TAKRI
+            0x116CA,  // 116CA..1189F; UNKNOWN
+            0x118A0,  // 118A0..118F2; WARANG_CITI
+            0x118F3,  // 118F3..118FE; UNKNOWN
+            0x118FF,  // 118FF       ; WARANG_CITI
+            0x11900,  // 11900..11ABF; UNKNOWN
+            0x11AC0,  // 11AC0..11AF8; PAU_CIN_HAU
+            0x11AF9,  // 11AF9..11FFF; UNKNOWN
+            0x12000,  // 12000..12398; CUNEIFORM
+            0x12399,  // 12399..123FF; UNKNOWN
+            0x12400,  // 12400..1246E; CUNEIFORM
+            0x1246F,  // 1246F       ; UNKNOWN
+            0x12470,  // 12470..12474; CUNEIFORM
+            0x12475,  // 12475..12FFF; UNKNOWN
+            0x13000,  // 13000..1342E; EGYPTIAN_HIEROGLYPHS
+            0x1342F,  // 1342F..167FF; UNKNOWN
             0x16800,  // 16800..16A38; BAMUM
-            0x16F00,  // 16F00..16F9F; MIAO
-            0x1B000,  // 1B000..1B000; KATAKANA
-            0x1B001,  // 1B001..1CFFF; HIRAGANA
-            0x1D000,  // 1D000..1D166; COMMON
+            0x16A39,  // 16A39..16A3F; UNKNOWN
+            0x16A40,  // 16A40..16A5E; MRO
+            0x16A5F,  // 16A5F       ; UNKNOWN
+            0x16A60,  // 16A60..16A69; MRO
+            0x16A6A,  // 16A6A..16A6D; UNKNOWN
+            0x16A6E,  // 16A6E..16A6F; MRO
+            0x16A70,  // 16A70..16ACF; UNKNOWN
+            0x16AD0,  // 16AD0..16AED; BASSA_VAH
+            0x16AEE,  // 16AEE..16AEF; UNKNOWN
+            0x16AF0,  // 16AF0..16AF5; BASSA_VAH
+            0x16AF6,  // 16AF6..16AFF; UNKNOWN
+            0x16B00,  // 16B00..16B45; PAHAWH_HMONG
+            0x16B46,  // 16B46..16B4F; UNKNOWN
+            0x16B50,  // 16B50..16B59; PAHAWH_HMONG
+            0x16B5A,  // 16B5A       ; UNKNOWN
+            0x16B5B,  // 16B5B..16B61; PAHAWH_HMONG
+            0x16B62,  // 16B62       ; UNKNOWN
+            0x16B63,  // 16B63..16B77; PAHAWH_HMONG
+            0x16B78,  // 16B78..16B7C; UNKNOWN
+            0x16B7D,  // 16B7D..16B8F; PAHAWH_HMONG
+            0x16B90,  // 16B90..16EFF; UNKNOWN
+            0x16F00,  // 16F00..16F44; MIAO
+            0x16F45,  // 16F45..16F4F; UNKNOWN
+            0x16F50,  // 16F50..16F7E; MIAO
+            0x16F7F,  // 16F7F..16F8E; UNKNOWN
+            0x16F8F,  // 16F8F..16F9F; MIAO
+            0x16FA0,  // 16FA0..1AFFF; UNKNOWN
+            0x1B000,  // 1B000       ; KATAKANA
+            0x1B001,  // 1B001       ; HIRAGANA
+            0x1B002,  // 1B002..1BBFF; UNKNOWN
+            0x1BC00,  // 1BC00..1BC6A; DUPLOYAN
+            0x1BC6B,  // 1BC6B..1BC6F; UNKNOWN
+            0x1BC70,  // 1BC70..1BC7C; DUPLOYAN
+            0x1BC7D,  // 1BC7D..1BC7F; UNKNOWN
+            0x1BC80,  // 1BC80..1BC88; DUPLOYAN
+            0x1BC89,  // 1BC89..1BC8F; UNKNOWN
+            0x1BC90,  // 1BC90..1BC99; DUPLOYAN
+            0x1BC9A,  // 1BC9A..1BC9B; UNKNOWN
+            0x1BC9C,  // 1BC9C..1BC9F; DUPLOYAN
+            0x1BCA0,  // 1BCA0..1BCA3; COMMON
+            0x1BCA4,  // 1BCA4..1CFFF; UNKNOWN
+            0x1D000,  // 1D000..1D0F5; COMMON
+            0x1D0F6,  // 1D0F6..1D0FF; UNKNOWN
+            0x1D100,  // 1D100..1D126; COMMON
+            0x1D127,  // 1D127..1D128; UNKNOWN
+            0x1D129,  // 1D129..1D166; COMMON
             0x1D167,  // 1D167..1D169; INHERITED
             0x1D16A,  // 1D16A..1D17A; COMMON
             0x1D17B,  // 1D17B..1D182; INHERITED
@@ -4020,354 +5420,1635 @@
             0x1D185,  // 1D185..1D18B; INHERITED
             0x1D18C,  // 1D18C..1D1A9; COMMON
             0x1D1AA,  // 1D1AA..1D1AD; INHERITED
-            0x1D1AE,  // 1D1AE..1D1FF; COMMON
-            0x1D200,  // 1D200..1D2FF; GREEK
-            0x1D300,  // 1D300..1EDFF; COMMON
-            0x1EE00,  // 1EE00..1EFFF; ARABIC
-            0x1F000,  // 1F000..1F1FF; COMMON
-            0x1F200,  // 1F200..1F200; HIRAGANA
-            0x1F201,  // 1F210..1FFFF; COMMON
-            0x20000,  // 20000..E0000; HAN
-            0xE0001,  // E0001..E00FF; COMMON
+            0x1D1AE,  // 1D1AE..1D1DD; COMMON
+            0x1D1DE,  // 1D1DE..1D1FF; UNKNOWN
+            0x1D200,  // 1D200..1D245; GREEK
+            0x1D246,  // 1D246..1D2FF; UNKNOWN
+            0x1D300,  // 1D300..1D356; COMMON
+            0x1D357,  // 1D357..1D35F; UNKNOWN
+            0x1D360,  // 1D360..1D371; COMMON
+            0x1D372,  // 1D372..1D3FF; UNKNOWN
+            0x1D400,  // 1D400..1D454; COMMON
+            0x1D455,  // 1D455       ; UNKNOWN
+            0x1D456,  // 1D456..1D49C; COMMON
+            0x1D49D,  // 1D49D       ; UNKNOWN
+            0x1D49E,  // 1D49E..1D49F; COMMON
+            0x1D4A0,  // 1D4A0..1D4A1; UNKNOWN
+            0x1D4A2,  // 1D4A2       ; COMMON
+            0x1D4A3,  // 1D4A3..1D4A4; UNKNOWN
+            0x1D4A5,  // 1D4A5..1D4A6; COMMON
+            0x1D4A7,  // 1D4A7..1D4A8; UNKNOWN
+            0x1D4A9,  // 1D4A9..1D4AC; COMMON
+            0x1D4AD,  // 1D4AD       ; UNKNOWN
+            0x1D4AE,  // 1D4AE..1D4B9; COMMON
+            0x1D4BA,  // 1D4BA       ; UNKNOWN
+            0x1D4BB,  // 1D4BB       ; COMMON
+            0x1D4BC,  // 1D4BC       ; UNKNOWN
+            0x1D4BD,  // 1D4BD..1D4C3; COMMON
+            0x1D4C4,  // 1D4C4       ; UNKNOWN
+            0x1D4C5,  // 1D4C5..1D505; COMMON
+            0x1D506,  // 1D506       ; UNKNOWN
+            0x1D507,  // 1D507..1D50A; COMMON
+            0x1D50B,  // 1D50B..1D50C; UNKNOWN
+            0x1D50D,  // 1D50D..1D514; COMMON
+            0x1D515,  // 1D515       ; UNKNOWN
+            0x1D516,  // 1D516..1D51C; COMMON
+            0x1D51D,  // 1D51D       ; UNKNOWN
+            0x1D51E,  // 1D51E..1D539; COMMON
+            0x1D53A,  // 1D53A       ; UNKNOWN
+            0x1D53B,  // 1D53B..1D53E; COMMON
+            0x1D53F,  // 1D53F       ; UNKNOWN
+            0x1D540,  // 1D540..1D544; COMMON
+            0x1D545,  // 1D545       ; UNKNOWN
+            0x1D546,  // 1D546       ; COMMON
+            0x1D547,  // 1D547..1D549; UNKNOWN
+            0x1D54A,  // 1D54A..1D550; COMMON
+            0x1D551,  // 1D551       ; UNKNOWN
+            0x1D552,  // 1D552..1D6A5; COMMON
+            0x1D6A6,  // 1D6A6..1D6A7; UNKNOWN
+            0x1D6A8,  // 1D6A8..1D7CB; COMMON
+            0x1D7CC,  // 1D7CC..1D7CD; UNKNOWN
+            0x1D7CE,  // 1D7CE..1D7FF; COMMON
+            0x1D800,  // 1D800..1E7FF; UNKNOWN
+            0x1E800,  // 1E800..1E8C4; MENDE_KIKAKUI
+            0x1E8C5,  // 1E8C5..1E8C6; UNKNOWN
+            0x1E8C7,  // 1E8C7..1E8D6; MENDE_KIKAKUI
+            0x1E8D7,  // 1E8D7..1EDFF; UNKNOWN
+            0x1EE00,  // 1EE00..1EE03; ARABIC
+            0x1EE04,  // 1EE04       ; UNKNOWN
+            0x1EE05,  // 1EE05..1EE1F; ARABIC
+            0x1EE20,  // 1EE20       ; UNKNOWN
+            0x1EE21,  // 1EE21..1EE22; ARABIC
+            0x1EE23,  // 1EE23       ; UNKNOWN
+            0x1EE24,  // 1EE24       ; ARABIC
+            0x1EE25,  // 1EE25..1EE26; UNKNOWN
+            0x1EE27,  // 1EE27       ; ARABIC
+            0x1EE28,  // 1EE28       ; UNKNOWN
+            0x1EE29,  // 1EE29..1EE32; ARABIC
+            0x1EE33,  // 1EE33       ; UNKNOWN
+            0x1EE34,  // 1EE34..1EE37; ARABIC
+            0x1EE38,  // 1EE38       ; UNKNOWN
+            0x1EE39,  // 1EE39       ; ARABIC
+            0x1EE3A,  // 1EE3A       ; UNKNOWN
+            0x1EE3B,  // 1EE3B       ; ARABIC
+            0x1EE3C,  // 1EE3C..1EE41; UNKNOWN
+            0x1EE42,  // 1EE42       ; ARABIC
+            0x1EE43,  // 1EE43..1EE46; UNKNOWN
+            0x1EE47,  // 1EE47       ; ARABIC
+            0x1EE48,  // 1EE48       ; UNKNOWN
+            0x1EE49,  // 1EE49       ; ARABIC
+            0x1EE4A,  // 1EE4A       ; UNKNOWN
+            0x1EE4B,  // 1EE4B       ; ARABIC
+            0x1EE4C,  // 1EE4C       ; UNKNOWN
+            0x1EE4D,  // 1EE4D..1EE4F; ARABIC
+            0x1EE50,  // 1EE50       ; UNKNOWN
+            0x1EE51,  // 1EE51..1EE52; ARABIC
+            0x1EE53,  // 1EE53       ; UNKNOWN
+            0x1EE54,  // 1EE54       ; ARABIC
+            0x1EE55,  // 1EE55..1EE56; UNKNOWN
+            0x1EE57,  // 1EE57       ; ARABIC
+            0x1EE58,  // 1EE58       ; UNKNOWN
+            0x1EE59,  // 1EE59       ; ARABIC
+            0x1EE5A,  // 1EE5A       ; UNKNOWN
+            0x1EE5B,  // 1EE5B       ; ARABIC
+            0x1EE5C,  // 1EE5C       ; UNKNOWN
+            0x1EE5D,  // 1EE5D       ; ARABIC
+            0x1EE5E,  // 1EE5E       ; UNKNOWN
+            0x1EE5F,  // 1EE5F       ; ARABIC
+            0x1EE60,  // 1EE60       ; UNKNOWN
+            0x1EE61,  // 1EE61..1EE62; ARABIC
+            0x1EE63,  // 1EE63       ; UNKNOWN
+            0x1EE64,  // 1EE64       ; ARABIC
+            0x1EE65,  // 1EE65..1EE66; UNKNOWN
+            0x1EE67,  // 1EE67..1EE6A; ARABIC
+            0x1EE6B,  // 1EE6B       ; UNKNOWN
+            0x1EE6C,  // 1EE6C..1EE72; ARABIC
+            0x1EE73,  // 1EE73       ; UNKNOWN
+            0x1EE74,  // 1EE74..1EE77; ARABIC
+            0x1EE78,  // 1EE78       ; UNKNOWN
+            0x1EE79,  // 1EE79..1EE7C; ARABIC
+            0x1EE7D,  // 1EE7D       ; UNKNOWN
+            0x1EE7E,  // 1EE7E       ; ARABIC
+            0x1EE7F,  // 1EE7F       ; UNKNOWN
+            0x1EE80,  // 1EE80..1EE89; ARABIC
+            0x1EE8A,  // 1EE8A       ; UNKNOWN
+            0x1EE8B,  // 1EE8B..1EE9B; ARABIC
+            0x1EE9C,  // 1EE9C..1EEA0; UNKNOWN
+            0x1EEA1,  // 1EEA1..1EEA3; ARABIC
+            0x1EEA4,  // 1EEA4       ; UNKNOWN
+            0x1EEA5,  // 1EEA5..1EEA9; ARABIC
+            0x1EEAA,  // 1EEAA       ; UNKNOWN
+            0x1EEAB,  // 1EEAB..1EEBB; ARABIC
+            0x1EEBC,  // 1EEBC..1EEEF; UNKNOWN
+            0x1EEF0,  // 1EEF0..1EEF1; ARABIC
+            0x1EEF2,  // 1EEF2..1EFFF; UNKNOWN
+            0x1F000,  // 1F000..1F02B; COMMON
+            0x1F02C,  // 1F02C..1F02F; UNKNOWN
+            0x1F030,  // 1F030..1F093; COMMON
+            0x1F094,  // 1F094..1F09F; UNKNOWN
+            0x1F0A0,  // 1F0A0..1F0AE; COMMON
+            0x1F0AF,  // 1F0AF..1F0B0; UNKNOWN
+            0x1F0B1,  // 1F0B1..1F0BF; COMMON
+            0x1F0C0,  // 1F0C0       ; UNKNOWN
+            0x1F0C1,  // 1F0C1..1F0CF; COMMON
+            0x1F0D0,  // 1F0D0       ; UNKNOWN
+            0x1F0D1,  // 1F0D1..1F0F5; COMMON
+            0x1F0F6,  // 1F0F6..1F0FF; UNKNOWN
+            0x1F100,  // 1F100..1F10C; COMMON
+            0x1F10D,  // 1F10D..1F10F; UNKNOWN
+            0x1F110,  // 1F110..1F12E; COMMON
+            0x1F12F,  // 1F12F       ; UNKNOWN
+            0x1F130,  // 1F130..1F16B; COMMON
+            0x1F16C,  // 1F16C..1F16F; UNKNOWN
+            0x1F170,  // 1F170..1F19A; COMMON
+            0x1F19B,  // 1F19B..1F1E5; UNKNOWN
+            0x1F1E6,  // 1F1E6..1F1FF; COMMON
+            0x1F200,  // 1F200       ; HIRAGANA
+            0x1F201,  // 1F201..1F202; COMMON
+            0x1F203,  // 1F203..1F20F; UNKNOWN
+            0x1F210,  // 1F210..1F23A; COMMON
+            0x1F23B,  // 1F23B..1F23F; UNKNOWN
+            0x1F240,  // 1F240..1F248; COMMON
+            0x1F249,  // 1F249..1F24F; UNKNOWN
+            0x1F250,  // 1F250..1F251; COMMON
+            0x1F252,  // 1F252..1F2FF; UNKNOWN
+            0x1F300,  // 1F300..1F32C; COMMON
+            0x1F32D,  // 1F32D..1F32F; UNKNOWN
+            0x1F330,  // 1F330..1F37D; COMMON
+            0x1F37E,  // 1F37E..1F37F; UNKNOWN
+            0x1F380,  // 1F380..1F3CE; COMMON
+            0x1F3CF,  // 1F3CF..1F3D3; UNKNOWN
+            0x1F3D4,  // 1F3D4..1F3F7; COMMON
+            0x1F3F8,  // 1F3F8..1F3FF; UNKNOWN
+            0x1F400,  // 1F400..1F4FE; COMMON
+            0x1F4FF,  // 1F4FF       ; UNKNOWN
+            0x1F500,  // 1F500..1F54A; COMMON
+            0x1F54B,  // 1F54B..1F54F; UNKNOWN
+            0x1F550,  // 1F550..1F579; COMMON
+            0x1F57A,  // 1F57A       ; UNKNOWN
+            0x1F57B,  // 1F57B..1F5A3; COMMON
+            0x1F5A4,  // 1F5A4       ; UNKNOWN
+            0x1F5A5,  // 1F5A5..1F642; COMMON
+            0x1F643,  // 1F643..1F644; UNKNOWN
+            0x1F645,  // 1F645..1F6CF; COMMON
+            0x1F6D0,  // 1F6D0..1F6DF; UNKNOWN
+            0x1F6E0,  // 1F6E0..1F6EC; COMMON
+            0x1F6ED,  // 1F6ED..1F6EF; UNKNOWN
+            0x1F6F0,  // 1F6F0..1F6F3; COMMON
+            0x1F6F4,  // 1F6F4..1F6FF; UNKNOWN
+            0x1F700,  // 1F700..1F773; COMMON
+            0x1F774,  // 1F774..1F77F; UNKNOWN
+            0x1F780,  // 1F780..1F7D4; COMMON
+            0x1F7D5,  // 1F7D5..1F7FF; UNKNOWN
+            0x1F800,  // 1F800..1F80B; COMMON
+            0x1F80C,  // 1F80C..1F80F; UNKNOWN
+            0x1F810,  // 1F810..1F847; COMMON
+            0x1F848,  // 1F848..1F84F; UNKNOWN
+            0x1F850,  // 1F850..1F859; COMMON
+            0x1F85A,  // 1F85A..1F85F; UNKNOWN
+            0x1F860,  // 1F860..1F887; COMMON
+            0x1F888,  // 1F888..1F88F; UNKNOWN
+            0x1F890,  // 1F890..1F8AD; COMMON
+            0x1F8AE,  // 1F8AE..1FFFF; UNKNOWN
+            0x20000,  // 20000..2A6D6; HAN
+            0x2A6D7,  // 2A6D7..2A6FF; UNKNOWN
+            0x2A700,  // 2A700..2B734; HAN
+            0x2B735,  // 2B735..2B73F; UNKNOWN
+            0x2B740,  // 2B740..2B81D; HAN
+            0x2B81E,  // 2B81E..2F7FF; UNKNOWN
+            0x2F800,  // 2F800..2FA1D; HAN
+            0x2FA1E,  // 2FA1E..E0000; UNKNOWN
+            0xE0001,  // E0001       ; COMMON
+            0xE0002,  // E0002..E001F; UNKNOWN
+            0xE0020,  // E0020..E007F; COMMON
+            0xE0080,  // E0080..E00FF; UNKNOWN
             0xE0100,  // E0100..E01EF; INHERITED
             0xE01F0   // E01F0..10FFFF; UNKNOWN
-
         };
 
         private static final UnicodeScript[] scripts = {
-            COMMON,
-            LATIN,
-            COMMON,
-            LATIN,
-            COMMON,
-            LATIN,
-            COMMON,
-            LATIN,
-            COMMON,
-            LATIN,
-            COMMON,
-            LATIN,
-            COMMON,
-            LATIN,
-            COMMON,
-            LATIN,
-            COMMON,
-            BOPOMOFO,
-            COMMON,
-            INHERITED,
-            GREEK,
-            COMMON,
-            GREEK,
-            COMMON,
-            GREEK,
-            COMMON,
-            GREEK,
-            COMMON,
-            GREEK,
-            COPTIC,
-            GREEK,
-            CYRILLIC,
-            INHERITED,
-            CYRILLIC,
-            ARMENIAN,
-            COMMON,
-            ARMENIAN,
-            HEBREW,
-            ARABIC,
-            COMMON,
-            ARABIC,
-            COMMON,
-            ARABIC,
-            COMMON,
-            ARABIC,
-            COMMON,
-            ARABIC,
-            INHERITED,
-            ARABIC,
-            COMMON,
-            ARABIC,
-            INHERITED,
-            ARABIC,
-            COMMON,
-            ARABIC,
-            SYRIAC,
-            ARABIC,
-            THAANA,
-            NKO,
-            SAMARITAN,
-            MANDAIC,
-            ARABIC,
-            DEVANAGARI,
-            INHERITED,
-            DEVANAGARI,
-            COMMON,
-            DEVANAGARI,
-            BENGALI,
-            GURMUKHI,
-            GUJARATI,
-            ORIYA,
-            TAMIL,
-            TELUGU,
-            KANNADA,
-            MALAYALAM,
-            SINHALA,
-            THAI,
-            COMMON,
-            THAI,
-            LAO,
-            TIBETAN,
-            COMMON,
-            TIBETAN,
-            MYANMAR,
-            GEORGIAN,
-            COMMON,
-            GEORGIAN,
-            HANGUL,
-            ETHIOPIC,
-            CHEROKEE,
-            CANADIAN_ABORIGINAL,
-            OGHAM,
-            RUNIC,
-            COMMON,
-            RUNIC,
-            TAGALOG,
-            HANUNOO,
-            COMMON,
-            BUHID,
-            TAGBANWA,
-            KHMER,
-            MONGOLIAN,
-            COMMON,
-            MONGOLIAN,
-            COMMON,
-            MONGOLIAN,
-            CANADIAN_ABORIGINAL,
-            LIMBU,
-            TAI_LE,
-            NEW_TAI_LUE,
-            KHMER,
-            BUGINESE,
-            TAI_THAM,
-            BALINESE,
-            SUNDANESE,
-            BATAK,
-            LEPCHA,
-            OL_CHIKI,
-            SUNDANESE,
-            INHERITED,
-            COMMON,
-            INHERITED,
-            COMMON,
-            INHERITED,
-            COMMON,
-            INHERITED,
-            COMMON,
-            INHERITED,
-            COMMON,
-            LATIN,
-            GREEK,
-            CYRILLIC,
-            LATIN,
-            GREEK,
-            LATIN,
-            GREEK,
-            LATIN,
-            CYRILLIC,
-            LATIN,
-            GREEK,
-            INHERITED,
-            LATIN,
-            GREEK,
-            COMMON,
-            INHERITED,
-            COMMON,
-            LATIN,
-            COMMON,
-            LATIN,
-            COMMON,
-            LATIN,
-            COMMON,
-            INHERITED,
-            COMMON,
-            GREEK,
-            COMMON,
-            LATIN,
-            COMMON,
-            LATIN,
-            COMMON,
-            LATIN,
-            COMMON,
-            LATIN,
-            COMMON,
-            BRAILLE,
-            COMMON,
-            GLAGOLITIC,
-            LATIN,
-            COPTIC,
-            GEORGIAN,
-            TIFINAGH,
-            ETHIOPIC,
-            CYRILLIC,
-            COMMON,
-            HAN,
-            COMMON,
-            HAN,
-            COMMON,
-            HAN,
-            COMMON,
-            HAN,
-            INHERITED,
-            HANGUL,
-            COMMON,
-            HAN,
-            COMMON,
-            HIRAGANA,
-            INHERITED,
-            COMMON,
-            HIRAGANA,
-            COMMON,
-            KATAKANA,
-            COMMON,
-            KATAKANA,
-            BOPOMOFO,
-            HANGUL,
-            COMMON,
-            BOPOMOFO,
-            COMMON,
-            KATAKANA,
-            HANGUL,
-            COMMON,
-            HANGUL,
-            COMMON,
-            KATAKANA,
-            COMMON,
-            HAN,
-            COMMON,
-            HAN,
-            YI,
-            LISU,
-            VAI,
-            CYRILLIC,
-            BAMUM,
-            COMMON,
-            LATIN,
-            COMMON,
-            LATIN,
-            SYLOTI_NAGRI,
-            COMMON,
-            PHAGS_PA,
-            SAURASHTRA,
-            DEVANAGARI,
-            KAYAH_LI,
-            REJANG,
-            HANGUL,
-            JAVANESE,
-            CHAM,
-            MYANMAR,
-            TAI_VIET,
-            MEETEI_MAYEK,
-            ETHIOPIC,
-            MEETEI_MAYEK,
-            HANGUL,
-            UNKNOWN     ,
-            HAN,
-            LATIN,
-            ARMENIAN,
-            HEBREW,
-            ARABIC,
-            COMMON,
-            ARABIC,
-            COMMON,
-            INHERITED,
-            COMMON,
-            INHERITED,
-            COMMON,
-            ARABIC,
-            COMMON,
-            LATIN,
-            COMMON,
-            LATIN,
-            COMMON,
-            KATAKANA,
-            COMMON,
-            KATAKANA,
-            COMMON,
-            HANGUL,
-            COMMON,
-            LINEAR_B,
-            COMMON,
-            GREEK,
-            COMMON,
-            INHERITED,
-            LYCIAN,
-            CARIAN,
-            OLD_ITALIC,
-            GOTHIC,
-            UGARITIC,
-            OLD_PERSIAN,
-            DESERET,
-            SHAVIAN,
-            OSMANYA,
-            CYPRIOT,
-            IMPERIAL_ARAMAIC,
-            PHOENICIAN,
-            LYDIAN,
-            MEROITIC_HIEROGLYPHS,
-            MEROITIC_CURSIVE,
-            KHAROSHTHI,
-            OLD_SOUTH_ARABIAN,
-            AVESTAN,
-            INSCRIPTIONAL_PARTHIAN,
-            INSCRIPTIONAL_PAHLAVI,
-            OLD_TURKIC,
-            ARABIC,
-            BRAHMI,
-            KAITHI,
-            SORA_SOMPENG,
-            CHAKMA,
-            SHARADA,
-            TAKRI,
-            CUNEIFORM,
-            EGYPTIAN_HIEROGLYPHS,
-            BAMUM,
-            MIAO,
-            KATAKANA,
-            HIRAGANA,
-            COMMON,
-            INHERITED,
-            COMMON,
-            INHERITED,
-            COMMON,
-            INHERITED,
-            COMMON,
-            INHERITED,
-            COMMON,
-            GREEK,
-            COMMON,
-            ARABIC,
-            COMMON,
-            HIRAGANA,
-            COMMON,
-            HAN,
-            COMMON,
-            INHERITED,
-            UNKNOWN
+            COMMON,                   // 0000..0040
+            LATIN,                    // 0041..005A
+            COMMON,                   // 005B..0060
+            LATIN,                    // 0061..007A
+            COMMON,                   // 007B..00A9
+            LATIN,                    // 00AA
+            COMMON,                   // 00AB..00B9
+            LATIN,                    // 00BA
+            COMMON,                   // 00BB..00BF
+            LATIN,                    // 00C0..00D6
+            COMMON,                   // 00D7
+            LATIN,                    // 00D8..00F6
+            COMMON,                   // 00F7
+            LATIN,                    // 00F8..02B8
+            COMMON,                   // 02B9..02DF
+            LATIN,                    // 02E0..02E4
+            COMMON,                   // 02E5..02E9
+            BOPOMOFO,                 // 02EA..02EB
+            COMMON,                   // 02EC..02FF
+            INHERITED,                // 0300..036F
+            GREEK,                    // 0370..0373
+            COMMON,                   // 0374
+            GREEK,                    // 0375..0377
+            UNKNOWN,                  // 0378..0379
+            GREEK,                    // 037A..037D
+            COMMON,                   // 037E
+            GREEK,                    // 037F
+            UNKNOWN,                  // 0380..0383
+            GREEK,                    // 0384
+            COMMON,                   // 0385
+            GREEK,                    // 0386
+            COMMON,                   // 0387
+            GREEK,                    // 0388..038A
+            UNKNOWN,                  // 038B
+            GREEK,                    // 038C
+            UNKNOWN,                  // 038D
+            GREEK,                    // 038E..03A1
+            UNKNOWN,                  // 03A2
+            GREEK,                    // 03A3..03E1
+            COPTIC,                   // 03E2..03EF
+            GREEK,                    // 03F0..03FF
+            CYRILLIC,                 // 0400..0484
+            INHERITED,                // 0485..0486
+            CYRILLIC,                 // 0487..052F
+            UNKNOWN,                  // 0530
+            ARMENIAN,                 // 0531..0556
+            UNKNOWN,                  // 0557..0558
+            ARMENIAN,                 // 0559..055F
+            UNKNOWN,                  // 0560
+            ARMENIAN,                 // 0561..0587
+            UNKNOWN,                  // 0588
+            COMMON,                   // 0589
+            ARMENIAN,                 // 058A
+            UNKNOWN,                  // 058B..058C
+            ARMENIAN,                 // 058D..058F
+            UNKNOWN,                  // 0590
+            HEBREW,                   // 0591..05C7
+            UNKNOWN,                  // 05C8..05CF
+            HEBREW,                   // 05D0..05EA
+            UNKNOWN,                  // 05EB..05EF
+            HEBREW,                   // 05F0..05F4
+            UNKNOWN,                  // 05F5..05FF
+            ARABIC,                   // 0600..0604
+            COMMON,                   // 0605
+            ARABIC,                   // 0606..060B
+            COMMON,                   // 060C
+            ARABIC,                   // 060D..061A
+            COMMON,                   // 061B..061C
+            UNKNOWN,                  // 061D
+            ARABIC,                   // 061E
+            COMMON,                   // 061F
+            ARABIC,                   // 0620..063F
+            COMMON,                   // 0640
+            ARABIC,                   // 0641..064A
+            INHERITED,                // 064B..0655
+            ARABIC,                   // 0656..065F
+            COMMON,                   // 0660..0669
+            ARABIC,                   // 066A..066F
+            INHERITED,                // 0670
+            ARABIC,                   // 0671..06DC
+            COMMON,                   // 06DD
+            ARABIC,                   // 06DE..06FF
+            SYRIAC,                   // 0700..070D
+            UNKNOWN,                  // 070E
+            SYRIAC,                   // 070F..074A
+            UNKNOWN,                  // 074B..074C
+            SYRIAC,                   // 074D..074F
+            ARABIC,                   // 0750..077F
+            THAANA,                   // 0780..07B1
+            UNKNOWN,                  // 07B2..07BF
+            NKO,                      // 07C0..07FA
+            UNKNOWN,                  // 07FB..07FF
+            SAMARITAN,                // 0800..082D
+            UNKNOWN,                  // 082E..082F
+            SAMARITAN,                // 0830..083E
+            UNKNOWN,                  // 083F
+            MANDAIC,                  // 0840..085B
+            UNKNOWN,                  // 085C..085D
+            MANDAIC,                  // 085E
+            UNKNOWN,                  // 085F..089F
+            ARABIC,                   // 08A0..08B2
+            UNKNOWN,                  // 08B3..08E3
+            ARABIC,                   // 08E4..08FF
+            DEVANAGARI,               // 0900..0950
+            INHERITED,                // 0951..0952
+            DEVANAGARI,               // 0953..0963
+            COMMON,                   // 0964..0965
+            DEVANAGARI,               // 0966..097F
+            BENGALI,                  // 0980..0983
+            UNKNOWN,                  // 0984
+            BENGALI,                  // 0985..098C
+            UNKNOWN,                  // 098D..098E
+            BENGALI,                  // 098F..0990
+            UNKNOWN,                  // 0991..0992
+            BENGALI,                  // 0993..09A8
+            UNKNOWN,                  // 09A9
+            BENGALI,                  // 09AA..09B0
+            UNKNOWN,                  // 09B1
+            BENGALI,                  // 09B2
+            UNKNOWN,                  // 09B3..09B5
+            BENGALI,                  // 09B6..09B9
+            UNKNOWN,                  // 09BA..09BB
+            BENGALI,                  // 09BC..09C4
+            UNKNOWN,                  // 09C5..09C6
+            BENGALI,                  // 09C7..09C8
+            UNKNOWN,                  // 09C9..09CA
+            BENGALI,                  // 09CB..09CE
+            UNKNOWN,                  // 09CF..09D6
+            BENGALI,                  // 09D7
+            UNKNOWN,                  // 09D8..09DB
+            BENGALI,                  // 09DC..09DD
+            UNKNOWN,                  // 09DE
+            BENGALI,                  // 09DF..09E3
+            UNKNOWN,                  // 09E4..09E5
+            BENGALI,                  // 09E6..09FB
+            UNKNOWN,                  // 09FC..0A00
+            GURMUKHI,                 // 0A01..0A03
+            UNKNOWN,                  // 0A04
+            GURMUKHI,                 // 0A05..0A0A
+            UNKNOWN,                  // 0A0B..0A0E
+            GURMUKHI,                 // 0A0F..0A10
+            UNKNOWN,                  // 0A11..0A12
+            GURMUKHI,                 // 0A13..0A28
+            UNKNOWN,                  // 0A29
+            GURMUKHI,                 // 0A2A..0A30
+            UNKNOWN,                  // 0A31
+            GURMUKHI,                 // 0A32..0A33
+            UNKNOWN,                  // 0A34
+            GURMUKHI,                 // 0A35..0A36
+            UNKNOWN,                  // 0A37
+            GURMUKHI,                 // 0A38..0A39
+            UNKNOWN,                  // 0A3A..0A3B
+            GURMUKHI,                 // 0A3C
+            UNKNOWN,                  // 0A3D
+            GURMUKHI,                 // 0A3E..0A42
+            UNKNOWN,                  // 0A43..0A46
+            GURMUKHI,                 // 0A47..0A48
+            UNKNOWN,                  // 0A49..0A4A
+            GURMUKHI,                 // 0A4B..0A4D
+            UNKNOWN,                  // 0A4E..0A50
+            GURMUKHI,                 // 0A51
+            UNKNOWN,                  // 0A52..0A58
+            GURMUKHI,                 // 0A59..0A5C
+            UNKNOWN,                  // 0A5D
+            GURMUKHI,                 // 0A5E
+            UNKNOWN,                  // 0A5F..0A65
+            GURMUKHI,                 // 0A66..0A75
+            UNKNOWN,                  // 0A76..0A80
+            GUJARATI,                 // 0A81..0A83
+            UNKNOWN,                  // 0A84
+            GUJARATI,                 // 0A85..0A8D
+            UNKNOWN,                  // 0A8E
+            GUJARATI,                 // 0A8F..0A91
+            UNKNOWN,                  // 0A92
+            GUJARATI,                 // 0A93..0AA8
+            UNKNOWN,                  // 0AA9
+            GUJARATI,                 // 0AAA..0AB0
+            UNKNOWN,                  // 0AB1
+            GUJARATI,                 // 0AB2..0AB3
+            UNKNOWN,                  // 0AB4
+            GUJARATI,                 // 0AB5..0AB9
+            UNKNOWN,                  // 0ABA..0ABB
+            GUJARATI,                 // 0ABC..0AC5
+            UNKNOWN,                  // 0AC6
+            GUJARATI,                 // 0AC7..0AC9
+            UNKNOWN,                  // 0ACA
+            GUJARATI,                 // 0ACB..0ACD
+            UNKNOWN,                  // 0ACE..0ACF
+            GUJARATI,                 // 0AD0
+            UNKNOWN,                  // 0AD1..0ADF
+            GUJARATI,                 // 0AE0..0AE3
+            UNKNOWN,                  // 0AE4..0AE5
+            GUJARATI,                 // 0AE6..0AF1
+            UNKNOWN,                  // 0AF2..0B00
+            ORIYA,                    // 0B01..0B03
+            UNKNOWN,                  // 0B04
+            ORIYA,                    // 0B05..0B0C
+            UNKNOWN,                  // 0B0D..0B0E
+            ORIYA,                    // 0B0F..0B10
+            UNKNOWN,                  // 0B11..0B12
+            ORIYA,                    // 0B13..0B28
+            UNKNOWN,                  // 0B29
+            ORIYA,                    // 0B2A..0B30
+            UNKNOWN,                  // 0B31
+            ORIYA,                    // 0B32..0B33
+            UNKNOWN,                  // 0B34
+            ORIYA,                    // 0B35..0B39
+            UNKNOWN,                  // 0B3A..0B3B
+            ORIYA,                    // 0B3C..0B44
+            UNKNOWN,                  // 0B45..0B46
+            ORIYA,                    // 0B47..0B48
+            UNKNOWN,                  // 0B49..0B4A
+            ORIYA,                    // 0B4B..0B4D
+            UNKNOWN,                  // 0B4E..0B55
+            ORIYA,                    // 0B56..0B57
+            UNKNOWN,                  // 0B58..0B5B
+            ORIYA,                    // 0B5C..0B5D
+            UNKNOWN,                  // 0B5E
+            ORIYA,                    // 0B5F..0B63
+            UNKNOWN,                  // 0B64..0B65
+            ORIYA,                    // 0B66..0B77
+            UNKNOWN,                  // 0B78..0B81
+            TAMIL,                    // 0B82..0B83
+            UNKNOWN,                  // 0B84
+            TAMIL,                    // 0B85..0B8A
+            UNKNOWN,                  // 0B8B..0B8D
+            TAMIL,                    // 0B8E..0B90
+            UNKNOWN,                  // 0B91
+            TAMIL,                    // 0B92..0B95
+            UNKNOWN,                  // 0B96..0B98
+            TAMIL,                    // 0B99..0B9A
+            UNKNOWN,                  // 0B9B
+            TAMIL,                    // 0B9C
+            UNKNOWN,                  // 0B9D
+            TAMIL,                    // 0B9E..0B9F
+            UNKNOWN,                  // 0BA0..0BA2
+            TAMIL,                    // 0BA3..0BA4
+            UNKNOWN,                  // 0BA5..0BA7
+            TAMIL,                    // 0BA8..0BAA
+            UNKNOWN,                  // 0BAB..0BAD
+            TAMIL,                    // 0BAE..0BB9
+            UNKNOWN,                  // 0BBA..0BBD
+            TAMIL,                    // 0BBE..0BC2
+            UNKNOWN,                  // 0BC3..0BC5
+            TAMIL,                    // 0BC6..0BC8
+            UNKNOWN,                  // 0BC9
+            TAMIL,                    // 0BCA..0BCD
+            UNKNOWN,                  // 0BCE..0BCF
+            TAMIL,                    // 0BD0
+            UNKNOWN,                  // 0BD1..0BD6
+            TAMIL,                    // 0BD7
+            UNKNOWN,                  // 0BD8..0BE5
+            TAMIL,                    // 0BE6..0BFA
+            UNKNOWN,                  // 0BFB..0BFF
+            TELUGU,                   // 0C00..0C03
+            UNKNOWN,                  // 0C04
+            TELUGU,                   // 0C05..0C0C
+            UNKNOWN,                  // 0C0D
+            TELUGU,                   // 0C0E..0C10
+            UNKNOWN,                  // 0C11
+            TELUGU,                   // 0C12..0C28
+            UNKNOWN,                  // 0C29
+            TELUGU,                   // 0C2A..0C39
+            UNKNOWN,                  // 0C3A..0C3C
+            TELUGU,                   // 0C3D..0C44
+            UNKNOWN,                  // 0C45
+            TELUGU,                   // 0C46..0C48
+            UNKNOWN,                  // 0C49
+            TELUGU,                   // 0C4A..0C4D
+            UNKNOWN,                  // 0C4E..0C54
+            TELUGU,                   // 0C55..0C56
+            UNKNOWN,                  // 0C57
+            TELUGU,                   // 0C58..0C59
+            UNKNOWN,                  // 0C5A..0C5F
+            TELUGU,                   // 0C60..0C63
+            UNKNOWN,                  // 0C64..0C65
+            TELUGU,                   // 0C66..0C6F
+            UNKNOWN,                  // 0C70..0C77
+            TELUGU,                   // 0C78..0C7F
+            UNKNOWN,                  // 0C80
+            KANNADA,                  // 0C81..0C83
+            UNKNOWN,                  // 0C84
+            KANNADA,                  // 0C85..0C8C
+            UNKNOWN,                  // 0C8D
+            KANNADA,                  // 0C8E..0C90
+            UNKNOWN,                  // 0C91
+            KANNADA,                  // 0C92..0CA8
+            UNKNOWN,                  // 0CA9
+            KANNADA,                  // 0CAA..0CB3
+            UNKNOWN,                  // 0CB4
+            KANNADA,                  // 0CB5..0CB9
+            UNKNOWN,                  // 0CBA..0CBB
+            KANNADA,                  // 0CBC..0CC4
+            UNKNOWN,                  // 0CC5
+            KANNADA,                  // 0CC6..0CC8
+            UNKNOWN,                  // 0CC9
+            KANNADA,                  // 0CCA..0CCD
+            UNKNOWN,                  // 0CCE..0CD4
+            KANNADA,                  // 0CD5..0CD6
+            UNKNOWN,                  // 0CD7..0CDD
+            KANNADA,                  // 0CDE
+            UNKNOWN,                  // 0CDF
+            KANNADA,                  // 0CE0..0CE3
+            UNKNOWN,                  // 0CE4..0CE5
+            KANNADA,                  // 0CE6..0CEF
+            UNKNOWN,                  // 0CF0
+            KANNADA,                  // 0CF1..0CF2
+            UNKNOWN,                  // 0CF3..0D00
+            MALAYALAM,                // 0D01..0D03
+            UNKNOWN,                  // 0D04
+            MALAYALAM,                // 0D05..0D0C
+            UNKNOWN,                  // 0D0D
+            MALAYALAM,                // 0D0E..0D10
+            UNKNOWN,                  // 0D11
+            MALAYALAM,                // 0D12..0D3A
+            UNKNOWN,                  // 0D3B..0D3C
+            MALAYALAM,                // 0D3D..0D44
+            UNKNOWN,                  // 0D45
+            MALAYALAM,                // 0D46..0D48
+            UNKNOWN,                  // 0D49
+            MALAYALAM,                // 0D4A..0D4E
+            UNKNOWN,                  // 0D4F..0D56
+            MALAYALAM,                // 0D57
+            UNKNOWN,                  // 0D58..0D5F
+            MALAYALAM,                // 0D60..0D63
+            UNKNOWN,                  // 0D64..0D65
+            MALAYALAM,                // 0D66..0D75
+            UNKNOWN,                  // 0D76..0D78
+            MALAYALAM,                // 0D79..0D7F
+            UNKNOWN,                  // 0D80..0D81
+            SINHALA,                  // 0D82..0D83
+            UNKNOWN,                  // 0D84
+            SINHALA,                  // 0D85..0D96
+            UNKNOWN,                  // 0D97..0D99
+            SINHALA,                  // 0D9A..0DB1
+            UNKNOWN,                  // 0DB2
+            SINHALA,                  // 0DB3..0DBB
+            UNKNOWN,                  // 0DBC
+            SINHALA,                  // 0DBD
+            UNKNOWN,                  // 0DBE..0DBF
+            SINHALA,                  // 0DC0..0DC6
+            UNKNOWN,                  // 0DC7..0DC9
+            SINHALA,                  // 0DCA
+            UNKNOWN,                  // 0DCB..0DCE
+            SINHALA,                  // 0DCF..0DD4
+            UNKNOWN,                  // 0DD5
+            SINHALA,                  // 0DD6
+            UNKNOWN,                  // 0DD7
+            SINHALA,                  // 0DD8..0DDF
+            UNKNOWN,                  // 0DE0..0DE5
+            SINHALA,                  // 0DE6..0DEF
+            UNKNOWN,                  // 0DF0..0DF1
+            SINHALA,                  // 0DF2..0DF4
+            UNKNOWN,                  // 0DF5..0E00
+            THAI,                     // 0E01..0E3A
+            UNKNOWN,                  // 0E3B..0E3E
+            COMMON,                   // 0E3F
+            THAI,                     // 0E40..0E5B
+            UNKNOWN,                  // 0E5C..0E80
+            LAO,                      // 0E81..0E82
+            UNKNOWN,                  // 0E83
+            LAO,                      // 0E84
+            UNKNOWN,                  // 0E85..0E86
+            LAO,                      // 0E87..0E88
+            UNKNOWN,                  // 0E89
+            LAO,                      // 0E8A
+            UNKNOWN,                  // 0E8B..0E8C
+            LAO,                      // 0E8D
+            UNKNOWN,                  // 0E8E..0E93
+            LAO,                      // 0E94..0E97
+            UNKNOWN,                  // 0E98
+            LAO,                      // 0E99..0E9F
+            UNKNOWN,                  // 0EA0
+            LAO,                      // 0EA1..0EA3
+            UNKNOWN,                  // 0EA4
+            LAO,                      // 0EA5
+            UNKNOWN,                  // 0EA6
+            LAO,                      // 0EA7
+            UNKNOWN,                  // 0EA8..0EA9
+            LAO,                      // 0EAA..0EAB
+            UNKNOWN,                  // 0EAC
+            LAO,                      // 0EAD..0EB9
+            UNKNOWN,                  // 0EBA
+            LAO,                      // 0EBB..0EBD
+            UNKNOWN,                  // 0EBE..0EBF
+            LAO,                      // 0EC0..0EC4
+            UNKNOWN,                  // 0EC5
+            LAO,                      // 0EC6
+            UNKNOWN,                  // 0EC7
+            LAO,                      // 0EC8..0ECD
+            UNKNOWN,                  // 0ECE..0ECF
+            LAO,                      // 0ED0..0ED9
+            UNKNOWN,                  // 0EDA..0EDB
+            LAO,                      // 0EDC..0EDF
+            UNKNOWN,                  // 0EE0..0EFF
+            TIBETAN,                  // 0F00..0F47
+            UNKNOWN,                  // 0F48
+            TIBETAN,                  // 0F49..0F6C
+            UNKNOWN,                  // 0F6D..0F70
+            TIBETAN,                  // 0F71..0F97
+            UNKNOWN,                  // 0F98
+            TIBETAN,                  // 0F99..0FBC
+            UNKNOWN,                  // 0FBD
+            TIBETAN,                  // 0FBE..0FCC
+            UNKNOWN,                  // 0FCD
+            TIBETAN,                  // 0FCE..0FD4
+            COMMON,                   // 0FD5..0FD8
+            TIBETAN,                  // 0FD9..0FDA
+            UNKNOWN,                  // 0FDB..FFF
+            MYANMAR,                  // 1000..109F
+            GEORGIAN,                 // 10A0..10C5
+            UNKNOWN,                  // 10C6
+            GEORGIAN,                 // 10C7
+            UNKNOWN,                  // 10C8..10CC
+            GEORGIAN,                 // 10CD
+            UNKNOWN,                  // 10CE..10CF
+            GEORGIAN,                 // 10D0..10FA
+            COMMON,                   // 10FB
+            GEORGIAN,                 // 10FC..10FF
+            HANGUL,                   // 1100..11FF
+            ETHIOPIC,                 // 1200..1248
+            UNKNOWN,                  // 1249
+            ETHIOPIC,                 // 124A..124D
+            UNKNOWN,                  // 124E..124F
+            ETHIOPIC,                 // 1250..1256
+            UNKNOWN,                  // 1257
+            ETHIOPIC,                 // 1258
+            UNKNOWN,                  // 1259
+            ETHIOPIC,                 // 125A..125D
+            UNKNOWN,                  // 125E..125F
+            ETHIOPIC,                 // 1260..1288
+            UNKNOWN,                  // 1289
+            ETHIOPIC,                 // 128A..128D
+            UNKNOWN,                  // 128E..128F
+            ETHIOPIC,                 // 1290..12B0
+            UNKNOWN,                  // 12B1
+            ETHIOPIC,                 // 12B2..12B5
+            UNKNOWN,                  // 12B6..12B7
+            ETHIOPIC,                 // 12B8..12BE
+            UNKNOWN,                  // 12BF
+            ETHIOPIC,                 // 12C0
+            UNKNOWN,                  // 12C1
+            ETHIOPIC,                 // 12C2..12C5
+            UNKNOWN,                  // 12C6..12C7
+            ETHIOPIC,                 // 12C8..12D6
+            UNKNOWN,                  // 12D7
+            ETHIOPIC,                 // 12D8..1310
+            UNKNOWN,                  // 1311
+            ETHIOPIC,                 // 1312..1315
+            UNKNOWN,                  // 1316..1317
+            ETHIOPIC,                 // 1318..135A
+            UNKNOWN,                  // 135B..135C
+            ETHIOPIC,                 // 135D..137C
+            UNKNOWN,                  // 137D..137F
+            ETHIOPIC,                 // 1380..1399
+            UNKNOWN,                  // 139A..139F
+            CHEROKEE,                 // 13A0..13F4
+            UNKNOWN,                  // 13F5..13FF
+            CANADIAN_ABORIGINAL,      // 1400..167F
+            OGHAM,                    // 1680..169C
+            UNKNOWN,                  // 169D..169F
+            RUNIC,                    // 16A0..16EA
+            COMMON,                   // 16EB..16ED
+            RUNIC,                    // 16EE..16F8
+            UNKNOWN,                  // 16F9..16FF
+            TAGALOG,                  // 1700..170C
+            UNKNOWN,                  // 170D
+            TAGALOG,                  // 170E..1714
+            UNKNOWN,                  // 1715..171F
+            HANUNOO,                  // 1720..1734
+            COMMON,                   // 1735..1736
+            UNKNOWN,                  // 1737..173F
+            BUHID,                    // 1740..1753
+            UNKNOWN,                  // 1754..175F
+            TAGBANWA,                 // 1760..176C
+            UNKNOWN,                  // 176D
+            TAGBANWA,                 // 176E..1770
+            UNKNOWN,                  // 1771
+            TAGBANWA,                 // 1772..1773
+            UNKNOWN,                  // 1774..177F
+            KHMER,                    // 1780..17DD
+            UNKNOWN,                  // 17DE..17DF
+            KHMER,                    // 17E0..17E9
+            UNKNOWN,                  // 17EA..17EF
+            KHMER,                    // 17F0..17F9
+            UNKNOWN,                  // 17FA..17FF
+            MONGOLIAN,                // 1800..1801
+            COMMON,                   // 1802..1803
+            MONGOLIAN,                // 1804
+            COMMON,                   // 1805
+            MONGOLIAN,                // 1806..180E
+            UNKNOWN,                  // 180F
+            MONGOLIAN,                // 1810..1819
+            UNKNOWN,                  // 181A..181F
+            MONGOLIAN,                // 1820..1877
+            UNKNOWN,                  // 1878..187F
+            MONGOLIAN,                // 1880..18AA
+            UNKNOWN,                  // 18AB..18AF
+            CANADIAN_ABORIGINAL,      // 18B0..18F5
+            UNKNOWN,                  // 18F6..18FF
+            LIMBU,                    // 1900..191E
+            UNKNOWN,                  // 191F
+            LIMBU,                    // 1920..192B
+            UNKNOWN,                  // 192C..192F
+            LIMBU,                    // 1930..193B
+            UNKNOWN,                  // 193C..193F
+            LIMBU,                    // 1940
+            UNKNOWN,                  // 1941..1943
+            LIMBU,                    // 1944..194F
+            TAI_LE,                   // 1950..196D
+            UNKNOWN,                  // 196E..196F
+            TAI_LE,                   // 1970..1974
+            UNKNOWN,                  // 1975..197F
+            NEW_TAI_LUE,              // 1980..19AB
+            UNKNOWN,                  // 19AC..19AF
+            NEW_TAI_LUE,              // 19B0..19C9
+            UNKNOWN,                  // 19CA..19CF
+            NEW_TAI_LUE,              // 19D0..19DA
+            UNKNOWN,                  // 19DB..19DD
+            NEW_TAI_LUE,              // 19DE..19DF
+            KHMER,                    // 19E0..19FF
+            BUGINESE,                 // 1A00..1A1B
+            UNKNOWN,                  // 1A1C..1A1D
+            BUGINESE,                 // 1A1E..1A1F
+            TAI_THAM,                 // 1A20..1A5E
+            UNKNOWN,                  // 1A5F
+            TAI_THAM,                 // 1A60..1A7C
+            UNKNOWN,                  // 1A7D..1A7E
+            TAI_THAM,                 // 1A7F..1A89
+            UNKNOWN,                  // 1A8A..1A8F
+            TAI_THAM,                 // 1A90..1A99
+            UNKNOWN,                  // 1A9A..1A9F
+            TAI_THAM,                 // 1AA0..1AAD
+            UNKNOWN,                  // 1AAE..1AAF
+            INHERITED,                // 1AB0..1ABE
+            UNKNOWN,                  // 1ABF..1AFF
+            BALINESE,                 // 1B00..1B4B
+            UNKNOWN,                  // 1B4C..1B4F
+            BALINESE,                 // 1B50..1B7C
+            UNKNOWN,                  // 1B7D..1B7F
+            SUNDANESE,                // 1B80..1BBF
+            BATAK,                    // 1BC0..1BF3
+            UNKNOWN,                  // 1BF4..1BFB
+            BATAK,                    // 1BFC..1BFF
+            LEPCHA,                   // 1C00..1C37
+            UNKNOWN,                  // 1C38..1C3A
+            LEPCHA,                   // 1C3B..1C49
+            UNKNOWN,                  // 1C4A..1C4C
+            LEPCHA,                   // 1C4D..1C4F
+            OL_CHIKI,                 // 1C50..1C7F
+            UNKNOWN,                  // 1C80..1CBF
+            SUNDANESE,                // 1CC0..1CC7
+            UNKNOWN,                  // 1CC8..1CCF
+            INHERITED,                // 1CD0..1CD2
+            COMMON,                   // 1CD3
+            INHERITED,                // 1CD4..1CE0
+            COMMON,                   // 1CE1
+            INHERITED,                // 1CE2..1CE8
+            COMMON,                   // 1CE9..1CEC
+            INHERITED,                // 1CED
+            COMMON,                   // 1CEE..1CF3
+            INHERITED,                // 1CF4
+            COMMON,                   // 1CF5..1CF6
+            UNKNOWN,                  // 1CF7
+            INHERITED,                // 1CF8..1CF9
+            UNKNOWN,                  // 1CFA..1CFF
+            LATIN,                    // 1D00..1D25
+            GREEK,                    // 1D26..1D2A
+            CYRILLIC,                 // 1D2B
+            LATIN,                    // 1D2C..1D5C
+            GREEK,                    // 1D5D..1D61
+            LATIN,                    // 1D62..1D65
+            GREEK,                    // 1D66..1D6A
+            LATIN,                    // 1D6B..1D77
+            CYRILLIC,                 // 1D78
+            LATIN,                    // 1D79..1DBE
+            GREEK,                    // 1DBF
+            INHERITED,                // 1DC0..1DF5
+            UNKNOWN,                  // 1DF6..1DFB
+            INHERITED,                // 1DFC..1DFF
+            LATIN,                    // 1E00..1EFF
+            GREEK,                    // 1F00..1F15
+            UNKNOWN,                  // 1F16..1F17
+            GREEK,                    // 1F18..1F1D
+            UNKNOWN,                  // 1F1E..1F1F
+            GREEK,                    // 1F20..1F45
+            UNKNOWN,                  // 1F46..1F47
+            GREEK,                    // 1F48..1F4D
+            UNKNOWN,                  // 1F4E..1F4F
+            GREEK,                    // 1F50..1F57
+            UNKNOWN,                  // 1F58
+            GREEK,                    // 1F59
+            UNKNOWN,                  // 1F5A
+            GREEK,                    // 1F5B
+            UNKNOWN,                  // 1F5C
+            GREEK,                    // 1F5D
+            UNKNOWN,                  // 1F5E
+            GREEK,                    // 1F5F..1F7D
+            UNKNOWN,                  // 1F7E..1F7F
+            GREEK,                    // 1F80..1FB4
+            UNKNOWN,                  // 1FB5
+            GREEK,                    // 1FB6..1FC4
+            UNKNOWN,                  // 1FC5
+            GREEK,                    // 1FC6..1FD3
+            UNKNOWN,                  // 1FD4..1FD5
+            GREEK,                    // 1FD6..1FDB
+            UNKNOWN,                  // 1FDC
+            GREEK,                    // 1FDD..1FEF
+            UNKNOWN,                  // 1FF0..1FF1
+            GREEK,                    // 1FF2..1FF4
+            UNKNOWN,                  // 1FF5
+            GREEK,                    // 1FF6..1FFE
+            UNKNOWN,                  // 1FFF
+            COMMON,                   // 2000..200B
+            INHERITED,                // 200C..200D
+            COMMON,                   // 200E..2064
+            UNKNOWN,                  // 2065
+            COMMON,                   // 2066..2070
+            LATIN,                    // 2071
+            UNKNOWN,                  // 2072..2073
+            COMMON,                   // 2074..207E
+            LATIN,                    // 207F
+            COMMON,                   // 2080..208E
+            UNKNOWN,                  // 208F
+            LATIN,                    // 2090..209C
+            UNKNOWN,                  // 209D..209F
+            COMMON,                   // 20A0..20BD
+            UNKNOWN,                  // 20BE..20CF
+            INHERITED,                // 20D0..20F0
+            UNKNOWN,                  // 20F1..20FF
+            COMMON,                   // 2100..2125
+            GREEK,                    // 2126
+            COMMON,                   // 2127..2129
+            LATIN,                    // 212A..212B
+            COMMON,                   // 212C..2131
+            LATIN,                    // 2132
+            COMMON,                   // 2133..214D
+            LATIN,                    // 214E
+            COMMON,                   // 214F..215F
+            LATIN,                    // 2160..2188
+            COMMON,                   // 2189
+            UNKNOWN,                  // 218A..218F
+            COMMON,                   // 2190..23FA
+            UNKNOWN,                  // 23FB..23FF
+            COMMON,                   // 2400..2426
+            UNKNOWN,                  // 2427..243F
+            COMMON,                   // 2440..244A
+            UNKNOWN,                  // 244B..245F
+            COMMON,                   // 2460..27FF
+            BRAILLE,                  // 2800..28FF
+            COMMON,                   // 2900..2B73
+            UNKNOWN,                  // 2B74..2B75
+            COMMON,                   // 2B76..2B95
+            UNKNOWN,                  // 2B96..2B97
+            COMMON,                   // 2B98..2BB9
+            UNKNOWN,                  // 2BBA..2BBC
+            COMMON,                   // 2BBD..2BC8
+            UNKNOWN,                  // 2BC9
+            COMMON,                   // 2BCA..2BD1
+            UNKNOWN,                  // 2BD2..2BFF
+            GLAGOLITIC,               // 2C00..2C2E
+            UNKNOWN,                  // 2C2F
+            GLAGOLITIC,               // 2C30..2C5E
+            UNKNOWN,                  // 2C5F
+            LATIN,                    // 2C60..2C7F
+            COPTIC,                   // 2C80..2CF3
+            UNKNOWN,                  // 2CF4..2CF8
+            COPTIC,                   // 2CF9..2CFF
+            GEORGIAN,                 // 2D00..2D25
+            UNKNOWN,                  // 2D26
+            GEORGIAN,                 // 2D27
+            UNKNOWN,                  // 2D28..2D2C
+            GEORGIAN,                 // 2D2D
+            UNKNOWN,                  // 2D2E..2D2F
+            TIFINAGH,                 // 2D30..2D67
+            UNKNOWN,                  // 2D68..2D6E
+            TIFINAGH,                 // 2D6F..2D70
+            UNKNOWN,                  // 2D71..2D7E
+            TIFINAGH,                 // 2D7F
+            ETHIOPIC,                 // 2D80..2D96
+            UNKNOWN,                  // 2D97..2D9F
+            ETHIOPIC,                 // 2DA0..2DA6
+            UNKNOWN,                  // 2DA7
+            ETHIOPIC,                 // 2DA8..2DAE
+            UNKNOWN,                  // 2DAF
+            ETHIOPIC,                 // 2DB0..2DB6
+            UNKNOWN,                  // 2DB7
+            ETHIOPIC,                 // 2DB8..2DBE
+            UNKNOWN,                  // 2DBF
+            ETHIOPIC,                 // 2DC0..2DC6
+            UNKNOWN,                  // 2DC7
+            ETHIOPIC,                 // 2DC8..2DCE
+            UNKNOWN,                  // 2DCF
+            ETHIOPIC,                 // 2DD0..2DD6
+            UNKNOWN,                  // 2DD7
+            ETHIOPIC,                 // 2DD8..2DDE
+            UNKNOWN,                  // 2DDF
+            CYRILLIC,                 // 2DE0..2DFF
+            COMMON,                   // 2E00..2E42
+            UNKNOWN,                  // 2E43..2E7F
+            HAN,                      // 2E80..2E99
+            UNKNOWN,                  // 2E9A
+            HAN,                      // 2E9B..2EF3
+            UNKNOWN,                  // 2EF4..2EFF
+            HAN,                      // 2F00..2FD5
+            UNKNOWN,                  // 2FD6..2FEF
+            COMMON,                   // 2FF0..2FFB
+            UNKNOWN,                  // 2FFC..2FFF
+            COMMON,                   // 3000..3004
+            HAN,                      // 3005
+            COMMON,                   // 3006
+            HAN,                      // 3007
+            COMMON,                   // 3008..3020
+            HAN,                      // 3021..3029
+            INHERITED,                // 302A..302D
+            HANGUL,                   // 302E..302F
+            COMMON,                   // 3030..3037
+            HAN,                      // 3038..303B
+            COMMON,                   // 303C..303F
+            UNKNOWN,                  // 3040
+            HIRAGANA,                 // 3041..3096
+            UNKNOWN,                  // 3097..3098
+            INHERITED,                // 3099..309A
+            COMMON,                   // 309B..309C
+            HIRAGANA,                 // 309D..309F
+            COMMON,                   // 30A0
+            KATAKANA,                 // 30A1..30FA
+            COMMON,                   // 30FB..30FC
+            KATAKANA,                 // 30FD..30FF
+            UNKNOWN,                  // 3100..3104
+            BOPOMOFO,                 // 3105..312D
+            UNKNOWN,                  // 312E..3130
+            HANGUL,                   // 3131..318E
+            UNKNOWN,                  // 318F
+            COMMON,                   // 3190..319F
+            BOPOMOFO,                 // 31A0..31BA
+            UNKNOWN,                  // 31BB..31BF
+            COMMON,                   // 31C0..31E3
+            UNKNOWN,                  // 31E4..31EF
+            KATAKANA,                 // 31F0..31FF
+            HANGUL,                   // 3200..321E
+            UNKNOWN,                  // 321F
+            COMMON,                   // 3220..325F
+            HANGUL,                   // 3260..327E
+            COMMON,                   // 327F..32CF
+            KATAKANA,                 // 32D0..32FE
+            UNKNOWN,                  // 32FF
+            KATAKANA,                 // 3300..3357
+            COMMON,                   // 3358..33FF
+            HAN,                      // 3400..4DB5
+            UNKNOWN,                  // 4DB6..4DBF
+            COMMON,                   // 4DC0..4DFF
+            HAN,                      // 4E00..9FCC
+            UNKNOWN,                  // 9FCD..9FFF
+            YI,                       // A000..A48C
+            UNKNOWN,                  // A48D..A48F
+            YI,                       // A490..A4C6
+            UNKNOWN,                  // A4C7..A4CF
+            LISU,                     // A4D0..A4FF
+            VAI,                      // A500..A62B
+            UNKNOWN,                  // A62C..A63F
+            CYRILLIC,                 // A640..A69D
+            UNKNOWN,                  // A69E
+            CYRILLIC,                 // A69F
+            BAMUM,                    // A6A0..A6F7
+            UNKNOWN,                  // A6F8..A6FF
+            COMMON,                   // A700..A721
+            LATIN,                    // A722..A787
+            COMMON,                   // A788..A78A
+            LATIN,                    // A78B..A78E
+            UNKNOWN,                  // A78F
+            LATIN,                    // A790..A7AD
+            UNKNOWN,                  // A7AE..A7AF
+            LATIN,                    // A7B0..A7B1
+            UNKNOWN,                  // A7B2..A7F6
+            LATIN,                    // A7F7..A7FF
+            SYLOTI_NAGRI,             // A800..A82B
+            UNKNOWN,                  // A82C..A82F
+            COMMON,                   // A830..A839
+            UNKNOWN,                  // A83A..A83F
+            PHAGS_PA,                 // A840..A877
+            UNKNOWN,                  // A878..A87F
+            SAURASHTRA,               // A880..A8C4
+            UNKNOWN,                  // A8C5..A8CD
+            SAURASHTRA,               // A8CE..A8D9
+            UNKNOWN,                  // A8DA..A8DF
+            DEVANAGARI,               // A8E0..A8FB
+            UNKNOWN,                  // A8FC..A8FF
+            KAYAH_LI,                 // A900..A92D
+            COMMON,                   // A92E
+            KAYAH_LI,                 // A92F
+            REJANG,                   // A930..A953
+            UNKNOWN,                  // A954..A95E
+            REJANG,                   // A95F
+            HANGUL,                   // A960..A97C
+            UNKNOWN,                  // A97D..A97F
+            JAVANESE,                 // A980..A9CD
+            UNKNOWN,                  // A9CE
+            COMMON,                   // A9CF
+            JAVANESE,                 // A9D0..A9D9
+            UNKNOWN,                  // A9DA..A9DD
+            JAVANESE,                 // A9DE..A9DF
+            MYANMAR,                  // A9E0..A9FE
+            UNKNOWN,                  // A9FF
+            CHAM,                     // AA00..AA36
+            UNKNOWN,                  // AA37..AA3F
+            CHAM,                     // AA40..AA4D
+            UNKNOWN,                  // AA4E..AA4F
+            CHAM,                     // AA50..AA59
+            UNKNOWN,                  // AA5A..AA5B
+            CHAM,                     // AA5C..AA5F
+            MYANMAR,                  // AA60..AA7F
+            TAI_VIET,                 // AA80..AAC2
+            UNKNOWN,                  // AAC3..AADA
+            TAI_VIET,                 // AADB..AADF
+            MEETEI_MAYEK,             // AAE0..AAF6
+            UNKNOWN,                  // AAF7..AB00
+            ETHIOPIC,                 // AB01..AB06
+            UNKNOWN,                  // AB07..AB08
+            ETHIOPIC,                 // AB09..AB0E
+            UNKNOWN,                  // AB0F..AB10
+            ETHIOPIC,                 // AB11..AB16
+            UNKNOWN,                  // AB17..AB1F
+            ETHIOPIC,                 // AB20..AB26
+            UNKNOWN,                  // AB27
+            ETHIOPIC,                 // AB28..AB2E
+            UNKNOWN,                  // AB2F
+            LATIN,                    // AB30..AB5A
+            COMMON,                   // AB5B
+            LATIN,                    // AB5C..AB5F
+            UNKNOWN,                  // AB60..AB63
+            LATIN,                    // AB64
+            GREEK,                    // AB65
+            UNKNOWN,                  // AB66..ABBF
+            MEETEI_MAYEK,             // ABC0..ABED
+            UNKNOWN,                  // ABEE..ABEF
+            MEETEI_MAYEK,             // ABF0..ABF9
+            UNKNOWN,                  // ABFA..ABFF
+            HANGUL,                   // AC00..D7A3
+            UNKNOWN,                  // D7A4..D7AF
+            HANGUL,                   // D7B0..D7C6
+            UNKNOWN,                  // D7C7..D7CA
+            HANGUL,                   // D7CB..D7FB
+            UNKNOWN,                  // D7FC..F8FF
+            HAN,                      // F900..FA6D
+            UNKNOWN,                  // FA6E..FA6F
+            HAN,                      // FA70..FAD9
+            UNKNOWN,                  // FADA..FAFF
+            LATIN,                    // FB00..FB06
+            UNKNOWN,                  // FB07..FB12
+            ARMENIAN,                 // FB13..FB17
+            UNKNOWN,                  // FB18..FB1C
+            HEBREW,                   // FB1D..FB36
+            UNKNOWN,                  // FB37
+            HEBREW,                   // FB38..FB3C
+            UNKNOWN,                  // FB3D
+            HEBREW,                   // FB3E
+            UNKNOWN,                  // FB3F
+            HEBREW,                   // FB40..FB41
+            UNKNOWN,                  // FB42
+            HEBREW,                   // FB43..FB44
+            UNKNOWN,                  // FB45
+            HEBREW,                   // FB46..FB4F
+            ARABIC,                   // FB50..FBC1
+            UNKNOWN,                  // FBC2..FBD2
+            ARABIC,                   // FBD3..FD3D
+            COMMON,                   // FD3E..FD3F
+            UNKNOWN,                  // FD40..FD4F
+            ARABIC,                   // FD50..FD8F
+            UNKNOWN,                  // FD90..FD91
+            ARABIC,                   // FD92..FDC7
+            UNKNOWN,                  // FDC8..FDEF
+            ARABIC,                   // FDF0..FDFD
+            UNKNOWN,                  // FDFE..FDFF
+            INHERITED,                // FE00..FE0F
+            COMMON,                   // FE10..FE19
+            UNKNOWN,                  // FE1A..FE1F
+            INHERITED,                // FE20..FE2D
+            UNKNOWN,                  // FE2E..FE2F
+            COMMON,                   // FE30..FE52
+            UNKNOWN,                  // FE53
+            COMMON,                   // FE54..FE66
+            UNKNOWN,                  // FE67
+            COMMON,                   // FE68..FE6B
+            UNKNOWN,                  // FE6C..FE6F
+            ARABIC,                   // FE70..FE74
+            UNKNOWN,                  // FE75
+            ARABIC,                   // FE76..FEFC
+            UNKNOWN,                  // FEFD..FEFE
+            COMMON,                   // FEFF
+            UNKNOWN,                  // FF00
+            COMMON,                   // FF01..FF20
+            LATIN,                    // FF21..FF3A
+            COMMON,                   // FF3B..FF40
+            LATIN,                    // FF41..FF5A
+            COMMON,                   // FF5B..FF65
+            KATAKANA,                 // FF66..FF6F
+            COMMON,                   // FF70
+            KATAKANA,                 // FF71..FF9D
+            COMMON,                   // FF9E..FF9F
+            HANGUL,                   // FFA0..FFBE
+            UNKNOWN,                  // FFBF..FFC1
+            HANGUL,                   // FFC2..FFC7
+            UNKNOWN,                  // FFC8..FFC9
+            HANGUL,                   // FFCA..FFCF
+            UNKNOWN,                  // FFD0..FFD1
+            HANGUL,                   // FFD2..FFD7
+            UNKNOWN,                  // FFD8..FFD9
+            HANGUL,                   // FFDA..FFDC
+            UNKNOWN,                  // FFDD..FFDF
+            COMMON,                   // FFE0..FFE6
+            UNKNOWN,                  // FFE7
+            COMMON,                   // FFE8..FFEE
+            UNKNOWN,                  // FFEF..FFF8
+            COMMON,                   // FFF9..FFFD
+            UNKNOWN,                  // FFFE..FFFF
+            LINEAR_B,                 // 10000..1000B
+            UNKNOWN,                  // 1000C
+            LINEAR_B,                 // 1000D..10026
+            UNKNOWN,                  // 10027
+            LINEAR_B,                 // 10028..1003A
+            UNKNOWN,                  // 1003B
+            LINEAR_B,                 // 1003C..1003D
+            UNKNOWN,                  // 1003E
+            LINEAR_B,                 // 1003F..1004D
+            UNKNOWN,                  // 1004E..1004F
+            LINEAR_B,                 // 10050..1005D
+            UNKNOWN,                  // 1005E..1007F
+            LINEAR_B,                 // 10080..100FA
+            UNKNOWN,                  // 100FB..100FF
+            COMMON,                   // 10100..10102
+            UNKNOWN,                  // 10103..10106
+            COMMON,                   // 10107..10133
+            UNKNOWN,                  // 10134..10136
+            COMMON,                   // 10137..1013F
+            GREEK,                    // 10140..1018C
+            UNKNOWN,                  // 1018D..1018F
+            COMMON,                   // 10190..1019B
+            UNKNOWN,                  // 1019C..1019F
+            GREEK,                    // 101A0
+            UNKNOWN,                  // 101A1..101CF
+            COMMON,                   // 101D0..101FC
+            INHERITED,                // 101FD
+            UNKNOWN,                  // 101FE..1027F
+            LYCIAN,                   // 10280..1029C
+            UNKNOWN,                  // 1029D..1029F
+            CARIAN,                   // 102A0..102D0
+            UNKNOWN,                  // 102D1..102DF
+            INHERITED,                // 102E0
+            COMMON,                   // 102E1..102FB
+            UNKNOWN,                  // 102FC..102FF
+            OLD_ITALIC,               // 10300..10323
+            UNKNOWN,                  // 10324..1032F
+            GOTHIC,                   // 10330..1034A
+            UNKNOWN,                  // 1034B..1034F
+            OLD_PERMIC,               // 10350..1037A
+            UNKNOWN,                  // 1037B..1037F
+            UGARITIC,                 // 10380..1039D
+            UNKNOWN,                  // 1039E
+            UGARITIC,                 // 1039F
+            OLD_PERSIAN,              // 103A0..103C3
+            UNKNOWN,                  // 103C4..103C7
+            OLD_PERSIAN,              // 103C8..103D5
+            UNKNOWN,                  // 103D6..103FF
+            DESERET,                  // 10400..1044F
+            SHAVIAN,                  // 10450..1047F
+            OSMANYA,                  // 10480..1049D
+            UNKNOWN,                  // 1049E..1049F
+            OSMANYA,                  // 104A0..104A9
+            UNKNOWN,                  // 104AA..104FF
+            ELBASAN,                  // 10500..10527
+            UNKNOWN,                  // 10528..1052F
+            CAUCASIAN_ALBANIAN,       // 10530..10563
+            UNKNOWN,                  // 10564..1056E
+            CAUCASIAN_ALBANIAN,       // 1056F
+            UNKNOWN,                  // 10570..105FF
+            LINEAR_A,                 // 10600..10736
+            UNKNOWN,                  // 10737..1073F
+            LINEAR_A,                 // 10740..10755
+            UNKNOWN,                  // 10756..1075F
+            LINEAR_A,                 // 10760..10767
+            UNKNOWN,                  // 10768..107FF
+            CYPRIOT,                  // 10800..10805
+            UNKNOWN,                  // 10806..10807
+            CYPRIOT,                  // 10808
+            UNKNOWN,                  // 10809
+            CYPRIOT,                  // 1080A..10835
+            UNKNOWN,                  // 10836
+            CYPRIOT,                  // 10837..10838
+            UNKNOWN,                  // 10839..1083B
+            CYPRIOT,                  // 1083C
+            UNKNOWN,                  // 1083D..1083E
+            CYPRIOT,                  // 1083F
+            IMPERIAL_ARAMAIC,         // 10840..10855
+            UNKNOWN,                  // 10856
+            IMPERIAL_ARAMAIC,         // 10857..1085F
+            PALMYRENE,                // 10860..1087F
+            NABATAEAN,                // 10880..1089E
+            UNKNOWN,                  // 1089F..108A6
+            NABATAEAN,                // 108A7..108AF
+            UNKNOWN,                  // 108B0..108FF
+            PHOENICIAN,               // 10900..1091B
+            UNKNOWN,                  // 1091C..1091E
+            PHOENICIAN,               // 1091F
+            LYDIAN,                   // 10920..10939
+            UNKNOWN,                  // 1093A..1093E
+            LYDIAN,                   // 1093F
+            UNKNOWN,                  // 10940..1097F
+            MEROITIC_HIEROGLYPHS,     // 10980..1099F
+            MEROITIC_CURSIVE,         // 109A0..109B7
+            UNKNOWN,                  // 109B8..109BD
+            MEROITIC_CURSIVE,         // 109BE..109BF
+            UNKNOWN,                  // 109C0..109FF
+            KHAROSHTHI,               // 10A00..10A03
+            UNKNOWN,                  // 10A04
+            KHAROSHTHI,               // 10A05..10A06
+            UNKNOWN,                  // 10A07..10A0B
+            KHAROSHTHI,               // 10A0C..10A13
+            UNKNOWN,                  // 10A14
+            KHAROSHTHI,               // 10A15..10A17
+            UNKNOWN,                  // 10A18
+            KHAROSHTHI,               // 10A19..10A33
+            UNKNOWN,                  // 10A34..10A37
+            KHAROSHTHI,               // 10A38..10A3A
+            UNKNOWN,                  // 10A3B..10A3E
+            KHAROSHTHI,               // 10A3F..10A47
+            UNKNOWN,                  // 10A48..10A4F
+            KHAROSHTHI,               // 10A50..10A58
+            UNKNOWN,                  // 10A59..10A5F
+            OLD_SOUTH_ARABIAN,        // 10A60..10A7F
+            OLD_NORTH_ARABIAN,        // 10A80..10A9F
+            UNKNOWN,                  // 10AA0..10ABF
+            MANICHAEAN,               // 10AC0..10AE6
+            UNKNOWN,                  // 10AE7..10AEA
+            MANICHAEAN,               // 10AEB..10AF6
+            UNKNOWN,                  // 10AF7..10AFF
+            AVESTAN,                  // 10B00..10B35
+            UNKNOWN,                  // 10B36..10B38
+            AVESTAN,                  // 10B39..10B3F
+            INSCRIPTIONAL_PARTHIAN,   // 10B40..10B55
+            UNKNOWN,                  // 10B56..10B57
+            INSCRIPTIONAL_PARTHIAN,   // 10B58..10B5F
+            INSCRIPTIONAL_PAHLAVI,    // 10B60..10B72
+            UNKNOWN,                  // 10B73..10B77
+            INSCRIPTIONAL_PAHLAVI,    // 10B78..10B7F
+            PSALTER_PAHLAVI,          // 10B80..10B91
+            UNKNOWN,                  // 10B92..10B98
+            PSALTER_PAHLAVI,          // 10B99..10B9C
+            UNKNOWN,                  // 10B9D..10BA8
+            PSALTER_PAHLAVI,          // 10BA9..10BAF
+            UNKNOWN,                  // 10BB0..10BFF
+            OLD_TURKIC,               // 10C00..10C48
+            UNKNOWN,                  // 10C49..10E5F
+            ARABIC,                   // 10E60..10E7E
+            UNKNOWN,                  // 10E7F..10FFF
+            BRAHMI,                   // 11000..1104D
+            UNKNOWN,                  // 1104E..11051
+            BRAHMI,                   // 11052..1106F
+            UNKNOWN,                  // 11070..1107E
+            BRAHMI,                   // 1107F
+            KAITHI,                   // 11080..110C1
+            UNKNOWN,                  // 110C2..110CF
+            SORA_SOMPENG,             // 110D0..110E8
+            UNKNOWN,                  // 110E9..110EF
+            SORA_SOMPENG,             // 110F0..110F9
+            UNKNOWN,                  // 110FA..110FF
+            CHAKMA,                   // 11100..11134
+            UNKNOWN,                  // 11135
+            CHAKMA,                   // 11136..11143
+            UNKNOWN,                  // 11144..1114F
+            MAHAJANI,                 // 11150..11176
+            UNKNOWN,                  // 11177..1117F
+            SHARADA,                  // 11180..111C8
+            UNKNOWN,                  // 111C9..111CC
+            SHARADA,                  // 111CD
+            UNKNOWN,                  // 111CE..111CF
+            SHARADA,                  // 111D0..111DA
+            UNKNOWN,                  // 111DB..111E0
+            SINHALA,                  // 111E1..111F4
+            UNKNOWN,                  // 111F5..111FF
+            KHOJKI,                   // 11200..11211
+            UNKNOWN,                  // 11212
+            KHOJKI,                   // 11213..1123D
+            UNKNOWN,                  // 1123E..112AF
+            KHUDAWADI,                // 112B0..112EA
+            UNKNOWN,                  // 112EB..112EF
+            KHUDAWADI,                // 112F0..112F9
+            UNKNOWN,                  // 112FA..11300
+            GRANTHA,                  // 11301..11303
+            UNKNOWN,                  // 11304
+            GRANTHA,                  // 11305..1130C
+            UNKNOWN,                  // 1130D..1130E
+            GRANTHA,                  // 1130F..11310
+            UNKNOWN,                  // 11311..11312
+            GRANTHA,                  // 11313..11328
+            UNKNOWN,                  // 11329
+            GRANTHA,                  // 1132A..11330
+            UNKNOWN,                  // 11331
+            GRANTHA,                  // 11332..11333
+            UNKNOWN,                  // 11334
+            GRANTHA,                  // 11335..11339
+            UNKNOWN,                  // 1133A..1133B
+            GRANTHA,                  // 1133C..11344
+            UNKNOWN,                  // 11345..11346
+            GRANTHA,                  // 11347..11348
+            UNKNOWN,                  // 11349..1134A
+            GRANTHA,                  // 1134B..1134D
+            UNKNOWN,                  // 1134E..11356
+            GRANTHA,                  // 11357
+            UNKNOWN,                  // 11358..1135C
+            GRANTHA,                  // 1135D..11363
+            UNKNOWN,                  // 11364..11365
+            GRANTHA,                  // 11366..1136C
+            UNKNOWN,                  // 1136D..1136F
+            GRANTHA,                  // 11370..11374
+            UNKNOWN,                  // 11375..1147F
+            TIRHUTA,                  // 11480..114C7
+            UNKNOWN,                  // 114C8..114CF
+            TIRHUTA,                  // 114D0..114D9
+            UNKNOWN,                  // 114DA..1157F
+            SIDDHAM,                  // 11580..115B5
+            UNKNOWN,                  // 115B6..115B7
+            SIDDHAM,                  // 115B8..115C9
+            UNKNOWN,                  // 115CA..115FF
+            MODI,                     // 11600..11644
+            UNKNOWN,                  // 11645..1164F
+            MODI,                     // 11650..11659
+            UNKNOWN,                  // 1165A..1167F
+            TAKRI,                    // 11680..116B7
+            UNKNOWN,                  // 116B8..116BF
+            TAKRI,                    // 116C0..116C9
+            UNKNOWN,                  // 116CA..1189F
+            WARANG_CITI,              // 118A0..118F2
+            UNKNOWN,                  // 118F3..118FE
+            WARANG_CITI,              // 118FF
+            UNKNOWN,                  // 11900..11ABF
+            PAU_CIN_HAU,              // 11AC0..11AF8
+            UNKNOWN,                  // 11AF9..11FFF
+            CUNEIFORM,                // 12000..12398
+            UNKNOWN,                  // 12399..123FF
+            CUNEIFORM,                // 12400..1246E
+            UNKNOWN,                  // 1246F
+            CUNEIFORM,                // 12470..12474
+            UNKNOWN,                  // 12475..12FFF
+            EGYPTIAN_HIEROGLYPHS,     // 13000..1342E
+            UNKNOWN,                  // 1342F..167FF
+            BAMUM,                    // 16800..16A38
+            UNKNOWN,                  // 16A39..16A3F
+            MRO,                      // 16A40..16A5E
+            UNKNOWN,                  // 16A5F
+            MRO,                      // 16A60..16A69
+            UNKNOWN,                  // 16A6A..16A6D
+            MRO,                      // 16A6E..16A6F
+            UNKNOWN,                  // 16A70..16ACF
+            BASSA_VAH,                // 16AD0..16AED
+            UNKNOWN,                  // 16AEE..16AEF
+            BASSA_VAH,                // 16AF0..16AF5
+            UNKNOWN,                  // 16AF6..16AFF
+            PAHAWH_HMONG,             // 16B00..16B45
+            UNKNOWN,                  // 16B46..16B4F
+            PAHAWH_HMONG,             // 16B50..16B59
+            UNKNOWN,                  // 16B5A
+            PAHAWH_HMONG,             // 16B5B..16B61
+            UNKNOWN,                  // 16B62
+            PAHAWH_HMONG,             // 16B63..16B77
+            UNKNOWN,                  // 16B78..16B7C
+            PAHAWH_HMONG,             // 16B7D..16B8F
+            UNKNOWN,                  // 16B90..16EFF
+            MIAO,                     // 16F00..16F44
+            UNKNOWN,                  // 16F45..16F4F
+            MIAO,                     // 16F50..16F7E
+            UNKNOWN,                  // 16F7F..16F8E
+            MIAO,                     // 16F8F..16F9F
+            UNKNOWN,                  // 16FA0..1AFFF
+            KATAKANA,                 // 1B000
+            HIRAGANA,                 // 1B001
+            UNKNOWN,                  // 1B002..1BBFF
+            DUPLOYAN,                 // 1BC00..1BC6A
+            UNKNOWN,                  // 1BC6B..1BC6F
+            DUPLOYAN,                 // 1BC70..1BC7C
+            UNKNOWN,                  // 1BC7D..1BC7F
+            DUPLOYAN,                 // 1BC80..1BC88
+            UNKNOWN,                  // 1BC89..1BC8F
+            DUPLOYAN,                 // 1BC90..1BC99
+            UNKNOWN,                  // 1BC9A..1BC9B
+            DUPLOYAN,                 // 1BC9C..1BC9F
+            COMMON,                   // 1BCA0..1BCA3
+            UNKNOWN,                  // 1BCA4..1CFFF
+            COMMON,                   // 1D000..1D0F5
+            UNKNOWN,                  // 1D0F6..1D0FF
+            COMMON,                   // 1D100..1D126
+            UNKNOWN,                  // 1D127..1D128
+            COMMON,                   // 1D129..1D166
+            INHERITED,                // 1D167..1D169
+            COMMON,                   // 1D16A..1D17A
+            INHERITED,                // 1D17B..1D182
+            COMMON,                   // 1D183..1D184
+            INHERITED,                // 1D185..1D18B
+            COMMON,                   // 1D18C..1D1A9
+            INHERITED,                // 1D1AA..1D1AD
+            COMMON,                   // 1D1AE..1D1DD
+            UNKNOWN,                  // 1D1DE..1D1FF
+            GREEK,                    // 1D200..1D245
+            UNKNOWN,                  // 1D246..1D2FF
+            COMMON,                   // 1D300..1D356
+            UNKNOWN,                  // 1D357..1D35F
+            COMMON,                   // 1D360..1D371
+            UNKNOWN,                  // 1D372..1D3FF
+            COMMON,                   // 1D400..1D454
+            UNKNOWN,                  // 1D455
+            COMMON,                   // 1D456..1D49C
+            UNKNOWN,                  // 1D49D
+            COMMON,                   // 1D49E..1D49F
+            UNKNOWN,                  // 1D4A0..1D4A1
+            COMMON,                   // 1D4A2
+            UNKNOWN,                  // 1D4A3..1D4A4
+            COMMON,                   // 1D4A5..1D4A6
+            UNKNOWN,                  // 1D4A7..1D4A8
+            COMMON,                   // 1D4A9..1D4AC
+            UNKNOWN,                  // 1D4AD
+            COMMON,                   // 1D4AE..1D4B9
+            UNKNOWN,                  // 1D4BA
+            COMMON,                   // 1D4BB
+            UNKNOWN,                  // 1D4BC
+            COMMON,                   // 1D4BD..1D4C3
+            UNKNOWN,                  // 1D4C4
+            COMMON,                   // 1D4C5..1D505
+            UNKNOWN,                  // 1D506
+            COMMON,                   // 1D507..1D50A
+            UNKNOWN,                  // 1D50B..1D50C
+            COMMON,                   // 1D50D..1D514
+            UNKNOWN,                  // 1D515
+            COMMON,                   // 1D516..1D51C
+            UNKNOWN,                  // 1D51D
+            COMMON,                   // 1D51E..1D539
+            UNKNOWN,                  // 1D53A
+            COMMON,                   // 1D53B..1D53E
+            UNKNOWN,                  // 1D53F
+            COMMON,                   // 1D540..1D544
+            UNKNOWN,                  // 1D545
+            COMMON,                   // 1D546
+            UNKNOWN,                  // 1D547..1D549
+            COMMON,                   // 1D54A..1D550
+            UNKNOWN,                  // 1D551
+            COMMON,                   // 1D552..1D6A5
+            UNKNOWN,                  // 1D6A6..1D6A7
+            COMMON,                   // 1D6A8..1D7CB
+            UNKNOWN,                  // 1D7CC..1D7CD
+            COMMON,                   // 1D7CE..1D7FF
+            UNKNOWN,                  // 1D800..1E7FF
+            MENDE_KIKAKUI,            // 1E800..1E8C4
+            UNKNOWN,                  // 1E8C5..1E8C6
+            MENDE_KIKAKUI,            // 1E8C7..1E8D6
+            UNKNOWN,                  // 1E8D7..1EDFF
+            ARABIC,                   // 1EE00..1EE03
+            UNKNOWN,                  // 1EE04
+            ARABIC,                   // 1EE05..1EE1F
+            UNKNOWN,                  // 1EE20
+            ARABIC,                   // 1EE21..1EE22
+            UNKNOWN,                  // 1EE23
+            ARABIC,                   // 1EE24
+            UNKNOWN,                  // 1EE25..1EE26
+            ARABIC,                   // 1EE27
+            UNKNOWN,                  // 1EE28
+            ARABIC,                   // 1EE29..1EE32
+            UNKNOWN,                  // 1EE33
+            ARABIC,                   // 1EE34..1EE37
+            UNKNOWN,                  // 1EE38
+            ARABIC,                   // 1EE39
+            UNKNOWN,                  // 1EE3A
+            ARABIC,                   // 1EE3B
+            UNKNOWN,                  // 1EE3C..1EE41
+            ARABIC,                   // 1EE42
+            UNKNOWN,                  // 1EE43..1EE46
+            ARABIC,                   // 1EE47
+            UNKNOWN,                  // 1EE48
+            ARABIC,                   // 1EE49
+            UNKNOWN,                  // 1EE4A
+            ARABIC,                   // 1EE4B
+            UNKNOWN,                  // 1EE4C
+            ARABIC,                   // 1EE4D..1EE4F
+            UNKNOWN,                  // 1EE50
+            ARABIC,                   // 1EE51..1EE52
+            UNKNOWN,                  // 1EE53
+            ARABIC,                   // 1EE54
+            UNKNOWN,                  // 1EE55..1EE56
+            ARABIC,                   // 1EE57
+            UNKNOWN,                  // 1EE58
+            ARABIC,                   // 1EE59
+            UNKNOWN,                  // 1EE5A
+            ARABIC,                   // 1EE5B
+            UNKNOWN,                  // 1EE5C
+            ARABIC,                   // 1EE5D
+            UNKNOWN,                  // 1EE5E
+            ARABIC,                   // 1EE5F
+            UNKNOWN,                  // 1EE60
+            ARABIC,                   // 1EE61..1EE62
+            UNKNOWN,                  // 1EE63
+            ARABIC,                   // 1EE64
+            UNKNOWN,                  // 1EE65..1EE66
+            ARABIC,                   // 1EE67..1EE6A
+            UNKNOWN,                  // 1EE6B
+            ARABIC,                   // 1EE6C..1EE72
+            UNKNOWN,                  // 1EE73
+            ARABIC,                   // 1EE74..1EE77
+            UNKNOWN,                  // 1EE78
+            ARABIC,                   // 1EE79..1EE7C
+            UNKNOWN,                  // 1EE7D
+            ARABIC,                   // 1EE7E
+            UNKNOWN,                  // 1EE7F
+            ARABIC,                   // 1EE80..1EE89
+            UNKNOWN,                  // 1EE8A
+            ARABIC,                   // 1EE8B..1EE9B
+            UNKNOWN,                  // 1EE9C..1EEA0
+            ARABIC,                   // 1EEA1..1EEA3
+            UNKNOWN,                  // 1EEA4
+            ARABIC,                   // 1EEA5..1EEA9
+            UNKNOWN,                  // 1EEAA
+            ARABIC,                   // 1EEAB..1EEBB
+            UNKNOWN,                  // 1EEBC..1EEEF
+            ARABIC,                   // 1EEF0..1EEF1
+            UNKNOWN,                  // 1EEF2..1EFFF
+            COMMON,                   // 1F000..1F02B
+            UNKNOWN,                  // 1F02C..1F02F
+            COMMON,                   // 1F030..1F093
+            UNKNOWN,                  // 1F094..1F09F
+            COMMON,                   // 1F0A0..1F0AE
+            UNKNOWN,                  // 1F0AF..1F0B0
+            COMMON,                   // 1F0B1..1F0BF
+            UNKNOWN,                  // 1F0C0
+            COMMON,                   // 1F0C1..1F0CF
+            UNKNOWN,                  // 1F0D0
+            COMMON,                   // 1F0D1..1F0F5
+            UNKNOWN,                  // 1F0F6..1F0FF
+            COMMON,                   // 1F100..1F10C
+            UNKNOWN,                  // 1F10D..1F10F
+            COMMON,                   // 1F110..1F12E
+            UNKNOWN,                  // 1F12F
+            COMMON,                   // 1F130..1F16B
+            UNKNOWN,                  // 1F16C..1F16F
+            COMMON,                   // 1F170..1F19A
+            UNKNOWN,                  // 1F19B..1F1E5
+            COMMON,                   // 1F1E6..1F1FF
+            HIRAGANA,                 // 1F200
+            COMMON,                   // 1F201..1F202
+            UNKNOWN,                  // 1F203..1F20F
+            COMMON,                   // 1F210..1F23A
+            UNKNOWN,                  // 1F23B..1F23F
+            COMMON,                   // 1F240..1F248
+            UNKNOWN,                  // 1F249..1F24F
+            COMMON,                   // 1F250..1F251
+            UNKNOWN,                  // 1F252..1F2FF
+            COMMON,                   // 1F300..1F32C
+            UNKNOWN,                  // 1F32D..1F32F
+            COMMON,                   // 1F330..1F37D
+            UNKNOWN,                  // 1F37E..1F37F
+            COMMON,                   // 1F380..1F3CE
+            UNKNOWN,                  // 1F3CF..1F3D3
+            COMMON,                   // 1F3D4..1F3F7
+            UNKNOWN,                  // 1F3F8..1F3FF
+            COMMON,                   // 1F400..1F4FE
+            UNKNOWN,                  // 1F4FF
+            COMMON,                   // 1F500..1F54A
+            UNKNOWN,                  // 1F54B..1F54F
+            COMMON,                   // 1F550..1F579
+            UNKNOWN,                  // 1F57A
+            COMMON,                   // 1F57B..1F5A3
+            UNKNOWN,                  // 1F5A4
+            COMMON,                   // 1F5A5..1F642
+            UNKNOWN,                  // 1F643..1F644
+            COMMON,                   // 1F645..1F6CF
+            UNKNOWN,                  // 1F6D0..1F6DF
+            COMMON,                   // 1F6E0..1F6EC
+            UNKNOWN,                  // 1F6ED..1F6EF
+            COMMON,                   // 1F6F0..1F6F3
+            UNKNOWN,                  // 1F6F4..1F6FF
+            COMMON,                   // 1F700..1F773
+            UNKNOWN,                  // 1F774..1F77F
+            COMMON,                   // 1F780..1F7D4
+            UNKNOWN,                  // 1F7D5..1F7FF
+            COMMON,                   // 1F800..1F80B
+            UNKNOWN,                  // 1F80C..1F80F
+            COMMON,                   // 1F810..1F847
+            UNKNOWN,                  // 1F848..1F84F
+            COMMON,                   // 1F850..1F859
+            UNKNOWN,                  // 1F85A..1F85F
+            COMMON,                   // 1F860..1F887
+            UNKNOWN,                  // 1F888..1F88F
+            COMMON,                   // 1F890..1F8AD
+            UNKNOWN,                  // 1F8AE..1FFFF
+            HAN,                      // 20000..2A6D6
+            UNKNOWN,                  // 2A6D7..2A6FF
+            HAN,                      // 2A700..2B734
+            UNKNOWN,                  // 2B735..2B73F
+            HAN,                      // 2B740..2B81D
+            UNKNOWN,                  // 2B81E..2F7FF
+            HAN,                      // 2F800..2FA1D
+            UNKNOWN,                  // 2FA1E..E0000
+            COMMON,                   // E0001
+            UNKNOWN,                  // E0002..E001F
+            COMMON,                   // E0020..E007F
+            UNKNOWN,                  // E0080..E00FF
+            INHERITED,                // E0100..E01EF
+            UNKNOWN                   // E01F0..10FFFF
         };
 
         private static HashMap<String, Character.UnicodeScript> aliases;
         static {
             aliases = new HashMap<>(128);
+            aliases.put("AGHB", CAUCASIAN_ALBANIAN);
             aliases.put("ARAB", ARABIC);
             aliases.put("ARMI", IMPERIAL_ARAMAIC);
             aliases.put("ARMN", ARMENIAN);
             aliases.put("AVST", AVESTAN);
             aliases.put("BALI", BALINESE);
             aliases.put("BAMU", BAMUM);
+            aliases.put("BASS", BASSA_VAH);
             aliases.put("BATK", BATAK);
             aliases.put("BENG", BENGALI);
             aliases.put("BOPO", BOPOMOFO);
+            aliases.put("BRAH", BRAHMI);
             aliases.put("BRAI", BRAILLE);
-            aliases.put("BRAH", BRAHMI);
             aliases.put("BUGI", BUGINESE);
             aliases.put("BUHD", BUHID);
             aliases.put("CAKM", CHAKMA);
@@ -4380,11 +7061,14 @@
             aliases.put("CYRL", CYRILLIC);
             aliases.put("DEVA", DEVANAGARI);
             aliases.put("DSRT", DESERET);
+            aliases.put("DUPL", DUPLOYAN);
             aliases.put("EGYP", EGYPTIAN_HIEROGLYPHS);
+            aliases.put("ELBA", ELBASAN);
             aliases.put("ETHI", ETHIOPIC);
             aliases.put("GEOR", GEORGIAN);
             aliases.put("GLAG", GLAGOLITIC);
             aliases.put("GOTH", GOTHIC);
+            aliases.put("GRAN", GRANTHA);
             aliases.put("GREK", GREEK);
             aliases.put("GUJR", GUJARATI);
             aliases.put("GURU", GURMUKHI);
@@ -4393,6 +7077,7 @@
             aliases.put("HANO", HANUNOO);
             aliases.put("HEBR", HEBREW);
             aliases.put("HIRA", HIRAGANA);
+            aliases.put("HMNG", PAHAWH_HMONG);
             // it appears we don't have the KATAKANA_OR_HIRAGANA
             //aliases.put("HRKT", KATAKANA_OR_HIRAGANA);
             aliases.put("ITAL", OLD_ITALIC);
@@ -4401,6 +7086,7 @@
             aliases.put("KANA", KATAKANA);
             aliases.put("KHAR", KHAROSHTHI);
             aliases.put("KHMR", KHMER);
+            aliases.put("KHOJ", KHOJKI);
             aliases.put("KNDA", KANNADA);
             aliases.put("KTHI", KAITHI);
             aliases.put("LANA", TAI_THAM);
@@ -4408,27 +7094,39 @@
             aliases.put("LATN", LATIN);
             aliases.put("LEPC", LEPCHA);
             aliases.put("LIMB", LIMBU);
+            aliases.put("LINA", LINEAR_A);
             aliases.put("LINB", LINEAR_B);
             aliases.put("LISU", LISU);
             aliases.put("LYCI", LYCIAN);
             aliases.put("LYDI", LYDIAN);
+            aliases.put("MAHJ", MAHAJANI);
             aliases.put("MAND", MANDAIC);
+            aliases.put("MANI", MANICHAEAN);
+            aliases.put("MEND", MENDE_KIKAKUI);
             aliases.put("MERC", MEROITIC_CURSIVE);
             aliases.put("MERO", MEROITIC_HIEROGLYPHS);
             aliases.put("MLYM", MALAYALAM);
+            aliases.put("MODI", MODI);
             aliases.put("MONG", MONGOLIAN);
+            aliases.put("MROO", MRO);
             aliases.put("MTEI", MEETEI_MAYEK);
             aliases.put("MYMR", MYANMAR);
+            aliases.put("NARB", OLD_NORTH_ARABIAN);
+            aliases.put("NBAT", NABATAEAN);
             aliases.put("NKOO", NKO);
             aliases.put("OGAM", OGHAM);
             aliases.put("OLCK", OL_CHIKI);
             aliases.put("ORKH", OLD_TURKIC);
             aliases.put("ORYA", ORIYA);
             aliases.put("OSMA", OSMANYA);
+            aliases.put("PALM", PALMYRENE);
+            aliases.put("PAUC", PAU_CIN_HAU);
+            aliases.put("PERM", OLD_PERMIC);
             aliases.put("PHAG", PHAGS_PA);
+            aliases.put("PHLI", INSCRIPTIONAL_PAHLAVI);
+            aliases.put("PHLP", PSALTER_PAHLAVI);
+            aliases.put("PHNX", PHOENICIAN);
             aliases.put("PLRD", MIAO);
-            aliases.put("PHLI", INSCRIPTIONAL_PAHLAVI);
-            aliases.put("PHNX", PHOENICIAN);
             aliases.put("PRTI", INSCRIPTIONAL_PARTHIAN);
             aliases.put("RJNG", REJANG);
             aliases.put("RUNR", RUNIC);
@@ -4437,14 +7135,16 @@
             aliases.put("SAUR", SAURASHTRA);
             aliases.put("SHAW", SHAVIAN);
             aliases.put("SHRD", SHARADA);
+            aliases.put("SIDD", SIDDHAM);
+            aliases.put("SIND", KHUDAWADI);
             aliases.put("SINH", SINHALA);
             aliases.put("SORA", SORA_SOMPENG);
             aliases.put("SUND", SUNDANESE);
             aliases.put("SYLO", SYLOTI_NAGRI);
             aliases.put("SYRC", SYRIAC);
             aliases.put("TAGB", TAGBANWA);
+            aliases.put("TAKR", TAKRI);
             aliases.put("TALE", TAI_LE);
-            aliases.put("TAKR", TAKRI);
             aliases.put("TALU", NEW_TAI_LUE);
             aliases.put("TAML", TAMIL);
             aliases.put("TAVT", TAI_VIET);
@@ -4454,8 +7154,10 @@
             aliases.put("THAA", THAANA);
             aliases.put("THAI", THAI);
             aliases.put("TIBT", TIBETAN);
+            aliases.put("TIRH", TIRHUTA);
             aliases.put("UGAR", UGARITIC);
             aliases.put("VAII", VAI);
+            aliases.put("WARA", WARANG_CITI);
             aliases.put("XPEO", OLD_PERSIAN);
             aliases.put("XSUX", CUNEIFORM);
             aliases.put("YIII", YI);
@@ -4569,6 +7271,7 @@
      * @return a <tt>Character</tt> instance representing <tt>c</tt>.
      * @since  1.5
      */
+    @HotSpotIntrinsicCandidate
     public static Character valueOf(char c) {
         if (c <= 127) { // must cache
             return CharacterCache.cache[(int)c];
@@ -4581,6 +7284,7 @@
      * @return  the primitive {@code char} value represented by
      *          this object.
      */
+    @HotSpotIntrinsicCandidate
     public char charValue() {
         return value;
     }
@@ -6594,8 +9298,9 @@
      *
      * @param   ch      the character to be converted.
      * @return  the numeric value of the character, as a nonnegative {@code int}
-     *           value; -2 if the character has a numeric value that is not a
-     *          nonnegative integer; -1 if the character has no numeric value.
+     *          value; -2 if the character has a numeric value but the value
+     *          can not be represented as a nonnegative {@code int} value;
+     *          -1 if the character has no numeric value.
      * @see     Character#forDigit(int, int)
      * @see     Character#isDigit(char)
      * @since   1.1
@@ -6627,8 +9332,9 @@
      *
      * @param   codePoint the character (Unicode code point) to be converted.
      * @return  the numeric value of the character, as a nonnegative {@code int}
-     *          value; -2 if the character has a numeric value that is not a
-     *          nonnegative integer; -1 if the character has no numeric value.
+     *          value; -2 if the character has a numeric value but the value
+     *          can not be represented as a nonnegative {@code int} value;
+     *          -1 if the character has no numeric value.
      * @see     Character#forDigit(int, int)
      * @see     Character#isDigit(int)
      * @since   1.5
@@ -6998,6 +9704,10 @@
      * @see Character#DIRECTIONALITY_RIGHT_TO_LEFT_EMBEDDING
      * @see Character#DIRECTIONALITY_RIGHT_TO_LEFT_OVERRIDE
      * @see Character#DIRECTIONALITY_POP_DIRECTIONAL_FORMAT
+     * @see Character#DIRECTIONALITY_LEFT_TO_RIGHT_ISOLATE
+     * @see Character#DIRECTIONALITY_RIGHT_TO_LEFT_ISOLATE
+     * @see Character#DIRECTIONALITY_FIRST_STRONG_ISOLATE
+     * @see Character#DIRECTIONALITY_POP_DIRECTIONAL_ISOLATE
      * @since 1.4
      */
     public static byte getDirectionality(char ch) {
@@ -7035,6 +9745,10 @@
      * @see Character#DIRECTIONALITY_RIGHT_TO_LEFT_EMBEDDING DIRECTIONALITY_RIGHT_TO_LEFT_EMBEDDING
      * @see Character#DIRECTIONALITY_RIGHT_TO_LEFT_OVERRIDE DIRECTIONALITY_RIGHT_TO_LEFT_OVERRIDE
      * @see Character#DIRECTIONALITY_POP_DIRECTIONAL_FORMAT DIRECTIONALITY_POP_DIRECTIONAL_FORMAT
+     * @see Character#DIRECTIONALITY_LEFT_TO_RIGHT_ISOLATE DIRECTIONALITY_LEFT_TO_RIGHT_ISOLATE
+     * @see Character#DIRECTIONALITY_RIGHT_TO_LEFT_ISOLATE DIRECTIONALITY_RIGHT_TO_LEFT_ISOLATE
+     * @see Character#DIRECTIONALITY_FIRST_STRONG_ISOLATE DIRECTIONALITY_FIRST_STRONG_ISOLATE
+     * @see Character#DIRECTIONALITY_POP_DIRECTIONAL_ISOLATE DIRECTIONALITY_POP_DIRECTIONAL_ISOLATE
      * @since    1.5
      */
     public static byte getDirectionality(int codePoint) {
@@ -7181,6 +9895,7 @@
      *     the bytes in the specified <tt>char</tt> value.
      * @since 1.5
      */
+    @HotSpotIntrinsicCandidate
     public static char reverseBytes(char ch) {
         return (char) (((ch & 0xFF00) >> 8) | (ch << 8));
     }
--- a/jdk/src/java.base/share/classes/java/lang/Class.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/Class.java	Wed Jul 05 20:42:36 2017 +0200
@@ -56,6 +56,7 @@
 import java.util.Objects;
 import java.util.StringJoiner;
 import sun.misc.Unsafe;
+import jdk.internal.HotSpotIntrinsicCandidate;
 import sun.reflect.CallerSensitive;
 import sun.reflect.ConstantPool;
 import sun.reflect.Reflection;
@@ -502,6 +503,7 @@
      *
      * @since 1.1
      */
+    @HotSpotIntrinsicCandidate
     public native boolean isInstance(Object obj);
 
 
@@ -529,6 +531,7 @@
      *            null.
      * @since 1.1
      */
+    @HotSpotIntrinsicCandidate
     public native boolean isAssignableFrom(Class<?> cls);
 
 
@@ -539,6 +542,7 @@
      * @return  {@code true} if this object represents an interface;
      *          {@code false} otherwise.
      */
+    @HotSpotIntrinsicCandidate
     public native boolean isInterface();
 
 
@@ -549,6 +553,7 @@
      *          {@code false} otherwise.
      * @since   1.1
      */
+    @HotSpotIntrinsicCandidate
     public native boolean isArray();
 
 
@@ -580,6 +585,7 @@
      * @see     java.lang.Void#TYPE
      * @since 1.1
      */
+    @HotSpotIntrinsicCandidate
     public native boolean isPrimitive();
 
     /**
@@ -751,6 +757,7 @@
      *
      * @return the direct superclass of the class represented by this object
      */
+    @HotSpotIntrinsicCandidate
     public native Class<? super T> getSuperclass();
 
 
@@ -984,6 +991,7 @@
      * @see     java.lang.reflect.Modifier
      * @since 1.1
      */
+    @HotSpotIntrinsicCandidate
     public native int getModifiers();
 
 
@@ -3382,6 +3390,7 @@
      * @since 1.5
      */
     @SuppressWarnings("unchecked")
+    @HotSpotIntrinsicCandidate
     public T cast(Object obj) {
         if (obj != null && !isInstance(obj))
             throw new ClassCastException(cannotCastMsg(obj));
--- a/jdk/src/java.base/share/classes/java/lang/Double.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/Double.java	Wed Jul 05 20:42:36 2017 +0200
@@ -27,6 +27,7 @@
 
 import sun.misc.FloatingDecimal;
 import sun.misc.DoubleConsts;
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 /**
  * The {@code Double} class wraps a value of the primitive type
@@ -514,6 +515,7 @@
      * @return a {@code Double} instance representing {@code d}.
      * @since  1.5
      */
+    @HotSpotIntrinsicCandidate
     public static Double valueOf(double d) {
         return new Double(d);
     }
@@ -711,6 +713,7 @@
      *
      * @return the {@code double} value represented by this object
      */
+    @HotSpotIntrinsicCandidate
     public double doubleValue() {
         return value;
     }
@@ -831,6 +834,7 @@
      * @param   value   a {@code double} precision floating-point number.
      * @return the bits that represent the floating-point number.
      */
+    @HotSpotIntrinsicCandidate
     public static long doubleToLongBits(double value) {
         if (!isNaN(value)) {
             return doubleToRawLongBits(value);
@@ -874,6 +878,7 @@
      * @return the bits that represent the floating-point number.
      * @since 1.3
      */
+    @HotSpotIntrinsicCandidate
     public static native long doubleToRawLongBits(double value);
 
     /**
@@ -937,6 +942,7 @@
      * @return  the {@code double} floating-point value with the same
      *          bit pattern.
      */
+    @HotSpotIntrinsicCandidate
     public static native double longBitsToDouble(long bits);
 
     /**
--- a/jdk/src/java.base/share/classes/java/lang/Float.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/Float.java	Wed Jul 05 20:42:36 2017 +0200
@@ -28,6 +28,7 @@
 import sun.misc.FloatingDecimal;
 import sun.misc.FloatConsts;
 import sun.misc.DoubleConsts;
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 /**
  * The {@code Float} class wraps a value of primitive type
@@ -429,6 +430,7 @@
      * @return a {@code Float} instance representing {@code f}.
      * @since  1.5
      */
+    @HotSpotIntrinsicCandidate
     public static Float valueOf(float f) {
         return new Float(f);
     }
@@ -622,6 +624,7 @@
      *
      * @return the {@code float} value represented by this object
      */
+    @HotSpotIntrinsicCandidate
     public float floatValue() {
         return value;
     }
@@ -740,6 +743,7 @@
      * @param   value   a floating-point number.
      * @return the bits that represent the floating-point number.
      */
+    @HotSpotIntrinsicCandidate
     public static int floatToIntBits(float value) {
         if (!isNaN(value)) {
             return floatToRawIntBits(value);
@@ -782,6 +786,7 @@
      * @return the bits that represent the floating-point number.
      * @since 1.3
      */
+    @HotSpotIntrinsicCandidate
     public static native int floatToRawIntBits(float value);
 
     /**
@@ -843,6 +848,7 @@
      * @return  the {@code float} floating-point value with the same bit
      *          pattern.
      */
+    @HotSpotIntrinsicCandidate
     public static native float intBitsToFloat(int bits);
 
     /**
--- a/jdk/src/java.base/share/classes/java/lang/Integer.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/Integer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -27,6 +27,7 @@
 
 import java.lang.annotation.Native;
 import java.util.Objects;
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 /**
  * The {@code Integer} class wraps a value of the primitive type
@@ -395,6 +396,7 @@
      * @param   i   an integer to be converted.
      * @return  a string representation of the argument in base&nbsp;10.
      */
+    @HotSpotIntrinsicCandidate
     public static String toString(int i) {
         if (i == Integer.MIN_VALUE)
             return "-2147483648";
@@ -972,6 +974,7 @@
      * @return an {@code Integer} instance representing {@code i}.
      * @since  1.5
      */
+    @HotSpotIntrinsicCandidate
     public static Integer valueOf(int i) {
         if (i >= IntegerCache.low && i <= IntegerCache.high)
             return IntegerCache.cache[i + (-IntegerCache.low)];
@@ -1035,6 +1038,7 @@
      * Returns the value of this {@code Integer} as an
      * {@code int}.
      */
+    @HotSpotIntrinsicCandidate
     public int intValue() {
         return value;
     }
@@ -1538,6 +1542,7 @@
      *     is equal to zero.
      * @since 1.5
      */
+    @HotSpotIntrinsicCandidate
     public static int numberOfLeadingZeros(int i) {
         // HD, Figure 5-6
         if (i == 0)
@@ -1565,6 +1570,7 @@
      *     to zero.
      * @since 1.5
      */
+    @HotSpotIntrinsicCandidate
     public static int numberOfTrailingZeros(int i) {
         // HD, Figure 5-14
         int y;
@@ -1587,6 +1593,7 @@
      *     representation of the specified {@code int} value.
      * @since 1.5
      */
+    @HotSpotIntrinsicCandidate
     public static int bitCount(int i) {
         // HD, Figure 5-2
         i = i - ((i >>> 1) & 0x55555555);
@@ -1688,6 +1695,7 @@
      *     {@code int} value.
      * @since 1.5
      */
+    @HotSpotIntrinsicCandidate
     public static int reverseBytes(int i) {
         return ((i >>> 24)           ) |
                ((i >>   8) &   0xFF00) |
--- a/jdk/src/java.base/share/classes/java/lang/Long.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/Long.java	Wed Jul 05 20:42:36 2017 +0200
@@ -28,6 +28,7 @@
 import java.lang.annotation.Native;
 import java.math.*;
 import java.util.Objects;
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 
 /**
@@ -1074,6 +1075,7 @@
      * @return a {@code Long} instance representing {@code l}.
      * @since  1.5
      */
+    @HotSpotIntrinsicCandidate
     public static Long valueOf(long l) {
         final int offset = 128;
         if (l >= -128 && l <= 127) { // will cache
@@ -1238,6 +1240,7 @@
      * Returns the value of this {@code Long} as a
      * {@code long} value.
      */
+    @HotSpotIntrinsicCandidate
     public long longValue() {
         return value;
     }
@@ -1655,6 +1658,7 @@
      *     is equal to zero.
      * @since 1.5
      */
+    @HotSpotIntrinsicCandidate
     public static int numberOfLeadingZeros(long i) {
         // HD, Figure 5-6
          if (i == 0)
@@ -1684,6 +1688,7 @@
      *     to zero.
      * @since 1.5
      */
+    @HotSpotIntrinsicCandidate
     public static int numberOfTrailingZeros(long i) {
         // HD, Figure 5-14
         int x, y;
@@ -1707,6 +1712,7 @@
      *     representation of the specified {@code long} value.
      * @since 1.5
      */
+     @HotSpotIntrinsicCandidate
      public static int bitCount(long i) {
         // HD, Figure 5-2
         i = i - ((i >>> 1) & 0x5555555555555555L);
@@ -1810,6 +1816,7 @@
      *     {@code long} value.
      * @since 1.5
      */
+    @HotSpotIntrinsicCandidate
     public static long reverseBytes(long i) {
         i = (i & 0x00ff00ff00ff00ffL) << 8 | (i >>> 8) & 0x00ff00ff00ff00ffL;
         return (i << 48) | ((i & 0xffff0000L) << 16) |
--- a/jdk/src/java.base/share/classes/java/lang/Math.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/Math.java	Wed Jul 05 20:42:36 2017 +0200
@@ -24,10 +24,11 @@
  */
 
 package java.lang;
+
 import java.util.Random;
-
 import sun.misc.FloatConsts;
 import sun.misc.DoubleConsts;
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 /**
  * The class {@code Math} contains methods for performing basic
@@ -147,6 +148,7 @@
      * @param   a   an angle, in radians.
      * @return  the sine of the argument.
      */
+    @HotSpotIntrinsicCandidate
     public static double sin(double a) {
         return StrictMath.sin(a); // default impl. delegates to StrictMath
     }
@@ -162,6 +164,7 @@
      * @param   a   an angle, in radians.
      * @return  the cosine of the argument.
      */
+    @HotSpotIntrinsicCandidate
     public static double cos(double a) {
         return StrictMath.cos(a); // default impl. delegates to StrictMath
     }
@@ -179,6 +182,7 @@
      * @param   a   an angle, in radians.
      * @return  the tangent of the argument.
      */
+    @HotSpotIntrinsicCandidate
     public static double tan(double a) {
         return StrictMath.tan(a); // default impl. delegates to StrictMath
     }
@@ -280,6 +284,7 @@
      * @return  the value <i>e</i><sup>{@code a}</sup>,
      *          where <i>e</i> is the base of the natural logarithms.
      */
+    @HotSpotIntrinsicCandidate
     public static double exp(double a) {
         return StrictMath.exp(a); // default impl. delegates to StrictMath
     }
@@ -301,6 +306,7 @@
      * @return  the value ln&nbsp;{@code a}, the natural logarithm of
      *          {@code a}.
      */
+    @HotSpotIntrinsicCandidate
     public static double log(double a) {
         return StrictMath.log(a); // default impl. delegates to StrictMath
     }
@@ -326,6 +332,7 @@
      * @return  the base 10 logarithm of  {@code a}.
      * @since 1.5
      */
+    @HotSpotIntrinsicCandidate
     public static double log10(double a) {
         return StrictMath.log10(a); // default impl. delegates to StrictMath
     }
@@ -347,6 +354,7 @@
      * @return  the positive square root of {@code a}.
      *          If the argument is NaN or less than zero, the result is NaN.
      */
+    @HotSpotIntrinsicCandidate
     public static double sqrt(double a) {
         return StrictMath.sqrt(a); // default impl. delegates to StrictMath
                                    // Note that hardware sqrt instructions
@@ -525,6 +533,7 @@
      *          in polar coordinates that corresponds to the point
      *          (<i>x</i>,&nbsp;<i>y</i>) in Cartesian coordinates.
      */
+    @HotSpotIntrinsicCandidate
     public static double atan2(double y, double x) {
         return StrictMath.atan2(y, x); // default impl. delegates to StrictMath
     }
@@ -652,6 +661,7 @@
      * @param   b   the exponent.
      * @return  the value {@code a}<sup>{@code b}</sup>.
      */
+    @HotSpotIntrinsicCandidate
     public static double pow(double a, double b) {
         return StrictMath.pow(a, b); // default impl. delegates to StrictMath
     }
@@ -806,6 +816,7 @@
      * @throws ArithmeticException if the result overflows an int
      * @since 1.8
      */
+    @HotSpotIntrinsicCandidate
     public static int addExact(int x, int y) {
         int r = x + y;
         // HD 2-12 Overflow iff both arguments have the opposite sign of the result
@@ -825,6 +836,7 @@
      * @throws ArithmeticException if the result overflows a long
      * @since 1.8
      */
+    @HotSpotIntrinsicCandidate
     public static long addExact(long x, long y) {
         long r = x + y;
         // HD 2-12 Overflow iff both arguments have the opposite sign of the result
@@ -844,6 +856,7 @@
      * @throws ArithmeticException if the result overflows an int
      * @since 1.8
      */
+    @HotSpotIntrinsicCandidate
     public static int subtractExact(int x, int y) {
         int r = x - y;
         // HD 2-12 Overflow iff the arguments have different signs and
@@ -864,6 +877,7 @@
      * @throws ArithmeticException if the result overflows a long
      * @since 1.8
      */
+    @HotSpotIntrinsicCandidate
     public static long subtractExact(long x, long y) {
         long r = x - y;
         // HD 2-12 Overflow iff the arguments have different signs and
@@ -884,6 +898,7 @@
      * @throws ArithmeticException if the result overflows an int
      * @since 1.8
      */
+    @HotSpotIntrinsicCandidate
     public static int multiplyExact(int x, int y) {
         long r = (long)x * (long)y;
         if ((int)r != r) {
@@ -902,6 +917,7 @@
      * @throws ArithmeticException if the result overflows a long
      * @since 1.8
      */
+    @HotSpotIntrinsicCandidate
     public static long multiplyExact(long x, long y) {
         long r = x * y;
         long ax = Math.abs(x);
@@ -927,6 +943,7 @@
      * @throws ArithmeticException if the result overflows an int
      * @since 1.8
      */
+    @HotSpotIntrinsicCandidate
     public static int incrementExact(int a) {
         if (a == Integer.MAX_VALUE) {
             throw new ArithmeticException("integer overflow");
@@ -944,6 +961,7 @@
      * @throws ArithmeticException if the result overflows a long
      * @since 1.8
      */
+    @HotSpotIntrinsicCandidate
     public static long incrementExact(long a) {
         if (a == Long.MAX_VALUE) {
             throw new ArithmeticException("long overflow");
@@ -961,6 +979,7 @@
      * @throws ArithmeticException if the result overflows an int
      * @since 1.8
      */
+    @HotSpotIntrinsicCandidate
     public static int decrementExact(int a) {
         if (a == Integer.MIN_VALUE) {
             throw new ArithmeticException("integer overflow");
@@ -978,6 +997,7 @@
      * @throws ArithmeticException if the result overflows a long
      * @since 1.8
      */
+    @HotSpotIntrinsicCandidate
     public static long decrementExact(long a) {
         if (a == Long.MIN_VALUE) {
             throw new ArithmeticException("long overflow");
@@ -995,6 +1015,7 @@
      * @throws ArithmeticException if the result overflows an int
      * @since 1.8
      */
+    @HotSpotIntrinsicCandidate
     public static int negateExact(int a) {
         if (a == Integer.MIN_VALUE) {
             throw new ArithmeticException("integer overflow");
@@ -1012,6 +1033,7 @@
      * @throws ArithmeticException if the result overflows a long
      * @since 1.8
      */
+    @HotSpotIntrinsicCandidate
     public static long negateExact(long a) {
         if (a == Long.MIN_VALUE) {
             throw new ArithmeticException("long overflow");
@@ -1256,6 +1278,7 @@
      * @param   a   the argument whose absolute value is to be determined
      * @return  the absolute value of the argument.
      */
+    @HotSpotIntrinsicCandidate
     public static double abs(double a) {
         return (a <= 0.0D) ? 0.0D - a : a;
     }
@@ -1270,6 +1293,7 @@
      * @param   b   another argument.
      * @return  the larger of {@code a} and {@code b}.
      */
+    @HotSpotIntrinsicCandidate
     public static int max(int a, int b) {
         return (a >= b) ? a : b;
     }
@@ -1354,6 +1378,7 @@
      * @param   b   another argument.
      * @return  the smaller of {@code a} and {@code b}.
      */
+    @HotSpotIntrinsicCandidate
     public static int min(int a, int b) {
         return (a <= b) ? a : b;
     }
--- a/jdk/src/java.base/share/classes/java/lang/Object.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/Object.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,6 +25,8 @@
 
 package java.lang;
 
+import jdk.internal.HotSpotIntrinsicCandidate;
+
 /**
  * Class {@code Object} is the root of the class hierarchy.
  * Every class has {@code Object} as a superclass. All objects,
@@ -44,6 +46,7 @@
     /**
      * Constructs a new object.
      */
+    @HotSpotIntrinsicCandidate
     public Object() {}
 
     /**
@@ -65,6 +68,7 @@
      *         class of this object.
      * @jls 15.8.2 Class Literals
      */
+    @HotSpotIntrinsicCandidate
     public final native Class<?> getClass();
 
     /**
@@ -101,6 +105,7 @@
      * @see     java.lang.Object#equals(java.lang.Object)
      * @see     java.lang.System#identityHashCode
      */
+    @HotSpotIntrinsicCandidate
     public native int hashCode();
 
     /**
@@ -213,6 +218,7 @@
      *               be cloned.
      * @see java.lang.Cloneable
      */
+    @HotSpotIntrinsicCandidate
     protected native Object clone() throws CloneNotSupportedException;
 
     /**
--- a/jdk/src/java.base/share/classes/java/lang/ProcessHandle.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/ProcessHandle.java	Wed Jul 05 20:42:36 2017 +0200
@@ -78,6 +78,16 @@
  * The methods of this class throw {@link java.lang.UnsupportedOperationException}
  * if the operating system does not allow access to query or kill a process.
  *
+ * <p>
+ * The {@code ProcessHandle} static factory methods return instances that are
+ * <a href="{@docRoot}/java/lang/doc-files/ValueBased.html">value-based</a>,
+ * immutable and thread-safe.
+ * Use of identity-sensitive operations (including reference equality
+ * ({@code ==}), identity hash code, or synchronization) on these instances of
+ * {@code ProcessHandle} may have unpredictable results and should be avoided.
+ * Use {@link #equals(Object) equals} or
+ * {@link #compareTo(ProcessHandle) compareTo} methods to compare ProcessHandles.
+ *
  * @see Process
  * @since 1.9
  */
@@ -86,6 +96,9 @@
     /**
      * Returns the native process ID of the process. The native process ID is an
      * identification number that the operating system assigns to the process.
+     * The operating system may reuse the process ID after a process terminates.
+     * Use {@link #equals(Object) equals} or
+     * {@link #compareTo(ProcessHandle) compareTo} to compare ProcessHandles.
      *
      * @return the native process ID of the process
      * @throws UnsupportedOperationException if the implementation
@@ -337,7 +350,43 @@
      * @return {@code true} if the process represented by this
      *         {@code ProcessHandle} object has not yet terminated
      */
-   boolean isAlive();
+    boolean isAlive();
+
+    /**
+     * Returns a hash code value for this ProcessHandle.
+     * The hashcode value follows the general contract for {@link Object#hashCode()}.
+     * The value is a function of the {@link #getPid getPid()} value and
+     * may be a function of additional information to uniquely identify the process.
+     * If two ProcessHandles are equal according to the {@link #equals(Object) equals}
+     * method, then calling the hashCode method on each of the two objects
+     * must produce the same integer result.
+     *
+     * @return a hash code value for this object
+     */
+    @Override
+    int hashCode();
+
+    /**
+     * Returns {@code true} if {@code other} object is non-null, is of the
+     * same implementation, and represents the same system process;
+     * otherwise it returns {@code false}.
+     * @implNote
+     * It is implementation specific whether ProcessHandles with the same PID
+     * represent the same system process. ProcessHandle implementations
+     * should contain additional information to uniquely identify the process.
+     * For example, the start time of the process could be used
+     * to determine if the PID has been re-used.
+     * The implementation of {@code equals} should return {@code true} for two
+     * ProcessHandles with the same PID unless there is information to
+     * distinguish them.
+     *
+     * @param other another object
+     * @return {@code true} if the {@code other} object is non-null,
+     *         is of the same implementation class and represents
+     *         the same system process; otherwise returns {@code false}
+     */
+    @Override
+    boolean equals(Object other);
 
     /**
      * Compares this ProcessHandle with the specified ProcessHandle for order.
--- a/jdk/src/java.base/share/classes/java/lang/ProcessHandleImpl.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/ProcessHandleImpl.java	Wed Jul 05 20:42:36 2017 +0200
@@ -39,6 +39,7 @@
 import java.util.concurrent.ThreadFactory;
 import java.util.concurrent.ThreadPoolExecutor;
 import java.util.concurrent.TimeUnit;
+import java.util.stream.IntStream;
 import java.util.stream.Stream;
 
 import sun.misc.InnocuousThread;
@@ -52,6 +53,24 @@
  * @since 1.9
  */
 final class ProcessHandleImpl implements ProcessHandle {
+    /**
+     * Cache the ProcessHandle of this process.
+     */
+    private static final ProcessHandleImpl current;
+
+    /**
+     * Map of pids to ExitCompletions.
+     */
+    private static final ConcurrentMap<Long, ExitCompletion>
+            completions = new ConcurrentHashMap<>();
+
+    static {
+        initNative();
+        long pid = getCurrentPid0();
+        current = new ProcessHandleImpl(pid, isAlive0(pid));
+    }
+
+    private static native void initNative();
 
     /**
      * The thread pool of "process reaper" daemon threads.
@@ -84,9 +103,6 @@
         }
     }
 
-    private static final ConcurrentMap<Long, ExitCompletion>
-        completions = new ConcurrentHashMap<>();
-
     /**
      * Returns a CompletableFuture that completes with process exit status when
      * the process completes.
@@ -142,22 +158,33 @@
     private static native int waitForProcessExit0(long pid, boolean reapvalue);
 
     /**
-     * Cache the ProcessHandle of this process.
-     */
-    private static final ProcessHandleImpl current =
-            new ProcessHandleImpl(getCurrentPid0());
-
-    /**
      * The pid of this ProcessHandle.
      */
     private final long pid;
 
     /**
+     * The start time of this process.
+     * If STARTTIME_ANY, the start time of the process is not available from the os.
+     * If greater than zero, the start time of the process.
+     */
+    private final long startTime;
+
+    /* The start time should match any value.
+     * Typically, this is because the OS can not supply it.
+     * The process is known to exist but not the exact start time.
+     */
+    private final long STARTTIME_ANY = 0L;
+
+    /* The start time of a Process that does not exist. */
+    private final long STARTTIME_PROCESS_UNKNOWN = -1;
+
+    /**
      * Private constructor.  Instances are created by the {@code get(long)} factory.
      * @param pid the pid for this instance
      */
-    private ProcessHandleImpl(long pid) {
+    private ProcessHandleImpl(long pid, long startTime) {
         this.pid = pid;
+        this.startTime = startTime;
     }
 
     /**
@@ -173,17 +200,21 @@
         if (sm != null) {
             sm.checkPermission(new RuntimePermission("manageProcess"));
         }
-        return Optional.ofNullable(isAlive0(pid) ? new ProcessHandleImpl(pid) : null);
+        long start = isAlive0(pid);
+        return (start >= 0)
+                ? Optional.of(new ProcessHandleImpl(pid, start))
+                : Optional.empty();
     }
 
     /**
-     * Returns a ProcessHandle corresponding known to exist pid.
-     * Called from ProcessImpl, it does not perform a security check or check if the process is alive.
+     * Returns a ProcessHandle for an existing native process known to be alive.
+     * The startTime of the process is retrieved and stored in the ProcessHandle.
+     * It does not perform a security check since it is called from ProcessImpl.
      * @param pid of the known to exist process
      * @return a ProcessHandle corresponding to an existing Process instance
      */
-    static ProcessHandle getUnchecked(long pid) {
-        return new ProcessHandleImpl(pid);
+    static ProcessHandleImpl getInternal(long pid) {
+        return new ProcessHandleImpl(pid, isAlive0(pid));
     }
 
     /**
@@ -227,12 +258,12 @@
      * @throws SecurityException           if permission is not granted by the
      *                                     security policy
      */
-    static Optional<ProcessHandle> parent(long pid) {
+    public Optional<ProcessHandle> parent() {
         SecurityManager sm = System.getSecurityManager();
         if (sm != null) {
             sm.checkPermission(new RuntimePermission("manageProcess"));
         }
-        long ppid = parent0(pid);
+        long ppid = parent0(pid, startTime);
         if (ppid <= 0) {
             return Optional.empty();
         }
@@ -242,9 +273,11 @@
     /**
      * Returns the parent of the native pid argument.
      *
+     * @param pid the process id
+     * @param startTime the startTime of the process
      * @return the parent of the native pid; if any, otherwise -1
      */
-    private static native long parent0(long pid);
+    private static native long parent0(long pid, long startTime);
 
     /**
      * Returns the number of pids filled in to the array.
@@ -252,37 +285,46 @@
      *      otherwise only direct child process pids are returned
      * @param pids an allocated long array to receive the pids
      * @param ppids an allocated long array to receive the parent pids; may be null
+     * @param starttimes an allocated long array to receive the child start times; may be null
      * @return if greater than or equals to zero is the number of pids in the array;
      *      if greater than the length of the arrays, the arrays are too small
      */
-    private static native int getProcessPids0(long pid, long[] pids, long[] ppids);
+    private static native int getProcessPids0(long pid, long[] pids,
+                                              long[] ppids, long[] starttimes);
 
     /**
      * Destroy the process for this ProcessHandle.
-     * @param pid the processs ID to destroy
+     * The native code checks the start time before sending the termination request.
+     *
      * @param force {@code true} if the process should be terminated forcibly;
      *     else {@code false} for a normal termination
      */
-    static void destroyProcess(long pid, boolean force) {
-        destroy0(pid, force);
+    boolean destroyProcess(boolean force) {
+        if (this.equals(current)) {
+            throw new IllegalStateException("destroy of current process not allowed");
+        }
+        return destroy0(pid, startTime, force);
     }
 
-    private static native boolean destroy0(long pid, boolean forcibly);
+    /**
+      * Signal the process to terminate.
+      * The process is signaled only if its start time matches the known start time.
+      *
+      * @param pid  process id to kill
+      * @param startTime the start time of the process
+      * @param forcibly true to forcibly terminate (SIGKILL vs SIGTERM)
+      * @return true if the process was signaled without error; false otherwise
+      */
+    private static native boolean destroy0(long pid, long startTime, boolean forcibly);
 
     @Override
     public boolean destroy() {
-        if (this.equals(current)) {
-            throw new IllegalStateException("destroy of current process not allowed");
-        }
-        return destroy0(getPid(), false);
+        return destroyProcess(false);
     }
 
     @Override
     public boolean destroyForcibly() {
-        if (this.equals(current)) {
-            throw new IllegalStateException("destroy of current process not allowed");
-        }
-        return destroy0(getPid(), true);
+        return destroyProcess(true);
     }
 
 
@@ -300,22 +342,20 @@
      */
     @Override
     public boolean isAlive() {
-        return isAlive0(pid);
+        long start = isAlive0(pid);
+        return (start >= 0 && (start == startTime || start == 0 || startTime == 0));
     }
 
     /**
-     * Returns true or false depending on whether the pid is alive.
-     * This must not reap the exitValue like the isAlive method above.
+     * Returns the process start time depending on whether the pid is alive.
+     * This must not reap the exitValue.
      *
      * @param pid the pid to check
-     * @return true or false
+     * @return the start time in milliseconds since 1970,
+     *         0 if the start time cannot be determined,
+     *         -1 if the pid does not exist.
      */
-    private static native boolean isAlive0(long pid);
-
-    @Override
-    public Optional<ProcessHandle> parent() {
-        return parent(pid);
-    }
+    private static native long isAlive0(long pid);
 
     @Override
     public Stream<ProcessHandle> children() {
@@ -336,11 +376,16 @@
         }
         int size = 100;
         long[] childpids = null;
+        long[] starttimes = null;
         while (childpids == null || size > childpids.length) {
             childpids = new long[size];
-            size = getProcessPids0(pid, childpids, null);
+            starttimes = new long[size];
+            size = getProcessPids0(pid, childpids, null, starttimes);
         }
-        return Arrays.stream(childpids, 0, size).mapToObj((id) -> new ProcessHandleImpl(id));
+
+        final long[] cpids = childpids;
+        final long[] stimes = starttimes;
+        return IntStream.range(0, size).mapToObj(i -> new ProcessHandleImpl(cpids[i], stimes[i]));
     }
 
     @Override
@@ -352,10 +397,12 @@
         int size = 100;
         long[] pids = null;
         long[] ppids = null;
+        long[] starttimes = null;
         while (pids == null || size > pids.length) {
             pids = new long[size];
             ppids = new long[size];
-            size = getProcessPids0(0, pids, ppids);
+            starttimes = new long[size];
+            size = getProcessPids0(0, pids, ppids, starttimes);
         }
 
         int next = 0;       // index of next process to check
@@ -368,13 +415,16 @@
                 if (ppids[i] == ppid) {
                     swap(pids, i, next);
                     swap(ppids, i, next);
+                    swap(starttimes, i, next);
                     next++;
                 }
             }
             ppid = pids[++count];   // pick up the next pid to scan for
         } while (count < next);
 
-        return Arrays.stream(pids, 0, count).mapToObj((id) -> new ProcessHandleImpl(id));
+        final long[] cpids = pids;
+        final long[] stimes = starttimes;
+        return IntStream.range(0, count).mapToObj(i -> new ProcessHandleImpl(cpids[i], stimes[i]));
     }
 
     // Swap two elements in an array
@@ -386,7 +436,7 @@
 
     @Override
     public ProcessHandle.Info info() {
-        return ProcessHandleImpl.Info.info(pid);
+        return ProcessHandleImpl.Info.info(pid, startTime);
     }
 
     @Override
@@ -406,8 +456,17 @@
 
     @Override
     public boolean equals(Object obj) {
-        return (obj instanceof ProcessHandleImpl) &&
-            (pid == ((ProcessHandleImpl) obj).pid);
+        if (this == obj) {
+            return true;
+        }
+        if (obj instanceof ProcessHandleImpl) {
+            ProcessHandleImpl other = (ProcessHandleImpl) obj;
+            return (pid == other.pid) &&
+                    (startTime == other.startTime
+                        || startTime == 0
+                        || other.startTime == 0);
+        }
+        return false;
     }
 
     /**
@@ -453,14 +512,24 @@
         /**
          * Returns the Info object with the fields from the process.
          * Whatever fields are provided by native are returned.
+         * If the startTime of the process does not match the provided
+         * startTime then an empty Info is returned.
          *
          * @param pid the native process identifier
+         * @param startTime the startTime of the process being queried
          * @return ProcessHandle.Info non-null; individual fields may be null
          *          or -1 if not available.
          */
-        public static ProcessHandle.Info info(long pid) {
+        public static ProcessHandle.Info info(long pid, long startTime) {
             Info info = new Info();
             info.info0(pid);
+            if (startTime != info.startTime) {
+                info.command = null;
+                info.arguments = null;
+                info.startTime = -1L;
+                info.totalTime = -1L;
+                info.user = null;
+            }
             return info;
         }
 
@@ -511,7 +580,7 @@
                 sb.append("args: ");
                 sb.append(Arrays.toString(arguments));
             }
-            if (startTime != -1) {
+            if (startTime > 0) {
                 if (sb.length() != 0) sb.append(", ");
                 sb.append("startTime: ");
                 sb.append(startInstant());
--- a/jdk/src/java.base/share/classes/java/lang/Short.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/Short.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,6 +25,8 @@
 
 package java.lang;
 
+import jdk.internal.HotSpotIntrinsicCandidate;
+
 /**
  * The {@code Short} class wraps a value of primitive type {@code
  * short} in an object.  An object of type {@code Short} contains a
@@ -227,6 +229,7 @@
      * @return a {@code Short} instance representing {@code s}.
      * @since  1.5
      */
+    @HotSpotIntrinsicCandidate
     public static Short valueOf(short s) {
         final int offset = 128;
         int sAsInt = s;
@@ -334,6 +337,7 @@
      * Returns the value of this {@code Short} as a
      * {@code short}.
      */
+    @HotSpotIntrinsicCandidate
     public short shortValue() {
         return value;
     }
@@ -487,6 +491,7 @@
      *     the bytes in the specified {@code short} value.
      * @since 1.5
      */
+    @HotSpotIntrinsicCandidate
     public static short reverseBytes(short i) {
         return (short) (((i & 0xFF00) >> 8) | (i << 8));
     }
--- a/jdk/src/java.base/share/classes/java/lang/StrictMath.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/StrictMath.java	Wed Jul 05 20:42:36 2017 +0200
@@ -24,8 +24,10 @@
  */
 
 package java.lang;
+
 import java.util.Random;
 import sun.misc.DoubleConsts;
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 /**
  * The class {@code StrictMath} contains methods for performing basic
@@ -243,7 +245,6 @@
      */
     public static native double log(double a);
 
-
     /**
      * Returns the base 10 logarithm of a {@code double} value.
      * Special cases:
@@ -280,6 +281,7 @@
      * @param   a   a value.
      * @return  the positive square root of {@code a}.
      */
+    @HotSpotIntrinsicCandidate
     public static native double sqrt(double a);
 
     /**
@@ -521,7 +523,6 @@
      */
     public static native double atan2(double y, double x);
 
-
     /**
      * Returns the value of the first argument raised to the power of the
      * second argument. Special cases:
@@ -1009,6 +1010,7 @@
      * @param   b   another argument.
      * @return  the larger of {@code a} and {@code b}.
      */
+    @HotSpotIntrinsicCandidate
     public static int max(int a, int b) {
         return Math.max(a, b);
     }
@@ -1073,6 +1075,7 @@
      * @param   b   another argument.
      * @return  the smaller of {@code a} and {@code b}.
      */
+    @HotSpotIntrinsicCandidate
     public static int min(int a, int b) {
         return Math.min(a, b);
     }
--- a/jdk/src/java.base/share/classes/java/lang/String.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/String.java	Wed Jul 05 20:42:36 2017 +0200
@@ -42,6 +42,7 @@
 import java.util.regex.PatternSyntaxException;
 import java.util.stream.IntStream;
 import java.util.stream.StreamSupport;
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 /**
  * The {@code String} class represents character strings. All
@@ -152,6 +153,7 @@
      * @param  original
      *         A {@code String}
      */
+    @HotSpotIntrinsicCandidate
     public String(String original) {
         this.value = original.value;
         this.hash = original.hash;
@@ -978,6 +980,7 @@
      * @see  #compareTo(String)
      * @see  #equalsIgnoreCase(String)
      */
+    @HotSpotIntrinsicCandidate
     public boolean equals(Object anObject) {
         if (this == anObject) {
             return true;
@@ -1154,6 +1157,7 @@
      *          value greater than {@code 0} if this string is
      *          lexicographically greater than the string argument.
      */
+    @HotSpotIntrinsicCandidate
     public int compareTo(String anotherString) {
         char[] v1 = value;
         char[] v2 = anotherString.value;
@@ -1696,6 +1700,7 @@
      * @return  the index of the first occurrence of the specified substring,
      *          or {@code -1} if there is no such occurrence.
      */
+    @HotSpotIntrinsicCandidate
     public int indexOf(String str) {
         return indexOf(str, 0);
     }
--- a/jdk/src/java.base/share/classes/java/lang/StringBuffer.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/StringBuffer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -26,6 +26,7 @@
 package java.lang;
 
 import java.util.Arrays;
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 /**
  * A thread-safe, mutable sequence of characters.
@@ -112,6 +113,7 @@
      * Constructs a string buffer with no characters in it and an
      * initial capacity of 16 characters.
      */
+    @HotSpotIntrinsicCandidate
     public StringBuffer() {
         super(16);
     }
@@ -124,6 +126,7 @@
      * @exception  NegativeArraySizeException  if the {@code capacity}
      *               argument is less than {@code 0}.
      */
+    @HotSpotIntrinsicCandidate
     public StringBuffer(int capacity) {
         super(capacity);
     }
@@ -135,6 +138,7 @@
      *
      * @param   str   the initial contents of the buffer.
      */
+    @HotSpotIntrinsicCandidate
     public StringBuffer(String str) {
         super(str.length() + 16);
         append(str);
@@ -271,6 +275,7 @@
     }
 
     @Override
+    @HotSpotIntrinsicCandidate
     public synchronized StringBuffer append(String str) {
         toStringCache = null;
         super.append(str);
@@ -382,6 +387,7 @@
     }
 
     @Override
+    @HotSpotIntrinsicCandidate
     public synchronized StringBuffer append(char c) {
         toStringCache = null;
         super.append(c);
@@ -389,6 +395,7 @@
     }
 
     @Override
+    @HotSpotIntrinsicCandidate
     public synchronized StringBuffer append(int i) {
         toStringCache = null;
         super.append(i);
@@ -670,6 +677,7 @@
     }
 
     @Override
+    @HotSpotIntrinsicCandidate
     public synchronized String toString() {
         if (toStringCache == null) {
             toStringCache = Arrays.copyOfRange(value, 0, count);
--- a/jdk/src/java.base/share/classes/java/lang/StringBuilder.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/StringBuilder.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,6 +25,7 @@
 
 package java.lang;
 
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 /**
  * A mutable sequence of characters.  This class provides an API compatible
@@ -85,6 +86,7 @@
      * Constructs a string builder with no characters in it and an
      * initial capacity of 16 characters.
      */
+    @HotSpotIntrinsicCandidate
     public StringBuilder() {
         super(16);
     }
@@ -97,6 +99,7 @@
      * @throws     NegativeArraySizeException  if the {@code capacity}
      *               argument is less than {@code 0}.
      */
+    @HotSpotIntrinsicCandidate
     public StringBuilder(int capacity) {
         super(capacity);
     }
@@ -108,6 +111,7 @@
      *
      * @param   str   the initial contents of the buffer.
      */
+    @HotSpotIntrinsicCandidate
     public StringBuilder(String str) {
         super(str.length() + 16);
         append(str);
@@ -132,6 +136,7 @@
     }
 
     @Override
+    @HotSpotIntrinsicCandidate
     public StringBuilder append(String str) {
         super.append(str);
         return this;
@@ -198,12 +203,14 @@
     }
 
     @Override
+    @HotSpotIntrinsicCandidate
     public StringBuilder append(char c) {
         super.append(c);
         return this;
     }
 
     @Override
+    @HotSpotIntrinsicCandidate
     public StringBuilder append(int i) {
         super.append(i);
         return this;
@@ -402,6 +409,7 @@
     }
 
     @Override
+    @HotSpotIntrinsicCandidate
     public String toString() {
         // Create a copy, don't share the array
         return new String(value, 0, count);
--- a/jdk/src/java.base/share/classes/java/lang/System.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/System.java	Wed Jul 05 20:42:36 2017 +0200
@@ -42,6 +42,7 @@
 import sun.reflect.Reflection;
 import sun.security.util.SecurityConstants;
 import sun.reflect.annotation.AnnotationType;
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 /**
  * The <code>System</code> class contains several useful class fields
@@ -349,6 +350,7 @@
      *          the current time and midnight, January 1, 1970 UTC.
      * @see     java.util.Date
      */
+    @HotSpotIntrinsicCandidate
     public static native long currentTimeMillis();
 
     /**
@@ -392,6 +394,7 @@
      *         high-resolution time source, in nanoseconds
      * @since 1.5
      */
+    @HotSpotIntrinsicCandidate
     public static native long nanoTime();
 
     /**
@@ -486,6 +489,7 @@
      * @exception  NullPointerException if either <code>src</code> or
      *               <code>dest</code> is <code>null</code>.
      */
+    @HotSpotIntrinsicCandidate
     public static native void arraycopy(Object src,  int  srcPos,
                                         Object dest, int destPos,
                                         int length);
@@ -501,6 +505,7 @@
      * @return  the hashCode
      * @since   1.1
      */
+    @HotSpotIntrinsicCandidate
     public static native int identityHashCode(Object x);
 
     /**
--- a/jdk/src/java.base/share/classes/java/lang/Thread.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/Thread.java	Wed Jul 05 20:42:36 2017 +0200
@@ -40,7 +40,7 @@
 import sun.reflect.CallerSensitive;
 import sun.reflect.Reflection;
 import sun.security.util.SecurityConstants;
-
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 /**
  * A <i>thread</i> is a thread of execution in a program. The Java
@@ -261,6 +261,7 @@
      *
      * @return  the currently executing thread.
      */
+    @HotSpotIntrinsicCandidate
     public static native Thread currentThread();
 
     /**
@@ -966,6 +967,7 @@
      * is reset or not based on the value of ClearInterrupted that is
      * passed.
      */
+    @HotSpotIntrinsicCandidate
     private native boolean isInterrupted(boolean ClearInterrupted);
 
     /**
--- a/jdk/src/java.base/share/classes/java/lang/invoke/MethodHandle.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/invoke/MethodHandle.java	Wed Jul 05 20:42:36 2017 +0200
@@ -27,6 +27,7 @@
 
 
 import java.util.*;
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 import static java.lang.invoke.MethodHandleStatics.*;
 
@@ -476,6 +477,7 @@
      * @throws WrongMethodTypeException if the target's type is not identical with the caller's symbolic type descriptor
      * @throws Throwable anything thrown by the underlying method propagates unchanged through the method handle call
      */
+    @HotSpotIntrinsicCandidate
     public final native @PolymorphicSignature Object invokeExact(Object... args) throws Throwable;
 
     /**
@@ -513,6 +515,7 @@
      * @throws ClassCastException if the target's type can be adjusted to the caller, but a reference cast fails
      * @throws Throwable anything thrown by the underlying method propagates unchanged through the method handle call
      */
+    @HotSpotIntrinsicCandidate
     public final native @PolymorphicSignature Object invoke(Object... args) throws Throwable;
 
     /**
@@ -532,6 +535,7 @@
      * @param args the signature-polymorphic parameter list, statically represented using varargs
      * @return the signature-polymorphic result, statically represented using {@code Object}
      */
+    @HotSpotIntrinsicCandidate
     /*non-public*/ final native @PolymorphicSignature Object invokeBasic(Object... args) throws Throwable;
 
     /**
@@ -541,6 +545,7 @@
      * @param args the signature-polymorphic parameter list, statically represented using varargs
      * @return the signature-polymorphic result, statically represented using {@code Object}
      */
+    @HotSpotIntrinsicCandidate
     /*non-public*/ static native @PolymorphicSignature Object linkToVirtual(Object... args) throws Throwable;
 
     /**
@@ -550,6 +555,7 @@
      * @param args the signature-polymorphic parameter list, statically represented using varargs
      * @return the signature-polymorphic result, statically represented using {@code Object}
      */
+    @HotSpotIntrinsicCandidate
     /*non-public*/ static native @PolymorphicSignature Object linkToStatic(Object... args) throws Throwable;
 
     /**
@@ -559,6 +565,7 @@
      * @param args the signature-polymorphic parameter list, statically represented using varargs
      * @return the signature-polymorphic result, statically represented using {@code Object}
      */
+    @HotSpotIntrinsicCandidate
     /*non-public*/ static native @PolymorphicSignature Object linkToSpecial(Object... args) throws Throwable;
 
     /**
@@ -568,6 +575,7 @@
      * @param args the signature-polymorphic parameter list, statically represented using varargs
      * @return the signature-polymorphic result, statically represented using {@code Object}
      */
+    @HotSpotIntrinsicCandidate
     /*non-public*/ static native @PolymorphicSignature Object linkToInterface(Object... args) throws Throwable;
 
     /**
--- a/jdk/src/java.base/share/classes/java/lang/invoke/MethodHandleImpl.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/invoke/MethodHandleImpl.java	Wed Jul 05 20:42:36 2017 +0200
@@ -36,6 +36,7 @@
 import sun.invoke.util.ValueConversions;
 import sun.invoke.util.VerifyType;
 import sun.invoke.util.Wrapper;
+import jdk.internal.HotSpotIntrinsicCandidate;
 import sun.reflect.CallerSensitive;
 import sun.reflect.Reflection;
 import static java.lang.invoke.LambdaForm.*;
@@ -709,6 +710,7 @@
 
     // Intrinsified by C2. Counters are used during parsing to calculate branch frequencies.
     @LambdaForm.Hidden
+    @jdk.internal.HotSpotIntrinsicCandidate
     static
     boolean profileBoolean(boolean result, int[] counters) {
         // Profile is int[2] where [0] and [1] correspond to false and true occurrences respectively.
@@ -724,6 +726,7 @@
 
     // Intrinsified by C2. Returns true if obj is a compile-time constant.
     @LambdaForm.Hidden
+    @jdk.internal.HotSpotIntrinsicCandidate
     static
     boolean isCompileConstant(Object obj) {
         return false;
--- a/jdk/src/java.base/share/classes/java/lang/ref/Reference.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/ref/Reference.java	Wed Jul 05 20:42:36 2017 +0200
@@ -29,6 +29,7 @@
 import sun.misc.JavaLangRefAccess;
 import sun.misc.ManagedLocalsThread;
 import sun.misc.SharedSecrets;
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 /**
  * Abstract base class for reference objects.  This class defines the
@@ -251,6 +252,7 @@
      * @return   The object to which this reference refers, or
      *           <code>null</code> if this reference object has been cleared
      */
+    @HotSpotIntrinsicCandidate
     public T get() {
         return this.referent;
     }
--- a/jdk/src/java.base/share/classes/java/lang/reflect/Array.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/reflect/Array.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,6 +25,8 @@
 
 package java.lang.reflect;
 
+import jdk.internal.HotSpotIntrinsicCandidate;
+
 /**
  * The {@code Array} class provides static methods to dynamically create and
  * access Java arrays.
@@ -119,6 +121,7 @@
      * @exception IllegalArgumentException if the object argument is not
      * an array
      */
+    @HotSpotIntrinsicCandidate
     public static native int getLength(Object array)
         throws IllegalArgumentException;
 
@@ -477,6 +480,7 @@
      * Private
      */
 
+    @HotSpotIntrinsicCandidate
     private static native Object newArray(Class<?> componentType, int length)
         throws NegativeArraySizeException;
 
--- a/jdk/src/java.base/share/classes/java/lang/reflect/Method.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/reflect/Method.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,6 +25,7 @@
 
 package java.lang.reflect;
 
+import jdk.internal.HotSpotIntrinsicCandidate;
 import sun.reflect.CallerSensitive;
 import sun.reflect.MethodAccessor;
 import sun.reflect.Reflection;
@@ -485,6 +486,7 @@
      * provoked by this method fails.
      */
     @CallerSensitive
+    @HotSpotIntrinsicCandidate
     public Object invoke(Object obj, Object... args)
         throws IllegalAccessException, IllegalArgumentException,
            InvocationTargetException
--- a/jdk/src/java.base/share/classes/java/math/BigInteger.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/math/BigInteger.java	Wed Jul 05 20:42:36 2017 +0200
@@ -34,10 +34,13 @@
 import java.io.ObjectOutputStream;
 import java.io.ObjectStreamField;
 import java.util.Arrays;
+import java.util.Objects;
 import java.util.Random;
 import java.util.concurrent.ThreadLocalRandom;
+
 import sun.misc.DoubleConsts;
 import sun.misc.FloatConsts;
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 /**
  * Immutable arbitrary-precision integers.  All operations behave as if
@@ -262,6 +265,15 @@
      */
     private static final int MULTIPLY_SQUARE_THRESHOLD = 20;
 
+    /**
+     * The threshold for using an intrinsic version of
+     * implMontgomeryXXX to perform Montgomery multiplication.  If the
+     * number of ints in the number is more than this value we do not
+     * use the intrinsic.
+     */
+    private static final int MONTGOMERY_INTRINSIC_THRESHOLD = 512;
+
+
     // Constructors
 
     /**
@@ -1639,7 +1651,14 @@
      * Multiplies int arrays x and y to the specified lengths and places
      * the result into z. There will be no leading zeros in the resultant array.
      */
-    private int[] multiplyToLen(int[] x, int xlen, int[] y, int ylen, int[] z) {
+    private static int[] multiplyToLen(int[] x, int xlen, int[] y, int ylen, int[] z) {
+        multiplyToLenCheck(x, xlen);
+        multiplyToLenCheck(y, ylen);
+        return implMultiplyToLen(x, xlen, y, ylen, z);
+    }
+
+    @HotSpotIntrinsicCandidate
+    private static int[] implMultiplyToLen(int[] x, int xlen, int[] y, int ylen, int[] z) {
         int xstart = xlen - 1;
         int ystart = ylen - 1;
 
@@ -1669,6 +1688,18 @@
         return z;
     }
 
+    private static void multiplyToLenCheck(int[] array, int length) {
+        if (length <= 0) {
+            return;  // not an error because multiplyToLen won't execute if len <= 0
+        }
+
+        Objects.requireNonNull(array);
+
+        if (length > array.length) {
+            throw new ArrayIndexOutOfBoundsException(length - 1);
+        }
+    }
+
     /**
      * Multiplies two BigIntegers using the Karatsuba multiplication
      * algorithm.  This is a recursive divide-and-conquer algorithm which is
@@ -1999,6 +2030,7 @@
      /**
       * Java Runtime may use intrinsic for this method.
       */
+     @HotSpotIntrinsicCandidate
      private static final int[] implSquareToLen(int[] x, int len, int[] z, int zlen) {
         /*
          * The algorithm used here is adapted from Colin Plumb's C library.
@@ -2601,6 +2633,77 @@
         return (invertResult ? result.modInverse(m) : result);
     }
 
+    // Montgomery multiplication.  These are wrappers for
+    // implMontgomeryXX routines which are expected to be replaced by
+    // virtual machine intrinsics.  We don't use the intrinsics for
+    // very large operands: MONTGOMERY_INTRINSIC_THRESHOLD should be
+    // larger than any reasonable crypto key.
+    private static int[] montgomeryMultiply(int[] a, int[] b, int[] n, int len, long inv,
+                                            int[] product) {
+        implMontgomeryMultiplyChecks(a, b, n, len, product);
+        if (len > MONTGOMERY_INTRINSIC_THRESHOLD) {
+            // Very long argument: do not use an intrinsic
+            product = multiplyToLen(a, len, b, len, product);
+            return montReduce(product, n, len, (int)inv);
+        } else {
+            return implMontgomeryMultiply(a, b, n, len, inv, materialize(product, len));
+        }
+    }
+    private static int[] montgomerySquare(int[] a, int[] n, int len, long inv,
+                                          int[] product) {
+        implMontgomeryMultiplyChecks(a, a, n, len, product);
+        if (len > MONTGOMERY_INTRINSIC_THRESHOLD) {
+            // Very long argument: do not use an intrinsic
+            product = squareToLen(a, len, product);
+            return montReduce(product, n, len, (int)inv);
+        } else {
+            return implMontgomerySquare(a, n, len, inv, materialize(product, len));
+        }
+    }
+
+    // Range-check everything.
+    private static void implMontgomeryMultiplyChecks
+        (int[] a, int[] b, int[] n, int len, int[] product) throws RuntimeException {
+        if (len % 2 != 0) {
+            throw new IllegalArgumentException("input array length must be even: " + len);
+        }
+
+        if (len < 1) {
+            throw new IllegalArgumentException("invalid input length: " + len);
+        }
+
+        if (len > a.length ||
+            len > b.length ||
+            len > n.length ||
+            (product != null && len > product.length)) {
+            throw new IllegalArgumentException("input array length out of bound: " + len);
+        }
+    }
+
+    // Make sure that the int array z (which is expected to contain
+    // the result of a Montgomery multiplication) is present and
+    // sufficiently large.
+    private static int[] materialize(int[] z, int len) {
+         if (z == null || z.length < len)
+             z = new int[len];
+         return z;
+    }
+
+    // These methods are intended to be be replaced by virtual machine
+    // intrinsics.
+    @HotSpotIntrinsicCandidate
+    private static int[] implMontgomeryMultiply(int[] a, int[] b, int[] n, int len,
+                                         long inv, int[] product) {
+        product = multiplyToLen(a, len, b, len, product);
+        return montReduce(product, n, len, (int)inv);
+    }
+    @HotSpotIntrinsicCandidate
+    private static int[] implMontgomerySquare(int[] a, int[] n, int len,
+                                       long inv, int[] product) {
+        product = squareToLen(a, len, product);
+        return montReduce(product, n, len, (int)inv);
+    }
+
     static int[] bnExpModThreshTable = {7, 25, 81, 241, 673, 1793,
                                                 Integer.MAX_VALUE}; // Sentinel
 
@@ -2679,6 +2782,17 @@
         int[] mod = z.mag;
         int modLen = mod.length;
 
+        // Make modLen even. It is conventional to use a cryptographic
+        // modulus that is 512, 768, 1024, or 2048 bits, so this code
+        // will not normally be executed. However, it is necessary for
+        // the correct functioning of the HotSpot intrinsics.
+        if ((modLen & 1) != 0) {
+            int[] x = new int[modLen + 1];
+            System.arraycopy(mod, 0, x, 1, modLen);
+            mod = x;
+            modLen++;
+        }
+
         // Select an appropriate window size
         int wbits = 0;
         int ebits = bitLength(exp, exp.length);
@@ -2697,8 +2811,10 @@
         for (int i=0; i < tblmask; i++)
             table[i] = new int[modLen];
 
-        // Compute the modular inverse
-        int inv = -MutableBigInteger.inverseMod32(mod[modLen-1]);
+        // Compute the modular inverse of the least significant 64-bit
+        // digit of the modulus
+        long n0 = (mod[modLen-1] & LONG_MASK) + ((mod[modLen-2] & LONG_MASK) << 32);
+        long inv = -MutableBigInteger.inverseMod64(n0);
 
         // Convert base to Montgomery form
         int[] a = leftShift(base, base.length, modLen << 5);
@@ -2706,6 +2822,8 @@
         MutableBigInteger q = new MutableBigInteger(),
                           a2 = new MutableBigInteger(a),
                           b2 = new MutableBigInteger(mod);
+        b2.normalize(); // MutableBigInteger.divide() assumes that its
+                        // divisor is in normal form.
 
         MutableBigInteger r= a2.divide(b2, q);
         table[0] = r.toIntArray();
@@ -2714,22 +2832,19 @@
         if (table[0].length < modLen) {
            int offset = modLen - table[0].length;
            int[] t2 = new int[modLen];
-           for (int i=0; i < table[0].length; i++)
-               t2[i+offset] = table[0][i];
+           System.arraycopy(table[0], 0, t2, offset, table[0].length);
            table[0] = t2;
         }
 
         // Set b to the square of the base
-        int[] b = squareToLen(table[0], modLen, null);
-        b = montReduce(b, mod, modLen, inv);
+        int[] b = montgomerySquare(table[0], mod, modLen, inv, null);
 
         // Set t to high half of b
         int[] t = Arrays.copyOf(b, modLen);
 
         // Fill in the table with odd powers of the base
         for (int i=1; i < tblmask; i++) {
-            int[] prod = multiplyToLen(t, modLen, table[i-1], modLen, null);
-            table[i] = montReduce(prod, mod, modLen, inv);
+            table[i] = montgomeryMultiply(t, table[i-1], mod, modLen, inv, null);
         }
 
         // Pre load the window that slides over the exponent
@@ -2800,8 +2915,7 @@
                     isone = false;
                 } else {
                     t = b;
-                    a = multiplyToLen(t, modLen, mult, modLen, a);
-                    a = montReduce(a, mod, modLen, inv);
+                    a = montgomeryMultiply(t, mult, mod, modLen, inv, a);
                     t = a; a = b; b = t;
                 }
             }
@@ -2813,8 +2927,7 @@
             // Square the input
             if (!isone) {
                 t = b;
-                a = squareToLen(t, modLen, a);
-                a = montReduce(a, mod, modLen, inv);
+                a = montgomerySquare(t, mod, modLen, inv, a);
                 t = a; a = b; b = t;
             }
         }
@@ -2823,7 +2936,7 @@
         int[] t2 = new int[2*modLen];
         System.arraycopy(b, 0, t2, modLen, modLen);
 
-        b = montReduce(t2, mod, modLen, inv);
+        b = montReduce(t2, mod, modLen, (int)inv);
 
         t2 = Arrays.copyOf(b, modLen);
 
@@ -2916,6 +3029,7 @@
     /**
      * Java Runtime may use intrinsic for this method.
      */
+    @HotSpotIntrinsicCandidate
     private static int implMulAdd(int[] out, int[] in, int offset, int len, int k) {
         long kLong = k & LONG_MASK;
         long carry = 0;
--- a/jdk/src/java.base/share/classes/java/math/MutableBigInteger.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/math/MutableBigInteger.java	Wed Jul 05 20:42:36 2017 +0200
@@ -2065,6 +2065,21 @@
     }
 
     /**
+     * Returns the multiplicative inverse of val mod 2^64.  Assumes val is odd.
+     */
+    static long inverseMod64(long val) {
+        // Newton's iteration!
+        long t = val;
+        t *= 2 - val*t;
+        t *= 2 - val*t;
+        t *= 2 - val*t;
+        t *= 2 - val*t;
+        t *= 2 - val*t;
+        assert(t * val == 1);
+        return t;
+    }
+
+    /**
      * Calculate the multiplicative inverse of 2^k mod mod, where mod is odd.
      */
     static MutableBigInteger modInverseBP2(MutableBigInteger mod, int k) {
--- a/jdk/src/java.base/share/classes/java/net/ContentHandler.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/net/ContentHandler.java	Wed Jul 05 20:42:36 2017 +0200
@@ -44,14 +44,14 @@
  * instance of a subclass of {@code ContentHandler}, and its
  * {@code getContent} method is called to create the object.
  * <p>
- * If no content handler could be found, URLConnection will
- * look for a content handler in a user-defineable set of places.
+ * If no content handler could be {@linkplain URLConnection#getContent() found},
+ * URLConnection will look for a content handler in a user-definable set of places.
  * Users can define a vertical-bar delimited set of class prefixes
- * to search through by defining the <i>java.content.handler.pkgs</i>
+ * to search through by defining the <i>{@value java.net.URLConnection#contentPathProp}</i>
  * property. The class name must be of the form:
  * <blockquote>
  *     <i>{package-prefix}.{major}.{minor}</i>
- *     <P>
+ *     <p>
  *     where <i>{major}.{minor}</i> is formed by taking the
  *     content-type string, replacing all slash characters with a
  *     {@code period} ('.'), and all other non-alphanumeric characters
@@ -82,6 +82,7 @@
  * @since   1.0
  */
 abstract public class ContentHandler {
+
     /**
      * Given a URL connect stream positioned at the beginning of the
      * representation of an object, this method reads that stream and
@@ -104,8 +105,8 @@
      * @param      urlc   a URL connection.
      * @param      classes      an array of types requested
      * @return     the object read by the {@code ContentHandler} that is
-     *                 the first match of the suggested types.
-     *                 null if none of the requested  are supported.
+     *                 the first match of the suggested types or
+     *                 {@code null} if none of the requested  are supported.
      * @exception  IOException  if an I/O error occurs while reading the object.
      * @since 1.3
      */
@@ -113,12 +114,11 @@
     public Object getContent(URLConnection urlc, Class[] classes) throws IOException {
         Object obj = getContent(urlc);
 
-        for (int i = 0; i < classes.length; i++) {
-          if (classes[i].isInstance(obj)) {
+        for (Class<?> c : classes) {
+            if (c.isInstance(obj)) {
                 return obj;
-          }
+            }
         }
         return null;
     }
-
 }
--- a/jdk/src/java.base/share/classes/java/net/ContentHandlerFactory.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/net/ContentHandlerFactory.java	Wed Jul 05 20:42:36 2017 +0200
@@ -39,12 +39,13 @@
  * @since   1.0
  */
 public interface ContentHandlerFactory {
+
     /**
      * Creates a new {@code ContentHandler} to read an object from
      * a {@code URLStreamHandler}.
      *
      * @param   mimetype   the MIME type for which a content handler is desired.
-
+     *
      * @return  a new {@code ContentHandler} to read an object from a
      *          {@code URLStreamHandler}.
      * @see     java.net.ContentHandler
--- a/jdk/src/java.base/share/classes/java/net/InetAddress.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/net/InetAddress.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1995, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1995, 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
@@ -205,16 +205,33 @@
     static transient boolean preferIPv6Address = false;
 
     static class InetAddressHolder {
+        /**
+         * Reserve the original application specified hostname.
+         *
+         * The original hostname is useful for domain-based endpoint
+         * identification (see RFC 2818 and RFC 6125).  If an address
+         * was created with a raw IP address, a reverse name lookup
+         * may introduce endpoint identification security issue via
+         * DNS forging.
+         *
+         * Oracle JSSE provider is using this original hostname, via
+         * sun.misc.JavaNetAccess, for SSL/TLS endpoint identification.
+         *
+         * Note: May define a new public method in the future if necessary.
+         */
+        private String originalHostName;
 
         InetAddressHolder() {}
 
         InetAddressHolder(String hostName, int address, int family) {
+            this.originalHostName = hostName;
             this.hostName = hostName;
             this.address = address;
             this.family = family;
         }
 
         void init(String hostName, int family) {
+            this.originalHostName = hostName;
             this.hostName = hostName;
             if (family != -1) {
                 this.family = family;
@@ -227,6 +244,10 @@
             return hostName;
         }
 
+        String getOriginalHostName() {
+            return originalHostName;
+        }
+
         /**
          * Holds a 32-bit IPv4 address.
          */
--- a/jdk/src/java.base/share/classes/java/net/URLClassLoader.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/net/URLClassLoader.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 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
@@ -774,6 +774,10 @@
                 public URLClassPath getURLClassPath (URLClassLoader u) {
                     return u.ucp;
                 }
+
+                public String getOriginalHostName(InetAddress ia) {
+                    return ia.holder.getOriginalHostName();
+                }
             }
         );
         ClassLoader.registerAsParallelCapable();
--- a/jdk/src/java.base/share/classes/java/net/URLConnection.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/net/URLConnection.java	Wed Jul 05 20:42:36 2017 +0200
@@ -28,8 +28,12 @@
 import java.io.IOException;
 import java.io.InputStream;
 import java.io.OutputStream;
+import java.security.PrivilegedAction;
 import java.util.Hashtable;
 import java.util.Date;
+import java.util.Iterator;
+import java.util.ServiceConfigurationError;
+import java.util.ServiceLoader;
 import java.util.StringTokenizer;
 import java.util.Collections;
 import java.util.Map;
@@ -107,7 +111,7 @@
  *   <li>{@code getContentType}
  *   <li>{@code getDate}
  *   <li>{@code getExpiration}
- *   <li>{@code getLastModifed}
+ *   <li>{@code getLastModified}
  * </ul>
  * <p>
  * provide convenient access to these fields. The
@@ -695,16 +699,30 @@
      * This method first determines the content type of the object by
      * calling the {@code getContentType} method. If this is
      * the first time that the application has seen that specific content
-     * type, a content handler for that content type is created:
+     * type, a content handler for that content type is created.
+     * <p> This is done as follows:
      * <ol>
      * <li>If the application has set up a content handler factory instance
      *     using the {@code setContentHandlerFactory} method, the
      *     {@code createContentHandler} method of that instance is called
      *     with the content type as an argument; the result is a content
      *     handler for that content type.
-     * <li>If no content handler factory has yet been set up, or if the
-     *     factory's {@code createContentHandler} method returns
-     *     {@code null}, then this method tries to load a content handler
+     * <li>If no {@code ContentHandlerFactory} has yet been set up,
+     *     or if the factory's {@code createContentHandler} method
+     *     returns {@code null}, then the {@linkplain java.util.ServiceLoader
+     *     ServiceLoader} mechanism is used to locate {@linkplain
+     *     java.net.ContentHandlerFactory ContentHandlerFactory}
+     *     implementations using the system class
+     *     loader. The order that factories are located is implementation
+     *     specific, and an implementation is free to cache the located
+     *     factories. A {@linkplain java.util.ServiceConfigurationError
+     *     ServiceConfigurationError}, {@code Error} or {@code RuntimeException}
+     *     thrown from the {@code createContentHandler}, if encountered, will
+     *     be propagated to the calling thread. The {@code
+     *     createContentHandler} method of each factory, if instantiated, is
+     *     invoked, with the content type, until a factory returns non-null,
+     *     or all factories have been exhausted.
+     * <li>Failing that, this method tries to load a content handler
      *     class as defined by {@link java.net.ContentHandler ContentHandler}.
      *     If the class does not exist, or is not a subclass of {@code
      *     ContentHandler}, then an {@code UnknownServiceException} is thrown.
@@ -855,8 +873,7 @@
      * @see #getDoInput()
      */
     public void setDoInput(boolean doinput) {
-        if (connected)
-            throw new IllegalStateException("Already connected");
+        checkConnected();
         doInput = doinput;
     }
 
@@ -885,8 +902,7 @@
      * @see #getDoOutput()
      */
     public void setDoOutput(boolean dooutput) {
-        if (connected)
-            throw new IllegalStateException("Already connected");
+        checkConnected();
         doOutput = dooutput;
     }
 
@@ -911,8 +927,7 @@
      * @see     #getAllowUserInteraction()
      */
     public void setAllowUserInteraction(boolean allowuserinteraction) {
-        if (connected)
-            throw new IllegalStateException("Already connected");
+        checkConnected();
         allowUserInteraction = allowuserinteraction;
     }
 
@@ -974,8 +989,7 @@
      * @see #getUseCaches()
      */
     public void setUseCaches(boolean usecaches) {
-        if (connected)
-            throw new IllegalStateException("Already connected");
+        checkConnected();
         useCaches = usecaches;
     }
 
@@ -1000,8 +1014,7 @@
      * @see     #getIfModifiedSince()
      */
     public void setIfModifiedSince(long ifmodifiedsince) {
-        if (connected)
-            throw new IllegalStateException("Already connected");
+        checkConnected();
         ifModifiedSince = ifmodifiedsince;
     }
 
@@ -1055,12 +1068,11 @@
      *                  (e.g., "{@code Accept}").
      * @param   value   the value associated with it.
      * @throws IllegalStateException if already connected
-     * @throws NullPointerException if key is <CODE>null</CODE>
+     * @throws NullPointerException if key is {@code null}
      * @see #getRequestProperty(java.lang.String)
      */
     public void setRequestProperty(String key, String value) {
-        if (connected)
-            throw new IllegalStateException("Already connected");
+        checkConnected();
         if (key == null)
             throw new NullPointerException ("key is null");
 
@@ -1084,8 +1096,7 @@
      * @since 1.4
      */
     public void addRequestProperty(String key, String value) {
-        if (connected)
-            throw new IllegalStateException("Already connected");
+        checkConnected();
         if (key == null)
             throw new NullPointerException ("key is null");
 
@@ -1107,8 +1118,7 @@
      * @see #setRequestProperty(java.lang.String, java.lang.String)
      */
     public String getRequestProperty(String key) {
-        if (connected)
-            throw new IllegalStateException("Already connected");
+        checkConnected();
 
         if (requests == null)
             return null;
@@ -1129,8 +1139,7 @@
      * @since 1.4
      */
     public Map<String,List<String>> getRequestProperties() {
-        if (connected)
-            throw new IllegalStateException("Already connected");
+        checkConnected();
 
         if (requests == null)
             return Collections.emptyMap();
@@ -1183,7 +1192,7 @@
     /**
      * The ContentHandler factory.
      */
-    static ContentHandlerFactory factory;
+    private static volatile ContentHandlerFactory factory;
 
     /**
      * Sets the {@code ContentHandlerFactory} of an
@@ -1216,37 +1225,45 @@
         factory = fac;
     }
 
-    private static Hashtable<String, ContentHandler> handlers = new Hashtable<>();
+    private static final Hashtable<String, ContentHandler> handlers = new Hashtable<>();
 
     /**
      * Gets the Content Handler appropriate for this connection.
      */
-    synchronized ContentHandler getContentHandler()
-        throws UnknownServiceException
-    {
+    private ContentHandler getContentHandler() throws UnknownServiceException {
         String contentType = stripOffParameters(getContentType());
-        ContentHandler handler = null;
-        if (contentType == null)
+        if (contentType == null) {
             throw new UnknownServiceException("no content-type");
-        try {
-            handler = handlers.get(contentType);
+        }
+
+        ContentHandler handler = handlers.get(contentType);
+        if (handler != null)
+            return handler;
+
+        if (factory != null) {
+            handler = factory.createContentHandler(contentType);
             if (handler != null)
                 return handler;
-        } catch(Exception e) {
+        }
+
+        handler = lookupContentHandlerViaProvider(contentType);
+
+        if (handler != null) {
+            ContentHandler h = handlers.putIfAbsent(contentType, handler);
+            return h != null ? h : handler;
         }
 
-        if (factory != null)
-            handler = factory.createContentHandler(contentType);
-        if (handler == null) {
-            try {
-                handler = lookupContentHandlerClassFor(contentType);
-            } catch(Exception e) {
-                e.printStackTrace();
-                handler = UnknownContentHandler.INSTANCE;
-            }
-            handlers.put(contentType, handler);
+        try {
+            handler = lookupContentHandlerClassFor(contentType);
+        } catch (Exception e) {
+            e.printStackTrace();
+            handler = UnknownContentHandler.INSTANCE;
         }
-        return handler;
+
+        assert handler != null;
+
+        ContentHandler h = handlers.putIfAbsent(contentType, handler);
+        return h != null ? h : handler;
     }
 
     /*
@@ -1270,10 +1287,10 @@
     private static final String contentPathProp = "java.content.handler.pkgs";
 
     /**
-     * Looks for a content handler in a user-defineable set of places.
-     * By default it looks in sun.net.www.content, but users can define a
-     * vertical-bar delimited set of class prefixes to search through in
-     * addition by defining the java.content.handler.pkgs property.
+     * Looks for a content handler in a user-definable set of places.
+     * By default it looks in {@value #contentClassPrefix}, but users can define
+     * a vertical-bar delimited set of class prefixes to search through in
+     * addition by defining the {@value #contentPathProp} property.
      * The class name must be of the form:
      * <pre>
      *     {package-prefix}.{major}.{minor}
@@ -1281,11 +1298,10 @@
      *     YoyoDyne.experimental.text.plain
      * </pre>
      */
-    private ContentHandler lookupContentHandlerClassFor(String contentType)
-        throws InstantiationException, IllegalAccessException, ClassNotFoundException {
+    private ContentHandler lookupContentHandlerClassFor(String contentType) {
         String contentHandlerClassName = typeToPackageName(contentType);
 
-        String contentHandlerPkgPrefixes =getContentHandlerPkgPrefixes();
+        String contentHandlerPkgPrefixes = getContentHandlerPkgPrefixes();
 
         StringTokenizer packagePrefixIter =
             new StringTokenizer(contentHandlerPkgPrefixes, "|");
@@ -1305,17 +1321,46 @@
                     }
                 }
                 if (cls != null) {
-                    ContentHandler handler =
-                        (ContentHandler)cls.newInstance();
-                    return handler;
+                    return (ContentHandler) cls.newInstance();
                 }
-            } catch(Exception e) {
-            }
+            } catch(Exception ignored) { }
         }
 
         return UnknownContentHandler.INSTANCE;
     }
 
+    private ContentHandler lookupContentHandlerViaProvider(String contentType) {
+        return AccessController.doPrivileged(
+                new PrivilegedAction<>() {
+                    @Override
+                    public ContentHandler run() {
+                        ClassLoader cl = ClassLoader.getSystemClassLoader();
+                        ServiceLoader<ContentHandlerFactory> sl =
+                                ServiceLoader.load(ContentHandlerFactory.class, cl);
+
+                        Iterator<ContentHandlerFactory> iterator = sl.iterator();
+
+                        ContentHandler handler = null;
+                        while (iterator.hasNext()) {
+                            ContentHandlerFactory f;
+                            try {
+                                f = iterator.next();
+                            } catch (ServiceConfigurationError e) {
+                                if (e.getCause() instanceof SecurityException) {
+                                    continue;
+                                }
+                                throw e;
+                            }
+                            handler = f.createContentHandler(contentType);
+                            if (handler != null) {
+                                break;
+                            }
+                        }
+                        return handler;
+                    }
+                });
+    }
+
     /**
      * Utility function to map a MIME content type into an equivalent
      * pair of class name components.  For example: "text/html" would
@@ -1345,8 +1390,8 @@
      * Returns a vertical bar separated list of package prefixes for potential
      * content handlers.  Tries to get the java.content.handler.pkgs property
      * to use as a set of package prefixes to search.  Whether or not
-     * that property has been defined, the sun.net.www.content is always
-     * the last one on the returned package list.
+     * that property has been defined, the {@value #contentClassPrefix}
+     * is always the last one on the returned package list.
      */
     private String getContentHandlerPkgPrefixes() {
         String packagePrefixList = AccessController.doPrivileged(
@@ -1764,9 +1809,12 @@
         return skipped;
     }
 
+    private void checkConnected() {
+        if (connected)
+            throw new IllegalStateException("Already connected");
+    }
 }
 
-
 class UnknownContentHandler extends ContentHandler {
     static final ContentHandler INSTANCE = new UnknownContentHandler();
 
--- a/jdk/src/java.base/share/classes/java/nio/Buffer.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/nio/Buffer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -26,6 +26,7 @@
 package java.nio;
 
 import java.util.Spliterator;
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 /**
  * A container for data of a specific primitive type.
@@ -535,6 +536,7 @@
      * IndexOutOfBoundsException} if it is not smaller than the limit
      * or is smaller than zero.
      */
+    @HotSpotIntrinsicCandidate
     final int checkIndex(int i) {                       // package-private
         if ((i < 0) || (i >= limit))
             throw new IndexOutOfBoundsException();
--- a/jdk/src/java.base/share/classes/java/nio/X-Buffer-bin.java.template	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/nio/X-Buffer-bin.java.template	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2002, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 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
@@ -119,9 +119,10 @@
      *
      * <p> The new buffer's position will be zero, its capacity and its limit
      * will be the number of bytes remaining in this buffer divided by
-     * $nbytes$, and its mark will be undefined.  The new buffer will be direct
-     * if, and only if, this buffer is direct, and it will be read-only if, and
-     * only if, this buffer is read-only.  </p>
+     * $nbytes$, its mark will be undefined, and its byte order will be that
+     * of the byte buffer at the moment the view is created.  The new buffer
+     * will be direct if, and only if, this buffer is direct, and it will be
+     * read-only if, and only if, this buffer is read-only.  </p>
      *
      * @return  A new $type$ buffer
      */
--- a/jdk/src/java.base/share/classes/java/nio/X-Buffer.java.template	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/nio/X-Buffer.java.template	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 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
@@ -295,8 +295,9 @@
      * Allocates a new direct $type$ buffer.
      *
      * <p> The new buffer's position will be zero, its limit will be its
-     * capacity, its mark will be undefined, and each of its elements will be
-     * initialized to zero.  Whether or not it has a
+     * capacity, its mark will be undefined, each of its elements will be
+     * initialized to zero, and its byte order will be
+     * {@link ByteOrder#BIG_ENDIAN BIG_ENDIAN}.  Whether or not it has a
      * {@link #hasArray backing array} is unspecified.
      *
      * @param  capacity
@@ -317,9 +318,16 @@
      * Allocates a new $type$ buffer.
      *
      * <p> The new buffer's position will be zero, its limit will be its
-     * capacity, its mark will be undefined, and each of its elements will be
-     * initialized to zero.  It will have a {@link #array backing array},
-     * and its {@link #arrayOffset array offset} will be zero.
+     * capacity, its mark will be undefined, each of its elements will be
+     * initialized to zero, and its byte order will be
+#if[byte]
+     * {@link ByteOrder#BIG_ENDIAN BIG_ENDIAN}.
+#else[byte]
+     * the {@link ByteOrder#nativeOrder native order} of the underlying
+     * hardware.
+#end[byte]
+     * It will have a {@link #array backing array}, and its
+     * {@link #arrayOffset array offset} will be zero.
      *
      * @param  capacity
      *         The new buffer's capacity, in $type$s
@@ -342,8 +350,15 @@
      * that is, modifications to the buffer will cause the array to be modified
      * and vice versa.  The new buffer's capacity will be
      * <tt>array.length</tt>, its position will be <tt>offset</tt>, its limit
-     * will be <tt>offset + length</tt>, and its mark will be undefined.  Its
-     * {@link #array backing array} will be the given array, and
+     * will be <tt>offset + length</tt>, its mark will be undefined, and its
+     * byte order will be
+#if[byte]
+     * {@link ByteOrder#BIG_ENDIAN BIG_ENDIAN}.
+#else[byte]
+     * the {@link ByteOrder#nativeOrder native order} of the underlying
+     * hardware.
+#end[byte]
+     * Its {@link #array backing array} will be the given array, and
      * its {@link #arrayOffset array offset} will be zero.  </p>
      *
      * @param  array
@@ -382,10 +397,16 @@
      * <p> The new buffer will be backed by the given $type$ array;
      * that is, modifications to the buffer will cause the array to be modified
      * and vice versa.  The new buffer's capacity and limit will be
-     * <tt>array.length</tt>, its position will be zero, and its mark will be
-     * undefined.  Its {@link #array backing array} will be the
-     * given array, and its {@link #arrayOffset array offset} will
-     * be zero.  </p>
+     * <tt>array.length</tt>, its position will be zero, its mark will be
+     * undefined, and its byte order will be
+#if[byte]
+     * {@link ByteOrder#BIG_ENDIAN BIG_ENDIAN}.
+#else[byte]
+     * the {@link ByteOrder#nativeOrder native order} of the underlying
+     * hardware.
+#end[byte]
+     * Its {@link #array backing array} will be the given array, and its
+     * {@link #arrayOffset array offset} will be zero.  </p>
      *
      * @param  array
      *         The array that will back this buffer
@@ -499,10 +520,15 @@
      * values will be independent.
      *
      * <p> The new buffer's position will be zero, its capacity and its limit
-     * will be the number of $type$s remaining in this buffer, and its mark
-     * will be undefined.  The new buffer will be direct if, and only if, this
-     * buffer is direct, and it will be read-only if, and only if, this buffer
-     * is read-only.  </p>
+     * will be the number of $type$s remaining in this buffer, its mark will be
+     * undefined, and its byte order will be
+#if[byte]
+     * {@link ByteOrder#BIG_ENDIAN BIG_ENDIAN}.
+#else[byte]
+     * identical to that of this buffer.
+#end[byte]
+     * The new buffer will be direct if, and only if, this buffer is direct, and
+     * it will be read-only if, and only if, this buffer is read-only.  </p>
      *
      * @return  The new $type$ buffer
      */
@@ -516,10 +542,15 @@
      * versa; the two buffers' position, limit, and mark values will be
      * independent.
      *
-     * <p> The new buffer's capacity, limit, position, and mark values will be
-     * identical to those of this buffer.  The new buffer will be direct if,
-     * and only if, this buffer is direct, and it will be read-only if, and
-     * only if, this buffer is read-only.  </p>
+     * <p> The new buffer's capacity, limit, position,
+#if[byte]
+     * and mark values will be identical to those of this buffer, and its byte
+     * order will be {@link ByteOrder#BIG_ENDIAN BIG_ENDIAN}.
+#else[byte]
+     * mark values, and byte order will be identical to those of this buffer.
+#end[byte]
+     * The new buffer will be direct if, and only if, this buffer is direct, and
+     * it will be read-only if, and only if, this buffer is read-only.  </p>
      *
      * @return  The new $type$ buffer
      */
@@ -535,8 +566,13 @@
      * content to be modified.  The two buffers' position, limit, and mark
      * values will be independent.
      *
-     * <p> The new buffer's capacity, limit, position, and mark values will be
-     * identical to those of this buffer.
+     * <p> The new buffer's capacity, limit, position,
+#if[byte]
+     * and mark values will be identical to those of this buffer, and its byte
+     * order will be {@link ByteOrder#BIG_ENDIAN BIG_ENDIAN}.
+#else[byte]
+     * mark values, and byte order will be identical to those of this buffer.
+#end[byte]
      *
      * <p> If this buffer is itself read-only then this method behaves in
      * exactly the same way as the {@link #duplicate duplicate} method.  </p>
--- a/jdk/src/java.base/share/classes/java/security/Identity.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/security/Identity.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1996, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1996, 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
@@ -261,7 +261,7 @@
         certificates.addElement(certificate);
     }
 
-    private boolean keyEquals(Key aKey, Key anotherKey) {
+    private boolean keyEquals(PublicKey aKey, PublicKey anotherKey) {
         String aKeyFormat = aKey.getFormat();
         String anotherKeyFormat = anotherKey.getFormat();
         if ((aKeyFormat == null) ^ (anotherKeyFormat == null))
--- a/jdk/src/java.base/share/classes/java/security/MessageDigest.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/security/MessageDigest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1996, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1996, 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
@@ -440,6 +440,10 @@
      * @return true if the digests are equal, false otherwise.
      */
     public static boolean isEqual(byte[] digesta, byte[] digestb) {
+        if (digesta == digestb) return true;
+        if (digesta == null || digestb == null) {
+            return false;
+        }
         if (digesta.length != digestb.length) {
             return false;
         }
--- a/jdk/src/java.base/share/classes/java/security/Signature.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/security/Signature.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1996, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1996, 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
@@ -1324,7 +1324,7 @@
                 byte[] out = cipher.doFinal(sigBytes);
                 byte[] dataBytes = data.toByteArray();
                 data.reset();
-                return Arrays.equals(out, dataBytes);
+                return MessageDigest.isEqual(out, dataBytes);
             } catch (BadPaddingException e) {
                 // e.g. wrong public key used
                 // return false rather than throwing exception
--- a/jdk/src/java.base/share/classes/java/security/cert/X509CRLSelector.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/security/cert/X509CRLSelector.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 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
@@ -679,10 +679,14 @@
                 nowPlusSkew = new Date(dateAndTime.getTime() + skew);
                 nowMinusSkew = new Date(dateAndTime.getTime() - skew);
             }
+
+            // Check that the test date is within the validity interval:
+            //   [ thisUpdate - MAX_CLOCK_SKEW,
+            //     nextUpdate + MAX_CLOCK_SKEW ]
             if (nowMinusSkew.after(nextUpdate)
                 || nowPlusSkew.before(crlThisUpdate)) {
                 if (debug != null) {
-                    debug.println("X509CRLSelector.match: update out of range");
+                    debug.println("X509CRLSelector.match: update out-of-range");
                 }
                 return false;
             }
--- a/jdk/src/java.base/share/classes/java/text/Bidi.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/text/Bidi.java	Wed Jul 05 20:42:36 2017 +0200
@@ -185,7 +185,7 @@
         AttributedString astr = new AttributedString("");
         Bidi newBidi = new Bidi(astr.getIterator());
 
-        return bidiBase.setLine(this, bidiBase, newBidi, newBidi.bidiBase,lineStart, lineLimit);
+        return bidiBase.setLine(this, bidiBase, newBidi, newBidi.bidiBase, lineStart, lineLimit);
     }
 
     /**
--- a/jdk/src/java.base/share/classes/java/text/Normalizer.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/text/Normalizer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -38,7 +38,6 @@
 package java.text;
 
 import sun.text.normalizer.NormalizerBase;
-import sun.text.normalizer.NormalizerImpl;
 
 /**
  * This class provides the method <code>normalize</code> which transforms Unicode
--- a/jdk/src/java.base/share/classes/java/util/Arrays.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/Arrays.java	Wed Jul 05 20:42:36 2017 +0200
@@ -42,6 +42,7 @@
 import java.util.stream.LongStream;
 import java.util.stream.Stream;
 import java.util.stream.StreamSupport;
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 /**
  * This class contains various methods for manipulating arrays (such as
@@ -2654,6 +2655,7 @@
      * @param a2 the other array to be tested for equality
      * @return <tt>true</tt> if the two arrays are equal
      */
+    @HotSpotIntrinsicCandidate
     public static boolean equals(char[] a, char[] a2) {
         if (a==a2)
             return true;
@@ -3205,6 +3207,7 @@
      *     an array of class <tt>newType</tt>
      * @since 1.6
      */
+    @HotSpotIntrinsicCandidate
     public static <T,U> T[] copyOf(U[] original, int newLength, Class<? extends T[]> newType) {
         @SuppressWarnings("unchecked")
         T[] copy = ((Object)newType == (Object)Object[].class)
@@ -3474,6 +3477,7 @@
      *     an array of class <tt>newType</tt>.
      * @since 1.6
      */
+    @HotSpotIntrinsicCandidate
     public static <T,U> T[] copyOfRange(U[] original, int from, int to, Class<? extends T[]> newType) {
         int newLength = to - from;
         if (newLength < 0)
--- a/jdk/src/java.base/share/classes/java/util/Spliterators.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/Spliterators.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1235,8 +1235,8 @@
      * <p>An extending class need only
      * implement {@link #tryAdvance(java.util.function.Consumer) tryAdvance}.
      * The extending class should override
-     * {@link #forEachRemaining(java.util.function.Consumer) forEach} if it can
-     * provide a more performant implementation.
+     * {@link #forEachRemaining(java.util.function.Consumer) forEachRemaining}
+     * if it can provide a more performant implementation.
      *
      * @apiNote
      * This class is a useful aid for creating a spliterator when it is not
@@ -1356,10 +1356,10 @@
      * permit limited parallelism.
      *
      * <p>To implement a spliterator an extending class need only
-     * implement {@link #tryAdvance(java.util.function.IntConsumer)}
+     * implement {@link #tryAdvance(java.util.function.IntConsumer)
      * tryAdvance}.  The extending class should override
-     * {@link #forEachRemaining(java.util.function.IntConsumer)} forEach} if it
-     * can provide a more performant implementation.
+     * {@link #forEachRemaining(java.util.function.IntConsumer) forEachRemaining}
+     * if it can provide a more performant implementation.
      *
      * @apiNote
      * This class is a useful aid for creating a spliterator when it is not
@@ -1466,10 +1466,10 @@
      * to permit limited parallelism.
      *
      * <p>To implement a spliterator an extending class need only
-     * implement {@link #tryAdvance(java.util.function.LongConsumer)}
+     * implement {@link #tryAdvance(java.util.function.LongConsumer)
      * tryAdvance}.  The extending class should override
-     * {@link #forEachRemaining(java.util.function.LongConsumer)} forEach} if it
-     * can provide a more performant implementation.
+     * {@link #forEachRemaining(java.util.function.LongConsumer) forEachRemaining}
+     * if it can provide a more performant implementation.
      *
      * @apiNote
      * This class is a useful aid for creating a spliterator when it is not
@@ -1576,10 +1576,10 @@
      * {@code trySplit} to permit limited parallelism.
      *
      * <p>To implement a spliterator an extending class need only
-     * implement {@link #tryAdvance(java.util.function.DoubleConsumer)}
+     * implement {@link #tryAdvance(java.util.function.DoubleConsumer)
      * tryAdvance}.  The extending class should override
-     * {@link #forEachRemaining(java.util.function.DoubleConsumer)} forEach} if
-     * it can provide a more performant implementation.
+     * {@link #forEachRemaining(java.util.function.DoubleConsumer) forEachRemaining}
+     * if it can provide a more performant implementation.
      *
      * @apiNote
      * This class is a useful aid for creating a spliterator when it is not
--- a/jdk/src/java.base/share/classes/java/util/stream/AbstractPipeline.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/stream/AbstractPipeline.java	Wed Jul 05 20:42:36 2017 +0200
@@ -489,15 +489,17 @@
 
     @Override
     @SuppressWarnings("unchecked")
-    final <P_IN> void copyIntoWithCancel(Sink<P_IN> wrappedSink, Spliterator<P_IN> spliterator) {
+    final <P_IN> boolean copyIntoWithCancel(Sink<P_IN> wrappedSink, Spliterator<P_IN> spliterator) {
         @SuppressWarnings({"rawtypes","unchecked"})
         AbstractPipeline p = AbstractPipeline.this;
         while (p.depth > 0) {
             p = p.previousStage;
         }
+
         wrappedSink.begin(spliterator.getExactSizeIfKnown());
-        p.forEachWithCancel(spliterator, wrappedSink);
+        boolean cancelled = p.forEachWithCancel(spliterator, wrappedSink);
         wrappedSink.end();
+        return cancelled;
     }
 
     @Override
@@ -602,8 +604,9 @@
      *
      * @param spliterator the spliterator to pull elements from
      * @param sink the sink to push elements to
+     * @return true if the cancellation was requested
      */
-    abstract void forEachWithCancel(Spliterator<E_OUT> spliterator, Sink<E_OUT> sink);
+    abstract boolean forEachWithCancel(Spliterator<E_OUT> spliterator, Sink<E_OUT> sink);
 
     /**
      * Make a node builder compatible with this stream shape.
--- a/jdk/src/java.base/share/classes/java/util/stream/DoublePipeline.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/stream/DoublePipeline.java	Wed Jul 05 20:42:36 2017 +0200
@@ -40,6 +40,7 @@
 import java.util.function.DoubleToLongFunction;
 import java.util.function.DoubleUnaryOperator;
 import java.util.function.IntFunction;
+import java.util.function.LongPredicate;
 import java.util.function.ObjDoubleConsumer;
 import java.util.function.Supplier;
 
@@ -153,10 +154,12 @@
     }
 
     @Override
-    final void forEachWithCancel(Spliterator<Double> spliterator, Sink<Double> sink) {
+    final boolean forEachWithCancel(Spliterator<Double> spliterator, Sink<Double> sink) {
         Spliterator.OfDouble spl = adapt(spliterator);
         DoubleConsumer adaptedSink = adapt(sink);
-        do { } while (!sink.cancellationRequested() && spl.tryAdvance(adaptedSink));
+        boolean cancelled;
+        do { } while (!(cancelled = sink.cancellationRequested()) && spl.tryAdvance(adaptedSink));
+        return cancelled;
     }
 
     @Override
@@ -353,6 +356,16 @@
     }
 
     @Override
+    public final DoubleStream takeWhile(DoublePredicate predicate) {
+        return WhileOps.makeTakeWhileDouble(this, predicate);
+    }
+
+    @Override
+    public final DoubleStream dropWhile(DoublePredicate predicate) {
+        return WhileOps.makeDropWhileDouble(this, predicate);
+    }
+
+    @Override
     public final DoubleStream sorted() {
         return SortedOps.makeDouble(this);
     }
--- a/jdk/src/java.base/share/classes/java/util/stream/DoubleStream.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/stream/DoubleStream.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012, 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
@@ -24,18 +24,13 @@
  */
 package java.util.stream;
 
-import java.nio.charset.Charset;
-import java.nio.file.Files;
-import java.nio.file.Path;
 import java.util.Arrays;
-import java.util.Collection;
 import java.util.DoubleSummaryStatistics;
 import java.util.Objects;
 import java.util.OptionalDouble;
 import java.util.PrimitiveIterator;
 import java.util.Spliterator;
 import java.util.Spliterators;
-import java.util.concurrent.ConcurrentHashMap;
 import java.util.function.BiConsumer;
 import java.util.function.DoubleBinaryOperator;
 import java.util.function.DoubleConsumer;
@@ -280,6 +275,137 @@
     DoubleStream skip(long n);
 
     /**
+     * Returns, if this stream is ordered, a stream consisting of the longest
+     * prefix of elements taken from this stream that match the given predicate.
+     * Otherwise returns, if this stream is unordered, a stream consisting of a
+     * subset of elements taken from this stream that match the given predicate.
+     *
+     * <p>If this stream is ordered then the longest prefix is a contiguous
+     * sequence of elements of this stream that match the given predicate.  The
+     * first element of the sequence is the first element of this stream, and
+     * the element immediately following the last element of the sequence does
+     * not match the given predicate.
+     *
+     * <p>If this stream is unordered, and some (but not all) elements of this
+     * stream match the given predicate, then the behavior of this operation is
+     * nondeterministic; it is free to take any subset of matching elements
+     * (which includes the empty set).
+     *
+     * <p>Independent of whether this stream is ordered or unordered if all
+     * elements of this stream match the given predicate then this operation
+     * takes all elements (the result is the same is the input), or if no
+     * elements of the stream match the given predicate then no elements are
+     * taken (the result is an empty stream).
+     *
+     * <p>This is a <a href="package-summary.html#StreamOps">short-circuiting
+     * stateful intermediate operation</a>.
+     *
+     * @implSpec
+     * The default implementation obtains the {@link #spliterator() spliterator}
+     * of this stream, wraps that spliterator so as to support the semantics
+     * of this operation on traversal, and returns a new stream associated with
+     * the wrapped spliterator.  The returned stream preserves the execution
+     * characteristics of this stream (namely parallel or sequential execution
+     * as per {@link #isParallel()}) but the wrapped spliterator may choose to
+     * not support splitting.  When the returned stream is closed, the close
+     * handlers for both the returned and this stream are invoked.
+     *
+     * @apiNote
+     * While {@code takeWhile()} is generally a cheap operation on sequential
+     * stream pipelines, it can be quite expensive on ordered parallel
+     * pipelines, since the operation is constrained to return not just any
+     * valid prefix, but the longest prefix of elements in the encounter order.
+     * Using an unordered stream source (such as
+     * {@link #generate(DoubleSupplier)}) or removing the ordering constraint
+     * with {@link #unordered()} may result in significant speedups of
+     * {@code takeWhile()} in parallel pipelines, if the semantics of your
+     * situation permit.  If consistency with encounter order is required, and
+     * you are experiencing poor performance or memory utilization with
+     * {@code takeWhile()} in parallel pipelines, switching to sequential
+     * execution with {@link #sequential()} may improve performance.
+     *
+     * @param predicate a <a href="package-summary.html#NonInterference">non-interfering</a>,
+     *                  <a href="package-summary.html#Statelessness">stateless</a>
+     *                  predicate to apply to elements to determine the longest
+     *                  prefix of elements.
+     * @return the new stream
+     */
+    default DoubleStream takeWhile(DoublePredicate predicate) {
+        Objects.requireNonNull(predicate);
+        // Reuses the unordered spliterator, which, when encounter is present,
+        // is safe to use as long as it configured not to split
+        return StreamSupport.doubleStream(
+                new WhileOps.UnorderedWhileSpliterator.OfDouble.Taking(spliterator(), true, predicate),
+                isParallel()).onClose(this::close);
+    }
+
+    /**
+     * Returns, if this stream is ordered, a stream consisting of the remaining
+     * elements of this stream after dropping the longest prefix of elements
+     * that match the given predicate.  Otherwise returns, if this stream is
+     * unordered, a stream consisting of the remaining elements of this stream
+     * after dropping a subset of elements that match the given predicate.
+     *
+     * <p>If this stream is ordered then the longest prefix is a contiguous
+     * sequence of elements of this stream that match the given predicate.  The
+     * first element of the sequence is the first element of this stream, and
+     * the element immediately following the last element of the sequence does
+     * not match the given predicate.
+     *
+     * <p>If this stream is unordered, and some (but not all) elements of this
+     * stream match the given predicate, then the behavior of this operation is
+     * nondeterministic; it is free to drop any subset of matching elements
+     * (which includes the empty set).
+     *
+     * <p>Independent of whether this stream is ordered or unordered if all
+     * elements of this stream match the given predicate then this operation
+     * drops all elements (the result is an empty stream), or if no elements of
+     * the stream match the given predicate then no elements are dropped (the
+     * result is the same is the input).
+     *
+     * <p>This is a <a href="package-summary.html#StreamOps">stateful
+     * intermediate operation</a>.
+     *
+     * @implSpec
+     * The default implementation obtains the {@link #spliterator() spliterator}
+     * of this stream, wraps that spliterator so as to support the semantics
+     * of this operation on traversal, and returns a new stream associated with
+     * the wrapped spliterator.  The returned stream preserves the execution
+     * characteristics of this stream (namely parallel or sequential execution
+     * as per {@link #isParallel()}) but the wrapped spliterator may choose to
+     * not support splitting.  When the returned stream is closed, the close
+     * handlers for both the returned and this stream are invoked.
+     *
+     * @apiNote
+     * While {@code dropWhile()} is generally a cheap operation on sequential
+     * stream pipelines, it can be quite expensive on ordered parallel
+     * pipelines, since the operation is constrained to return not just any
+     * valid prefix, but the longest prefix of elements in the encounter order.
+     * Using an unordered stream source (such as
+     * {@link #generate(DoubleSupplier)}) or removing the ordering constraint
+     * with {@link #unordered()} may result in significant speedups of
+     * {@code dropWhile()} in parallel pipelines, if the semantics of your
+     * situation permit.  If consistency with encounter order is required, and
+     * you are experiencing poor performance or memory utilization with
+     * {@code dropWhile()} in parallel pipelines, switching to sequential
+     * execution with {@link #sequential()} may improve performance.
+     *
+     * @param predicate a <a href="package-summary.html#NonInterference">non-interfering</a>,
+     *                  <a href="package-summary.html#Statelessness">stateless</a>
+     *                  predicate to apply to elements to determine the longest
+     *                  prefix of elements.
+     * @return the new stream
+     */
+    default DoubleStream dropWhile(DoublePredicate predicate) {
+        Objects.requireNonNull(predicate);
+        // Reuses the unordered spliterator, which, when encounter is present,
+        // is safe to use as long as it configured not to split
+        return StreamSupport.doubleStream(
+                new WhileOps.UnorderedWhileSpliterator.OfDouble.Dropping(spliterator(), true, predicate),
+                isParallel()).onClose(this::close);
+    }
+
+    /**
      * Performs an action for each element of this stream.
      *
      * <p>This is a <a href="package-summary.html#StreamOps">terminal
--- a/jdk/src/java.base/share/classes/java/util/stream/IntPipeline.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/stream/IntPipeline.java	Wed Jul 05 20:42:36 2017 +0200
@@ -156,10 +156,12 @@
     }
 
     @Override
-    final void forEachWithCancel(Spliterator<Integer> spliterator, Sink<Integer> sink) {
+    final boolean forEachWithCancel(Spliterator<Integer> spliterator, Sink<Integer> sink) {
         Spliterator.OfInt spl = adapt(spliterator);
         IntConsumer adaptedSink = adapt(sink);
-        do { } while (!sink.cancellationRequested() && spl.tryAdvance(adaptedSink));
+        boolean cancelled;
+        do { } while (!(cancelled = sink.cancellationRequested()) && spl.tryAdvance(adaptedSink));
+        return cancelled;
     }
 
     @Override
@@ -387,6 +389,16 @@
     }
 
     @Override
+    public final IntStream takeWhile(IntPredicate predicate) {
+        return WhileOps.makeTakeWhileInt(this, predicate);
+    }
+
+    @Override
+    public final IntStream dropWhile(IntPredicate predicate) {
+        return WhileOps.makeDropWhileInt(this, predicate);
+    }
+
+    @Override
     public final IntStream sorted() {
         return SortedOps.makeInt(this);
     }
--- a/jdk/src/java.base/share/classes/java/util/stream/IntStream.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/stream/IntStream.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012, 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
@@ -273,6 +273,135 @@
     IntStream skip(long n);
 
     /**
+     * Returns, if this stream is ordered, a stream consisting of the longest
+     * prefix of elements taken from this stream that match the given predicate.
+     * Otherwise returns, if this stream is unordered, a stream consisting of a
+     * subset of elements taken from this stream that match the given predicate.
+     *
+     * <p>If this stream is ordered then the longest prefix is a contiguous
+     * sequence of elements of this stream that match the given predicate.  The
+     * first element of the sequence is the first element of this stream, and
+     * the element immediately following the last element of the sequence does
+     * not match the given predicate.
+     *
+     * <p>If this stream is unordered, and some (but not all) elements of this
+     * stream match the given predicate, then the behavior of this operation is
+     * nondeterministic; it is free to take any subset of matching elements
+     * (which includes the empty set).
+     *
+     * <p>Independent of whether this stream is ordered or unordered if all
+     * elements of this stream match the given predicate then this operation
+     * takes all elements (the result is the same is the input), or if no
+     * elements of the stream match the given predicate then no elements are
+     * taken (the result is an empty stream).
+     *
+     * <p>This is a <a href="package-summary.html#StreamOps">short-circuiting
+     * stateful intermediate operation</a>.
+     *
+     * @implSpec
+     * The default implementation obtains the {@link #spliterator() spliterator}
+     * of this stream, wraps that spliterator so as to support the semantics
+     * of this operation on traversal, and returns a new stream associated with
+     * the wrapped spliterator.  The returned stream preserves the execution
+     * characteristics of this stream (namely parallel or sequential execution
+     * as per {@link #isParallel()}) but the wrapped spliterator may choose to
+     * not support splitting.  When the returned stream is closed, the close
+     * handlers for both the returned and this stream are invoked.
+     *
+     * @apiNote
+     * While {@code takeWhile()} is generally a cheap operation on sequential
+     * stream pipelines, it can be quite expensive on ordered parallel
+     * pipelines, since the operation is constrained to return not just any
+     * valid prefix, but the longest prefix of elements in the encounter order.
+     * Using an unordered stream source (such as {@link #generate(IntSupplier)})
+     * or removing the ordering constraint with {@link #unordered()} may result
+     * in significant speedups of {@code takeWhile()} in parallel pipelines, if
+     * the semantics of your situation permit.  If consistency with encounter
+     * order is required, and you are experiencing poor performance or memory
+     * utilization with {@code takeWhile()} in parallel pipelines, switching to
+     * sequential execution with {@link #sequential()} may improve performance.
+     *
+     * @param predicate a <a href="package-summary.html#NonInterference">non-interfering</a>,
+     *                  <a href="package-summary.html#Statelessness">stateless</a>
+     *                  predicate to apply to elements to determine the longest
+     *                  prefix of elements.
+     * @return the new stream
+     */
+    default IntStream takeWhile(IntPredicate predicate) {
+        Objects.requireNonNull(predicate);
+        // Reuses the unordered spliterator, which, when encounter is present,
+        // is safe to use as long as it configured not to split
+        return StreamSupport.intStream(
+                new WhileOps.UnorderedWhileSpliterator.OfInt.Taking(spliterator(), true, predicate),
+                isParallel()).onClose(this::close);
+    }
+
+    /**
+     * Returns, if this stream is ordered, a stream consisting of the remaining
+     * elements of this stream after dropping the longest prefix of elements
+     * that match the given predicate.  Otherwise returns, if this stream is
+     * unordered, a stream consisting of the remaining elements of this stream
+     * after dropping a subset of elements that match the given predicate.
+     *
+     * <p>If this stream is ordered then the longest prefix is a contiguous
+     * sequence of elements of this stream that match the given predicate.  The
+     * first element of the sequence is the first element of this stream, and
+     * the element immediately following the last element of the sequence does
+     * not match the given predicate.
+     *
+     * <p>If this stream is unordered, and some (but not all) elements of this
+     * stream match the given predicate, then the behavior of this operation is
+     * nondeterministic; it is free to drop any subset of matching elements
+     * (which includes the empty set).
+     *
+     * <p>Independent of whether this stream is ordered or unordered if all
+     * elements of this stream match the given predicate then this operation
+     * drops all elements (the result is an empty stream), or if no elements of
+     * the stream match the given predicate then no elements are dropped (the
+     * result is the same is the input).
+     *
+     * <p>This is a <a href="package-summary.html#StreamOps">stateful
+     * intermediate operation</a>.
+     *
+     * @implSpec
+     * The default implementation obtains the {@link #spliterator() spliterator}
+     * of this stream, wraps that spliterator so as to support the semantics
+     * of this operation on traversal, and returns a new stream associated with
+     * the wrapped spliterator.  The returned stream preserves the execution
+     * characteristics of this stream (namely parallel or sequential execution
+     * as per {@link #isParallel()}) but the wrapped spliterator may choose to
+     * not support splitting.  When the returned stream is closed, the close
+     * handlers for both the returned and this stream are invoked.
+     *
+     * @apiNote
+     * While {@code dropWhile()} is generally a cheap operation on sequential
+     * stream pipelines, it can be quite expensive on ordered parallel
+     * pipelines, since the operation is constrained to return not just any
+     * valid prefix, but the longest prefix of elements in the encounter order.
+     * Using an unordered stream source (such as {@link #generate(IntSupplier)})
+     * or removing the ordering constraint with {@link #unordered()} may result
+     * in significant speedups of {@code dropWhile()} in parallel pipelines, if
+     * the semantics of your situation permit.  If consistency with encounter
+     * order is required, and you are experiencing poor performance or memory
+     * utilization with {@code dropWhile()} in parallel pipelines, switching to
+     * sequential execution with {@link #sequential()} may improve performance.
+     *
+     * @param predicate a <a href="package-summary.html#NonInterference">non-interfering</a>,
+     *                  <a href="package-summary.html#Statelessness">stateless</a>
+     *                  predicate to apply to elements to determine the longest
+     *                  prefix of elements.
+     * @return the new stream
+     */
+    default IntStream dropWhile(IntPredicate predicate) {
+        Objects.requireNonNull(predicate);
+        // Reuses the unordered spliterator, which, when encounter is present,
+        // is safe to use as long as it configured not to split
+        return StreamSupport.intStream(
+                new WhileOps.UnorderedWhileSpliterator.OfInt.Dropping(spliterator(), true, predicate),
+                isParallel()).onClose(this::close);
+    }
+
+    /**
      * Performs an action for each element of this stream.
      *
      * <p>This is a <a href="package-summary.html#StreamOps">terminal
--- a/jdk/src/java.base/share/classes/java/util/stream/LongPipeline.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/stream/LongPipeline.java	Wed Jul 05 20:42:36 2017 +0200
@@ -154,10 +154,12 @@
     }
 
     @Override
-    final void forEachWithCancel(Spliterator<Long> spliterator, Sink<Long> sink) {
+    final boolean forEachWithCancel(Spliterator<Long> spliterator, Sink<Long> sink) {
         Spliterator.OfLong spl = adapt(spliterator);
         LongConsumer adaptedSink =  adapt(sink);
-        do { } while (!sink.cancellationRequested() && spl.tryAdvance(adaptedSink));
+        boolean cancelled;
+        do { } while (!(cancelled = sink.cancellationRequested()) && spl.tryAdvance(adaptedSink));
+        return cancelled;
     }
 
     @Override
@@ -368,6 +370,16 @@
     }
 
     @Override
+    public final LongStream takeWhile(LongPredicate predicate) {
+        return WhileOps.makeTakeWhileLong(this, predicate);
+    }
+
+    @Override
+    public final LongStream dropWhile(LongPredicate predicate) {
+        return WhileOps.makeDropWhileLong(this, predicate);
+    }
+
+    @Override
     public final LongStream sorted() {
         return SortedOps.makeLong(this);
     }
--- a/jdk/src/java.base/share/classes/java/util/stream/LongStream.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/stream/LongStream.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013, 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
@@ -24,11 +24,7 @@
  */
 package java.util.stream;
 
-import java.nio.charset.Charset;
-import java.nio.file.Files;
-import java.nio.file.Path;
 import java.util.Arrays;
-import java.util.Collection;
 import java.util.LongSummaryStatistics;
 import java.util.Objects;
 import java.util.OptionalDouble;
@@ -36,7 +32,6 @@
 import java.util.PrimitiveIterator;
 import java.util.Spliterator;
 import java.util.Spliterators;
-import java.util.concurrent.ConcurrentHashMap;
 import java.util.function.BiConsumer;
 import java.util.function.Function;
 import java.util.function.LongBinaryOperator;
@@ -278,6 +273,137 @@
     LongStream skip(long n);
 
     /**
+     * Returns, if this stream is ordered, a stream consisting of the longest
+     * prefix of elements taken from this stream that match the given predicate.
+     * Otherwise returns, if this stream is unordered, a stream consisting of a
+     * subset of elements taken from this stream that match the given predicate.
+     *
+     * <p>If this stream is ordered then the longest prefix is a contiguous
+     * sequence of elements of this stream that match the given predicate.  The
+     * first element of the sequence is the first element of this stream, and
+     * the element immediately following the last element of the sequence does
+     * not match the given predicate.
+     *
+     * <p>If this stream is unordered, and some (but not all) elements of this
+     * stream match the given predicate, then the behavior of this operation is
+     * nondeterministic; it is free to take any subset of matching elements
+     * (which includes the empty set).
+     *
+     * <p>Independent of whether this stream is ordered or unordered if all
+     * elements of this stream match the given predicate then this operation
+     * takes all elements (the result is the same is the input), or if no
+     * elements of the stream match the given predicate then no elements are
+     * taken (the result is an empty stream).
+     *
+     * <p>This is a <a href="package-summary.html#StreamOps">short-circuiting
+     * stateful intermediate operation</a>.
+     *
+     * @implSpec
+     * The default implementation obtains the {@link #spliterator() spliterator}
+     * of this stream, wraps that spliterator so as to support the semantics
+     * of this operation on traversal, and returns a new stream associated with
+     * the wrapped spliterator.  The returned stream preserves the execution
+     * characteristics of this stream (namely parallel or sequential execution
+     * as per {@link #isParallel()}) but the wrapped spliterator may choose to
+     * not support splitting.  When the returned stream is closed, the close
+     * handlers for both the returned and this stream are invoked.
+     *
+     * @apiNote
+     * While {@code takeWhile()} is generally a cheap operation on sequential
+     * stream pipelines, it can be quite expensive on ordered parallel
+     * pipelines, since the operation is constrained to return not just any
+     * valid prefix, but the longest prefix of elements in the encounter order.
+     * Using an unordered stream source (such as
+     * {@link #generate(LongSupplier)}) or removing the ordering constraint with
+     * {@link #unordered()} may result in significant speedups of
+     * {@code takeWhile()} in parallel pipelines, if the semantics of your
+     * situation permit.  If consistency with encounter order is required, and
+     * you are experiencing poor performance or memory utilization with
+     * {@code takeWhile()} in parallel pipelines, switching to sequential
+     * execution with {@link #sequential()} may improve performance.
+     *
+     * @param predicate a <a href="package-summary.html#NonInterference">non-interfering</a>,
+     *                  <a href="package-summary.html#Statelessness">stateless</a>
+     *                  predicate to apply to elements to determine the longest
+     *                  prefix of elements.
+     * @return the new stream
+     */
+    default LongStream takeWhile(LongPredicate predicate) {
+        Objects.requireNonNull(predicate);
+        // Reuses the unordered spliterator, which, when encounter is present,
+        // is safe to use as long as it configured not to split
+        return StreamSupport.longStream(
+                new WhileOps.UnorderedWhileSpliterator.OfLong.Taking(spliterator(), true, predicate),
+                isParallel()).onClose(this::close);
+    }
+
+    /**
+     * Returns, if this stream is ordered, a stream consisting of the remaining
+     * elements of this stream after dropping the longest prefix of elements
+     * that match the given predicate.  Otherwise returns, if this stream is
+     * unordered, a stream consisting of the remaining elements of this stream
+     * after dropping a subset of elements that match the given predicate.
+     *
+     * <p>If this stream is ordered then the longest prefix is a contiguous
+     * sequence of elements of this stream that match the given predicate.  The
+     * first element of the sequence is the first element of this stream, and
+     * the element immediately following the last element of the sequence does
+     * not match the given predicate.
+     *
+     * <p>If this stream is unordered, and some (but not all) elements of this
+     * stream match the given predicate, then the behavior of this operation is
+     * nondeterministic; it is free to drop any subset of matching elements
+     * (which includes the empty set).
+     *
+     * <p>Independent of whether this stream is ordered or unordered if all
+     * elements of this stream match the given predicate then this operation
+     * drops all elements (the result is an empty stream), or if no elements of
+     * the stream match the given predicate then no elements are dropped (the
+     * result is the same is the input).
+     *
+     * <p>This is a <a href="package-summary.html#StreamOps">stateful
+     * intermediate operation</a>.
+     *
+     * @implSpec
+     * The default implementation obtains the {@link #spliterator() spliterator}
+     * of this stream, wraps that spliterator so as to support the semantics
+     * of this operation on traversal, and returns a new stream associated with
+     * the wrapped spliterator.  The returned stream preserves the execution
+     * characteristics of this stream (namely parallel or sequential execution
+     * as per {@link #isParallel()}) but the wrapped spliterator may choose to
+     * not support splitting.  When the returned stream is closed, the close
+     * handlers for both the returned and this stream are invoked.
+     *
+     * @apiNote
+     * While {@code dropWhile()} is generally a cheap operation on sequential
+     * stream pipelines, it can be quite expensive on ordered parallel
+     * pipelines, since the operation is constrained to return not just any
+     * valid prefix, but the longest prefix of elements in the encounter order.
+     * Using an unordered stream source (such as
+     * {@link #generate(LongSupplier)}) or removing the ordering constraint with
+     * {@link #unordered()} may result in significant speedups of
+     * {@code dropWhile()} in parallel pipelines, if the semantics of your
+     * situation permit.  If consistency with encounter order is required, and
+     * you are experiencing poor performance or memory utilization with
+     * {@code dropWhile()} in parallel pipelines, switching to sequential
+     * execution with {@link #sequential()} may improve performance.
+     *
+     * @param predicate a <a href="package-summary.html#NonInterference">non-interfering</a>,
+     *                  <a href="package-summary.html#Statelessness">stateless</a>
+     *                  predicate to apply to elements to determine the longest
+     *                  prefix of elements.
+     * @return the new stream
+     */
+    default LongStream dropWhile(LongPredicate predicate) {
+        Objects.requireNonNull(predicate);
+        // Reuses the unordered spliterator, which, when encounter is present,
+        // is safe to use as long as it configured not to split
+        return StreamSupport.longStream(
+                new WhileOps.UnorderedWhileSpliterator.OfLong.Dropping(spliterator(), true, predicate),
+                isParallel()).onClose(this::close);
+    }
+
+    /**
      * Performs an action for each element of this stream.
      *
      * <p>This is a <a href="package-summary.html#StreamOps">terminal
--- a/jdk/src/java.base/share/classes/java/util/stream/Node.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/stream/Node.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012, 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
@@ -125,7 +125,11 @@
         Node.Builder<T> nodeBuilder = Nodes.builder(size, generator);
         nodeBuilder.begin(size);
         for (int i = 0; i < from && spliterator.tryAdvance(e -> { }); i++) { }
-        for (int i = 0; (i < size) && spliterator.tryAdvance(nodeBuilder); i++) { }
+        if (to == count()) {
+            spliterator.forEachRemaining(nodeBuilder);
+        } else {
+            for (int i = 0; i < size && spliterator.tryAdvance(nodeBuilder); i++) { }
+        }
         nodeBuilder.end();
         return nodeBuilder.build();
     }
@@ -360,7 +364,11 @@
             Node.Builder.OfInt nodeBuilder = Nodes.intBuilder(size);
             nodeBuilder.begin(size);
             for (int i = 0; i < from && spliterator.tryAdvance((IntConsumer) e -> { }); i++) { }
-            for (int i = 0; (i < size) && spliterator.tryAdvance((IntConsumer) nodeBuilder); i++) { }
+            if (to == count()) {
+                spliterator.forEachRemaining((IntConsumer) nodeBuilder);
+            } else {
+                for (int i = 0; i < size && spliterator.tryAdvance((IntConsumer) nodeBuilder); i++) { }
+            }
             nodeBuilder.end();
             return nodeBuilder.build();
         }
@@ -433,7 +441,11 @@
             Node.Builder.OfLong nodeBuilder = Nodes.longBuilder(size);
             nodeBuilder.begin(size);
             for (int i = 0; i < from && spliterator.tryAdvance((LongConsumer) e -> { }); i++) { }
-            for (int i = 0; (i < size) && spliterator.tryAdvance((LongConsumer) nodeBuilder); i++) { }
+            if (to == count()) {
+                spliterator.forEachRemaining((LongConsumer) nodeBuilder);
+            } else {
+                for (int i = 0; i < size && spliterator.tryAdvance((LongConsumer) nodeBuilder); i++) { }
+            }
             nodeBuilder.end();
             return nodeBuilder.build();
         }
@@ -508,7 +520,11 @@
             Node.Builder.OfDouble nodeBuilder = Nodes.doubleBuilder(size);
             nodeBuilder.begin(size);
             for (int i = 0; i < from && spliterator.tryAdvance((DoubleConsumer) e -> { }); i++) { }
-            for (int i = 0; (i < size) && spliterator.tryAdvance((DoubleConsumer) nodeBuilder); i++) { }
+            if (to == count()) {
+                spliterator.forEachRemaining((DoubleConsumer) nodeBuilder);
+            } else {
+                for (int i = 0; i < size && spliterator.tryAdvance((DoubleConsumer) nodeBuilder); i++) { }
+            }
             nodeBuilder.end();
             return nodeBuilder.build();
         }
--- a/jdk/src/java.base/share/classes/java/util/stream/Nodes.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/stream/Nodes.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012, 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
@@ -69,6 +69,14 @@
     private static final Node.OfLong EMPTY_LONG_NODE = new EmptyNode.OfLong();
     private static final Node.OfDouble EMPTY_DOUBLE_NODE = new EmptyNode.OfDouble();
 
+    /**
+     * @return an array generator for an array whose elements are of type T.
+     */
+    @SuppressWarnings("unchecked")
+    static <T> IntFunction<T[]> castingArray() {
+        return size -> (T[]) new Object[size];
+    }
+
     // General shape-based node creation methods
 
     /**
--- a/jdk/src/java.base/share/classes/java/util/stream/PipelineHelper.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/stream/PipelineHelper.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012, 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
@@ -136,8 +136,9 @@
      *
      * @param wrappedSink the destination {@code Sink}
      * @param spliterator the source {@code Spliterator}
+     * @return true if the cancellation was requested
      */
-    abstract <P_IN> void copyIntoWithCancel(Sink<P_IN> wrappedSink, Spliterator<P_IN> spliterator);
+    abstract <P_IN> boolean copyIntoWithCancel(Sink<P_IN> wrappedSink, Spliterator<P_IN> spliterator);
 
     /**
      * Takes a {@code Sink} that accepts elements of the output type of the
--- a/jdk/src/java.base/share/classes/java/util/stream/ReferencePipeline.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/stream/ReferencePipeline.java	Wed Jul 05 20:42:36 2017 +0200
@@ -122,8 +122,10 @@
     }
 
     @Override
-    final void forEachWithCancel(Spliterator<P_OUT> spliterator, Sink<P_OUT> sink) {
-        do { } while (!sink.cancellationRequested() && spliterator.tryAdvance(sink));
+    final boolean forEachWithCancel(Spliterator<P_OUT> spliterator, Sink<P_OUT> sink) {
+        boolean cancelled;
+        do { } while (!(cancelled = sink.cancellationRequested()) && spliterator.tryAdvance(sink));
+        return cancelled;
     }
 
     @Override
@@ -411,6 +413,16 @@
             return SliceOps.makeRef(this, n, -1);
     }
 
+    @Override
+    public final Stream<P_OUT> takeWhile(Predicate<? super P_OUT> predicate) {
+        return WhileOps.makeTakeWhileRef(this, predicate);
+    }
+
+    @Override
+    public final Stream<P_OUT> dropWhile(Predicate<? super P_OUT> predicate) {
+        return WhileOps.makeDropWhileRef(this, predicate);
+    }
+
     // Terminal operations from Stream
 
     @Override
--- a/jdk/src/java.base/share/classes/java/util/stream/SliceOps.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/stream/SliceOps.java	Wed Jul 05 20:42:36 2017 +0200
@@ -96,11 +96,6 @@
         }
     }
 
-    @SuppressWarnings("unchecked")
-    private static <T> IntFunction<T[]> castingArray() {
-        return size -> (T[]) new Object[size];
-    }
-
     /**
      * Appends a "slice" operation to the provided stream.  The slice operation
      * may be may be skip-only, limit-only, or skip-and-limit.
@@ -151,7 +146,7 @@
                     //     cancellation will be more aggressive cancelling later tasks
                     //     if the target slice size has been reached from a given task,
                     //     cancellation should also clear local results if any
-                    return new SliceTask<>(this, helper, spliterator, castingArray(), skip, limit).
+                    return new SliceTask<>(this, helper, spliterator, Nodes.castingArray(), skip, limit).
                             invoke().spliterator();
                 }
             }
--- a/jdk/src/java.base/share/classes/java/util/stream/Stream.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/stream/Stream.java	Wed Jul 05 20:42:36 2017 +0200
@@ -24,7 +24,6 @@
  */
 package java.util.stream;
 
-import java.nio.charset.Charset;
 import java.nio.file.Files;
 import java.nio.file.Path;
 import java.util.Arrays;
@@ -481,6 +480,135 @@
     Stream<T> skip(long n);
 
     /**
+     * Returns, if this stream is ordered, a stream consisting of the longest
+     * prefix of elements taken from this stream that match the given predicate.
+     * Otherwise returns, if this stream is unordered, a stream consisting of a
+     * subset of elements taken from this stream that match the given predicate.
+     *
+     * <p>If this stream is ordered then the longest prefix is a contiguous
+     * sequence of elements of this stream that match the given predicate.  The
+     * first element of the sequence is the first element of this stream, and
+     * the element immediately following the last element of the sequence does
+     * not match the given predicate.
+     *
+     * <p>If this stream is unordered, and some (but not all) elements of this
+     * stream match the given predicate, then the behavior of this operation is
+     * nondeterministic; it is free to take any subset of matching elements
+     * (which includes the empty set).
+     *
+     * <p>Independent of whether this stream is ordered or unordered if all
+     * elements of this stream match the given predicate then this operation
+     * takes all elements (the result is the same is the input), or if no
+     * elements of the stream match the given predicate then no elements are
+     * taken (the result is an empty stream).
+     *
+     * <p>This is a <a href="package-summary.html#StreamOps">short-circuiting
+     * stateful intermediate operation</a>.
+     *
+     * @implSpec
+     * The default implementation obtains the {@link #spliterator() spliterator}
+     * of this stream, wraps that spliterator so as to support the semantics
+     * of this operation on traversal, and returns a new stream associated with
+     * the wrapped spliterator.  The returned stream preserves the execution
+     * characteristics of this stream (namely parallel or sequential execution
+     * as per {@link #isParallel()}) but the wrapped spliterator may choose to
+     * not support splitting.  When the returned stream is closed, the close
+     * handlers for both the returned and this stream are invoked.
+     *
+     * @apiNote
+     * While {@code takeWhile()} is generally a cheap operation on sequential
+     * stream pipelines, it can be quite expensive on ordered parallel
+     * pipelines, since the operation is constrained to return not just any
+     * valid prefix, but the longest prefix of elements in the encounter order.
+     * Using an unordered stream source (such as {@link #generate(Supplier)}) or
+     * removing the ordering constraint with {@link #unordered()} may result in
+     * significant speedups of {@code takeWhile()} in parallel pipelines, if the
+     * semantics of your situation permit.  If consistency with encounter order
+     * is required, and you are experiencing poor performance or memory
+     * utilization with {@code takeWhile()} in parallel pipelines, switching to
+     * sequential execution with {@link #sequential()} may improve performance.
+     *
+     * @param predicate a <a href="package-summary.html#NonInterference">non-interfering</a>,
+     *                  <a href="package-summary.html#Statelessness">stateless</a>
+     *                  predicate to apply to elements to determine the longest
+     *                  prefix of elements.
+     * @return the new stream
+     */
+    default Stream<T> takeWhile(Predicate<? super T> predicate) {
+        Objects.requireNonNull(predicate);
+        // Reuses the unordered spliterator, which, when encounter is present,
+        // is safe to use as long as it configured not to split
+        return StreamSupport.stream(
+                new WhileOps.UnorderedWhileSpliterator.OfRef.Taking<>(spliterator(), true, predicate),
+                isParallel()).onClose(this::close);
+    }
+
+    /**
+     * Returns, if this stream is ordered, a stream consisting of the remaining
+     * elements of this stream after dropping the longest prefix of elements
+     * that match the given predicate.  Otherwise returns, if this stream is
+     * unordered, a stream consisting of the remaining elements of this stream
+     * after dropping a subset of elements that match the given predicate.
+     *
+     * <p>If this stream is ordered then the longest prefix is a contiguous
+     * sequence of elements of this stream that match the given predicate.  The
+     * first element of the sequence is the first element of this stream, and
+     * the element immediately following the last element of the sequence does
+     * not match the given predicate.
+     *
+     * <p>If this stream is unordered, and some (but not all) elements of this
+     * stream match the given predicate, then the behavior of this operation is
+     * nondeterministic; it is free to drop any subset of matching elements
+     * (which includes the empty set).
+     *
+     * <p>Independent of whether this stream is ordered or unordered if all
+     * elements of this stream match the given predicate then this operation
+     * drops all elements (the result is an empty stream), or if no elements of
+     * the stream match the given predicate then no elements are dropped (the
+     * result is the same is the input).
+     *
+     * <p>This is a <a href="package-summary.html#StreamOps">stateful
+     * intermediate operation</a>.
+     *
+     * @implSpec
+     * The default implementation obtains the {@link #spliterator() spliterator}
+     * of this stream, wraps that spliterator so as to support the semantics
+     * of this operation on traversal, and returns a new stream associated with
+     * the wrapped spliterator.  The returned stream preserves the execution
+     * characteristics of this stream (namely parallel or sequential execution
+     * as per {@link #isParallel()}) but the wrapped spliterator may choose to
+     * not support splitting.  When the returned stream is closed, the close
+     * handlers for both the returned and this stream are invoked.
+     *
+     * @apiNote
+     * While {@code dropWhile()} is generally a cheap operation on sequential
+     * stream pipelines, it can be quite expensive on ordered parallel
+     * pipelines, since the operation is constrained to return not just any
+     * valid prefix, but the longest prefix of elements in the encounter order.
+     * Using an unordered stream source (such as {@link #generate(Supplier)}) or
+     * removing the ordering constraint with {@link #unordered()} may result in
+     * significant speedups of {@code dropWhile()} in parallel pipelines, if the
+     * semantics of your situation permit.  If consistency with encounter order
+     * is required, and you are experiencing poor performance or memory
+     * utilization with {@code dropWhile()} in parallel pipelines, switching to
+     * sequential execution with {@link #sequential()} may improve performance.
+     *
+     * @param predicate a <a href="package-summary.html#NonInterference">non-interfering</a>,
+     *                  <a href="package-summary.html#Statelessness">stateless</a>
+     *                  predicate to apply to elements to determine the longest
+     *                  prefix of elements.
+     * @return the new stream
+     */
+    default Stream<T> dropWhile(Predicate<? super T> predicate) {
+        Objects.requireNonNull(predicate);
+        // Reuses the unordered spliterator, which, when encounter is present,
+        // is safe to use as long as it configured not to split
+        return StreamSupport.stream(
+                new WhileOps.UnorderedWhileSpliterator.OfRef.Dropping<>(spliterator(), true, predicate),
+                isParallel()).onClose(this::close);
+    }
+
+    /**
      * Performs an action for each element of this stream.
      *
      * <p>This is a <a href="package-summary.html#StreamOps">terminal
--- a/jdk/src/java.base/share/classes/java/util/stream/Streams.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/stream/Streams.java	Wed Jul 05 20:42:36 2017 +0200
@@ -31,6 +31,7 @@
 import java.util.function.DoubleConsumer;
 import java.util.function.IntConsumer;
 import java.util.function.LongConsumer;
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 /**
  * Utility methods for operating on and creating streams.
@@ -98,6 +99,7 @@
         }
 
         @Override
+        @HotSpotIntrinsicCandidate
         public void forEachRemaining(IntConsumer consumer) {
             Objects.requireNonNull(consumer);
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/java/util/stream/WhileOps.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,1394 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package java.util.stream;
+
+import java.util.Comparator;
+import java.util.Objects;
+import java.util.Spliterator;
+import java.util.concurrent.CountedCompleter;
+import java.util.concurrent.atomic.AtomicBoolean;
+import java.util.function.Consumer;
+import java.util.function.DoubleConsumer;
+import java.util.function.DoublePredicate;
+import java.util.function.IntConsumer;
+import java.util.function.IntFunction;
+import java.util.function.IntPredicate;
+import java.util.function.LongConsumer;
+import java.util.function.LongPredicate;
+import java.util.function.Predicate;
+
+/**
+ * Factory for instances of a takeWhile and dropWhile operations
+ * that produce subsequences of their input stream.
+ *
+ * @since 1.9
+ */
+final class WhileOps {
+
+    static final int TAKE_FLAGS = StreamOpFlag.NOT_SIZED | StreamOpFlag.IS_SHORT_CIRCUIT;
+
+    static final int DROP_FLAGS = StreamOpFlag.NOT_SIZED;
+
+    /**
+     * Appends a "takeWhile" operation to the provided Stream.
+     *
+     * @param <T> the type of both input and output elements
+     * @param upstream a reference stream with element type T
+     * @param predicate the predicate that returns false to halt taking.
+     */
+    static <T> Stream<T> makeTakeWhileRef(AbstractPipeline<?, T, ?> upstream,
+                                          Predicate<? super T> predicate) {
+        Objects.requireNonNull(predicate);
+        return new ReferencePipeline.StatefulOp<T, T>(upstream, StreamShape.REFERENCE, TAKE_FLAGS) {
+            @Override
+            <P_IN> Spliterator<T> opEvaluateParallelLazy(PipelineHelper<T> helper,
+                                                         Spliterator<P_IN> spliterator) {
+                if (StreamOpFlag.ORDERED.isKnown(helper.getStreamAndOpFlags())) {
+                    return opEvaluateParallel(helper, spliterator, Nodes.castingArray())
+                            .spliterator();
+                }
+                else {
+                    return new UnorderedWhileSpliterator.OfRef.Taking<>(
+                            helper.wrapSpliterator(spliterator), false, predicate);
+                }
+            }
+
+            @Override
+            <P_IN> Node<T> opEvaluateParallel(PipelineHelper<T> helper,
+                                              Spliterator<P_IN> spliterator,
+                                              IntFunction<T[]> generator) {
+                return new TakeWhileTask<>(this, helper, spliterator, generator)
+                        .invoke();
+            }
+
+            @Override
+            Sink<T> opWrapSink(int flags, Sink<T> sink) {
+                return new Sink.ChainedReference<T, T>(sink) {
+                    boolean take = true;
+
+                    @Override
+                    public void begin(long size) {
+                        downstream.begin(-1);
+                    }
+
+                    @Override
+                    public void accept(T t) {
+                        if (take = predicate.test(t)) {
+                            downstream.accept(t);
+                        }
+                    }
+
+                    @Override
+                    public boolean cancellationRequested() {
+                        return !take || downstream.cancellationRequested();
+                    }
+                };
+            }
+        };
+    }
+
+    /**
+     * Appends a "takeWhile" operation to the provided IntStream.
+     *
+     * @param upstream a reference stream with element type T
+     * @param predicate the predicate that returns false to halt taking.
+     */
+    static IntStream makeTakeWhileInt(AbstractPipeline<?, Integer, ?> upstream,
+                                      IntPredicate predicate) {
+        Objects.requireNonNull(predicate);
+        return new IntPipeline.StatefulOp<Integer>(upstream, StreamShape.INT_VALUE, TAKE_FLAGS) {
+            @Override
+            <P_IN> Spliterator<Integer> opEvaluateParallelLazy(PipelineHelper<Integer> helper,
+                                                               Spliterator<P_IN> spliterator) {
+                if (StreamOpFlag.ORDERED.isKnown(helper.getStreamAndOpFlags())) {
+                    return opEvaluateParallel(helper, spliterator, Integer[]::new)
+                            .spliterator();
+                }
+                else {
+                    return new UnorderedWhileSpliterator.OfInt.Taking(
+                            (Spliterator.OfInt) helper.wrapSpliterator(spliterator), false, predicate);
+                }
+            }
+
+            @Override
+            <P_IN> Node<Integer> opEvaluateParallel(PipelineHelper<Integer> helper,
+                                                    Spliterator<P_IN> spliterator,
+                                                    IntFunction<Integer[]> generator) {
+                return new TakeWhileTask<>(this, helper, spliterator, generator)
+                        .invoke();
+            }
+
+            @Override
+            Sink<Integer> opWrapSink(int flags, Sink<Integer> sink) {
+                return new Sink.ChainedInt<Integer>(sink) {
+                    boolean take = true;
+
+                    @Override
+                    public void begin(long size) {
+                        downstream.begin(-1);
+                    }
+
+                    @Override
+                    public void accept(int t) {
+                        if (take = predicate.test(t)) {
+                            downstream.accept(t);
+                        }
+                    }
+
+                    @Override
+                    public boolean cancellationRequested() {
+                        return !take || downstream.cancellationRequested();
+                    }
+                };
+            }
+        };
+    }
+
+    /**
+     * Appends a "takeWhile" operation to the provided LongStream.
+     *
+     * @param upstream a reference stream with element type T
+     * @param predicate the predicate that returns false to halt taking.
+     */
+    static LongStream makeTakeWhileLong(AbstractPipeline<?, Long, ?> upstream,
+                                        LongPredicate predicate) {
+        Objects.requireNonNull(predicate);
+        return new LongPipeline.StatefulOp<Long>(upstream, StreamShape.LONG_VALUE, TAKE_FLAGS) {
+            @Override
+            <P_IN> Spliterator<Long> opEvaluateParallelLazy(PipelineHelper<Long> helper,
+                                                            Spliterator<P_IN> spliterator) {
+                if (StreamOpFlag.ORDERED.isKnown(helper.getStreamAndOpFlags())) {
+                    return opEvaluateParallel(helper, spliterator, Long[]::new)
+                            .spliterator();
+                }
+                else {
+                    return new UnorderedWhileSpliterator.OfLong.Taking(
+                            (Spliterator.OfLong) helper.wrapSpliterator(spliterator), false, predicate);
+                }
+            }
+
+            @Override
+            <P_IN> Node<Long> opEvaluateParallel(PipelineHelper<Long> helper,
+                                                 Spliterator<P_IN> spliterator,
+                                                 IntFunction<Long[]> generator) {
+                return new TakeWhileTask<>(this, helper, spliterator, generator)
+                        .invoke();
+            }
+
+            @Override
+            Sink<Long> opWrapSink(int flags, Sink<Long> sink) {
+                return new Sink.ChainedLong<Long>(sink) {
+                    boolean take = true;
+
+                    @Override
+                    public void begin(long size) {
+                        downstream.begin(-1);
+                    }
+
+                    @Override
+                    public void accept(long t) {
+                        if (take = predicate.test(t)) {
+                            downstream.accept(t);
+                        }
+                    }
+
+                    @Override
+                    public boolean cancellationRequested() {
+                        return !take || downstream.cancellationRequested();
+                    }
+                };
+            }
+        };
+    }
+
+    /**
+     * Appends a "takeWhile" operation to the provided DoubleStream.
+     *
+     * @param upstream a reference stream with element type T
+     * @param predicate the predicate that returns false to halt taking.
+     */
+    static DoubleStream makeTakeWhileDouble(AbstractPipeline<?, Double, ?> upstream,
+                                            DoublePredicate predicate) {
+        Objects.requireNonNull(predicate);
+        return new DoublePipeline.StatefulOp<Double>(upstream, StreamShape.DOUBLE_VALUE, TAKE_FLAGS) {
+            @Override
+            <P_IN> Spliterator<Double> opEvaluateParallelLazy(PipelineHelper<Double> helper,
+                                                              Spliterator<P_IN> spliterator) {
+                if (StreamOpFlag.ORDERED.isKnown(helper.getStreamAndOpFlags())) {
+                    return opEvaluateParallel(helper, spliterator, Double[]::new)
+                            .spliterator();
+                }
+                else {
+                    return new UnorderedWhileSpliterator.OfDouble.Taking(
+                            (Spliterator.OfDouble) helper.wrapSpliterator(spliterator), false, predicate);
+                }
+            }
+
+            @Override
+            <P_IN> Node<Double> opEvaluateParallel(PipelineHelper<Double> helper,
+                                                   Spliterator<P_IN> spliterator,
+                                                   IntFunction<Double[]> generator) {
+                return new TakeWhileTask<>(this, helper, spliterator, generator)
+                        .invoke();
+            }
+
+            @Override
+            Sink<Double> opWrapSink(int flags, Sink<Double> sink) {
+                return new Sink.ChainedDouble<Double>(sink) {
+                    boolean take = true;
+
+                    @Override
+                    public void begin(long size) {
+                        downstream.begin(-1);
+                    }
+
+                    @Override
+                    public void accept(double t) {
+                        if (take = predicate.test(t)) {
+                            downstream.accept(t);
+                        }
+                    }
+
+                    @Override
+                    public boolean cancellationRequested() {
+                        return !take || downstream.cancellationRequested();
+                    }
+                };
+            }
+        };
+    }
+
+    /**
+     * A specialization for the dropWhile operation that controls if
+     * elements to be dropped are counted and passed downstream.
+     * <p>
+     * This specialization is utilized by the {@link TakeWhileTask} for
+     * pipelines that are ordered.  In such cases elements cannot be dropped
+     * until all elements have been collected.
+     *
+     * @param <T> the type of both input and output elements
+     */
+    interface DropWhileOp<T> {
+        /**
+         * Accepts a {@code Sink} which will receive the results of this
+         * dropWhile operation, and return a {@code DropWhileSink} which
+         * accepts
+         * elements and which performs the dropWhile operation passing the
+         * results to the provided {@code Sink}.
+         *
+         * @param sink sink to which elements should be sent after processing
+         * @param retainAndCountDroppedElements true if elements to be dropped
+         * are counted and passed to the sink, otherwise such elements
+         * are actually dropped and not passed to the sink.
+         * @return a dropWhile sink
+         */
+        DropWhileSink<T> opWrapSink(Sink<T> sink, boolean retainAndCountDroppedElements);
+    }
+
+    /**
+     * A specialization for a dropWhile sink.
+     *
+     * @param <T> the type of both input and output elements
+     */
+    interface DropWhileSink<T> extends Sink<T> {
+        /**
+         * @return the could of elements that would have been dropped and
+         * instead were passed downstream.
+         */
+        long getDropCount();
+    }
+
+    /**
+     * Appends a "dropWhile" operation to the provided Stream.
+     *
+     * @param <T> the type of both input and output elements
+     * @param upstream a reference stream with element type T
+     * @param predicate the predicate that returns false to halt dropping.
+     */
+    static <T> Stream<T> makeDropWhileRef(AbstractPipeline<?, T, ?> upstream,
+                                          Predicate<? super T> predicate) {
+        Objects.requireNonNull(predicate);
+
+        class Op extends ReferencePipeline.StatefulOp<T, T> implements DropWhileOp<T> {
+            public Op(AbstractPipeline<?, T, ?> upstream, StreamShape inputShape, int opFlags) {
+                super(upstream, inputShape, opFlags);
+            }
+
+            @Override
+            <P_IN> Spliterator<T> opEvaluateParallelLazy(PipelineHelper<T> helper,
+                                                         Spliterator<P_IN> spliterator) {
+                if (StreamOpFlag.ORDERED.isKnown(helper.getStreamAndOpFlags())) {
+                    return opEvaluateParallel(helper, spliterator, Nodes.castingArray())
+                            .spliterator();
+                }
+                else {
+                    return new UnorderedWhileSpliterator.OfRef.Dropping<>(
+                            helper.wrapSpliterator(spliterator), false, predicate);
+                }
+            }
+
+            @Override
+            <P_IN> Node<T> opEvaluateParallel(PipelineHelper<T> helper,
+                                              Spliterator<P_IN> spliterator,
+                                              IntFunction<T[]> generator) {
+                return new DropWhileTask<>(this, helper, spliterator, generator)
+                        .invoke();
+            }
+
+            @Override
+            Sink<T> opWrapSink(int flags, Sink<T> sink) {
+                return opWrapSink(sink, false);
+            }
+
+            public DropWhileSink<T> opWrapSink(Sink<T> sink, boolean retainAndCountDroppedElements) {
+                class OpSink extends Sink.ChainedReference<T, T> implements DropWhileSink<T> {
+                    long dropCount;
+                    boolean take;
+
+                    OpSink() {
+                        super(sink);
+                    }
+
+                    @Override
+                    public void accept(T t) {
+                        boolean takeElement = take || (take = !predicate.test(t));
+
+                        // If ordered and element is dropped increment index
+                        // for possible future truncation
+                        if (retainAndCountDroppedElements && !takeElement)
+                            dropCount++;
+
+                        // If ordered need to process element, otherwise
+                        // skip if element is dropped
+                        if (retainAndCountDroppedElements || takeElement)
+                            downstream.accept(t);
+                    }
+
+                    @Override
+                    public long getDropCount() {
+                        return dropCount;
+                    }
+                }
+                return new OpSink();
+            }
+        }
+        return new Op(upstream, StreamShape.REFERENCE, DROP_FLAGS);
+    }
+
+    /**
+     * Appends a "dropWhile" operation to the provided IntStream.
+     *
+     * @param upstream a reference stream with element type T
+     * @param predicate the predicate that returns false to halt dropping.
+     */
+    static IntStream makeDropWhileInt(AbstractPipeline<?, Integer, ?> upstream,
+                                      IntPredicate predicate) {
+        Objects.requireNonNull(predicate);
+        class Op extends IntPipeline.StatefulOp<Integer> implements DropWhileOp<Integer> {
+            public Op(AbstractPipeline<?, Integer, ?> upstream, StreamShape inputShape, int opFlags) {
+                super(upstream, inputShape, opFlags);
+            }
+
+            @Override
+            <P_IN> Spliterator<Integer> opEvaluateParallelLazy(PipelineHelper<Integer> helper,
+                                                               Spliterator<P_IN> spliterator) {
+                if (StreamOpFlag.ORDERED.isKnown(helper.getStreamAndOpFlags())) {
+                    return opEvaluateParallel(helper, spliterator, Integer[]::new)
+                            .spliterator();
+                }
+                else {
+                    return new UnorderedWhileSpliterator.OfInt.Dropping(
+                            (Spliterator.OfInt) helper.wrapSpliterator(spliterator), false, predicate);
+                }
+            }
+
+            @Override
+            <P_IN> Node<Integer> opEvaluateParallel(PipelineHelper<Integer> helper,
+                                                    Spliterator<P_IN> spliterator,
+                                                    IntFunction<Integer[]> generator) {
+                return new DropWhileTask<>(this, helper, spliterator, generator)
+                        .invoke();
+            }
+
+            @Override
+            Sink<Integer> opWrapSink(int flags, Sink<Integer> sink) {
+                return opWrapSink(sink, false);
+            }
+
+            public DropWhileSink<Integer> opWrapSink(Sink<Integer> sink, boolean retainAndCountDroppedElements) {
+                class OpSink extends Sink.ChainedInt<Integer> implements DropWhileSink<Integer> {
+                    long dropCount;
+                    boolean take;
+
+                    OpSink() {
+                        super(sink);
+                    }
+
+                    @Override
+                    public void accept(int t) {
+                        boolean takeElement = take || (take = !predicate.test(t));
+
+                        // If ordered and element is dropped increment index
+                        // for possible future truncation
+                        if (retainAndCountDroppedElements && !takeElement)
+                            dropCount++;
+
+                        // If ordered need to process element, otherwise
+                        // skip if element is dropped
+                        if (retainAndCountDroppedElements || takeElement)
+                            downstream.accept(t);
+                    }
+
+                    @Override
+                    public long getDropCount() {
+                        return dropCount;
+                    }
+                }
+                return new OpSink();
+            }
+        }
+        return new Op(upstream, StreamShape.INT_VALUE, DROP_FLAGS);
+    }
+
+    /**
+     * Appends a "dropWhile" operation to the provided LongStream.
+     *
+     * @param upstream a reference stream with element type T
+     * @param predicate the predicate that returns false to halt dropping.
+     */
+    static LongStream makeDropWhileLong(AbstractPipeline<?, Long, ?> upstream,
+                                        LongPredicate predicate) {
+        Objects.requireNonNull(predicate);
+        class Op extends LongPipeline.StatefulOp<Long> implements DropWhileOp<Long> {
+            public Op(AbstractPipeline<?, Long, ?> upstream, StreamShape inputShape, int opFlags) {
+                super(upstream, inputShape, opFlags);
+            }
+
+            @Override
+            <P_IN> Spliterator<Long> opEvaluateParallelLazy(PipelineHelper<Long> helper,
+                                                            Spliterator<P_IN> spliterator) {
+                if (StreamOpFlag.ORDERED.isKnown(helper.getStreamAndOpFlags())) {
+                    return opEvaluateParallel(helper, spliterator, Long[]::new)
+                            .spliterator();
+                }
+                else {
+                    return new UnorderedWhileSpliterator.OfLong.Dropping(
+                            (Spliterator.OfLong) helper.wrapSpliterator(spliterator), false, predicate);
+                }
+            }
+
+            @Override
+            <P_IN> Node<Long> opEvaluateParallel(PipelineHelper<Long> helper,
+                                                 Spliterator<P_IN> spliterator,
+                                                 IntFunction<Long[]> generator) {
+                return new DropWhileTask<>(this, helper, spliterator, generator)
+                        .invoke();
+            }
+
+            @Override
+            Sink<Long> opWrapSink(int flags, Sink<Long> sink) {
+                return opWrapSink(sink, false);
+            }
+
+            public DropWhileSink<Long> opWrapSink(Sink<Long> sink, boolean retainAndCountDroppedElements) {
+                class OpSink extends Sink.ChainedLong<Long> implements DropWhileSink<Long> {
+                    long dropCount;
+                    boolean take;
+
+                    OpSink() {
+                        super(sink);
+                    }
+
+                    @Override
+                    public void accept(long t) {
+                        boolean takeElement = take || (take = !predicate.test(t));
+
+                        // If ordered and element is dropped increment index
+                        // for possible future truncation
+                        if (retainAndCountDroppedElements && !takeElement)
+                            dropCount++;
+
+                        // If ordered need to process element, otherwise
+                        // skip if element is dropped
+                        if (retainAndCountDroppedElements || takeElement)
+                            downstream.accept(t);
+                    }
+
+                    @Override
+                    public long getDropCount() {
+                        return dropCount;
+                    }
+                }
+                return new OpSink();
+            }
+        }
+        return new Op(upstream, StreamShape.LONG_VALUE, DROP_FLAGS);
+    }
+
+    /**
+     * Appends a "dropWhile" operation to the provided DoubleStream.
+     *
+     * @param upstream a reference stream with element type T
+     * @param predicate the predicate that returns false to halt dropping.
+     */
+    static DoubleStream makeDropWhileDouble(AbstractPipeline<?, Double, ?> upstream,
+                                            DoublePredicate predicate) {
+        Objects.requireNonNull(predicate);
+        class Op extends DoublePipeline.StatefulOp<Double> implements DropWhileOp<Double> {
+            public Op(AbstractPipeline<?, Double, ?> upstream, StreamShape inputShape, int opFlags) {
+                super(upstream, inputShape, opFlags);
+            }
+
+            @Override
+            <P_IN> Spliterator<Double> opEvaluateParallelLazy(PipelineHelper<Double> helper,
+                                                              Spliterator<P_IN> spliterator) {
+                if (StreamOpFlag.ORDERED.isKnown(helper.getStreamAndOpFlags())) {
+                    return opEvaluateParallel(helper, spliterator, Double[]::new)
+                            .spliterator();
+                }
+                else {
+                    return new UnorderedWhileSpliterator.OfDouble.Dropping(
+                            (Spliterator.OfDouble) helper.wrapSpliterator(spliterator), false, predicate);
+                }
+            }
+
+            @Override
+            <P_IN> Node<Double> opEvaluateParallel(PipelineHelper<Double> helper,
+                                                   Spliterator<P_IN> spliterator,
+                                                   IntFunction<Double[]> generator) {
+                return new DropWhileTask<>(this, helper, spliterator, generator)
+                        .invoke();
+            }
+
+            @Override
+            Sink<Double> opWrapSink(int flags, Sink<Double> sink) {
+                return opWrapSink(sink, false);
+            }
+
+            public DropWhileSink<Double> opWrapSink(Sink<Double> sink, boolean retainAndCountDroppedElements) {
+                class OpSink extends Sink.ChainedDouble<Double> implements DropWhileSink<Double> {
+                    long dropCount;
+                    boolean take;
+
+                    OpSink() {
+                        super(sink);
+                    }
+
+                    @Override
+                    public void accept(double t) {
+                        boolean takeElement = take || (take = !predicate.test(t));
+
+                        // If ordered and element is dropped increment index
+                        // for possible future truncation
+                        if (retainAndCountDroppedElements && !takeElement)
+                            dropCount++;
+
+                        // If ordered need to process element, otherwise
+                        // skip if element is dropped
+                        if (retainAndCountDroppedElements || takeElement)
+                            downstream.accept(t);
+                    }
+
+                    @Override
+                    public long getDropCount() {
+                        return dropCount;
+                    }
+                }
+                return new OpSink();
+            }
+        }
+        return new Op(upstream, StreamShape.DOUBLE_VALUE, DROP_FLAGS);
+    }
+
+    //
+
+    /**
+     * A spliterator supporting takeWhile and dropWhile operations over an
+     * underlying spliterator whose covered elements have no encounter order.
+     * <p>
+     * Concrete subclasses of this spliterator support reference and primitive
+     * types for takeWhile and dropWhile.
+     * <p>
+     * For the takeWhile operation if during traversal taking completes then
+     * taking is cancelled globally for the splitting and traversal of all
+     * related spliterators.
+     * Cancellation is governed by a shared {@link AtomicBoolean} instance.  A
+     * spliterator in the process of taking when cancellation occurs will also
+     * be cancelled but not necessarily immediately.  To reduce contention on
+     * the {@link AtomicBoolean} instance, cancellation make be acted on after
+     * a small number of additional elements have been traversed.
+     * <p>
+     * For the dropWhile operation if during traversal dropping completes for
+     * some, but not all elements, then it is cancelled globally for the
+     * traversal of all related spliterators (splitting is not cancelled).
+     * Cancellation is governed in the same manner as for the takeWhile
+     * operation.
+     *
+     * @param <T> the type of elements returned by this spliterator
+     * @param <T_SPLITR> the type of the spliterator
+     */
+    static abstract class UnorderedWhileSpliterator<T, T_SPLITR extends Spliterator<T>> implements Spliterator<T> {
+        // Power of two constant minus one used for modulus of count
+        static final int CANCEL_CHECK_COUNT = (1 << 6) - 1;
+
+        // The underlying spliterator
+        final T_SPLITR s;
+        // True if no splitting should be performed, if true then
+        // this spliterator may be used for an underlying spliterator whose
+        // covered elements have an encounter order
+        // See use in stream take/dropWhile default default methods
+        final boolean noSplitting;
+        // True when operations are cancelled for all related spliterators
+        // For taking, spliterators cannot split or traversed
+        // For dropping, spliterators cannot be traversed
+        final AtomicBoolean cancel;
+        // True while taking or dropping should be performed when traversing
+        boolean takeOrDrop = true;
+        // The count of elements traversed
+        int count;
+
+        UnorderedWhileSpliterator(T_SPLITR s, boolean noSplitting) {
+            this.s = s;
+            this.noSplitting = noSplitting;
+            this.cancel = new AtomicBoolean();
+        }
+
+        UnorderedWhileSpliterator(T_SPLITR s, UnorderedWhileSpliterator<T, T_SPLITR> parent) {
+            this.s = s;
+            this.noSplitting = parent.noSplitting;
+            this.cancel = parent.cancel;
+        }
+
+        @Override
+        public long estimateSize() {
+            return s.estimateSize();
+        }
+
+        @Override
+        public int characteristics() {
+            // Size is not known
+            return s.characteristics() & ~(Spliterator.SIZED | Spliterator.SUBSIZED);
+        }
+
+        @Override
+        public long getExactSizeIfKnown() {
+            return -1L;
+        }
+
+        @Override
+        public Comparator<? super T> getComparator() {
+            return s.getComparator();
+        }
+
+        @Override
+        public T_SPLITR trySplit() {
+            @SuppressWarnings("unchecked")
+            T_SPLITR ls = noSplitting ? null : (T_SPLITR) s.trySplit();
+            return ls != null ? makeSpliterator(ls) : null;
+        }
+
+        boolean checkCancelOnCount() {
+            return count != 0 || !cancel.get();
+        }
+
+        abstract T_SPLITR makeSpliterator(T_SPLITR s);
+
+        static abstract class OfRef<T> extends UnorderedWhileSpliterator<T, Spliterator<T>> implements Consumer<T> {
+            final Predicate<? super T> p;
+            T t;
+
+            OfRef(Spliterator<T> s, boolean noSplitting, Predicate<? super T> p) {
+                super(s, noSplitting);
+                this.p = p;
+            }
+
+            OfRef(Spliterator<T> s, OfRef<T> parent) {
+                super(s, parent);
+                this.p = parent.p;
+            }
+
+            @Override
+            public void accept(T t) {
+                count = (count + 1) & CANCEL_CHECK_COUNT;
+                this.t = t;
+            }
+
+            static final class Taking<T> extends OfRef<T> {
+                Taking(Spliterator<T> s, boolean noSplitting, Predicate<? super T> p) {
+                    super(s, noSplitting, p);
+                }
+
+                Taking(Spliterator<T> s, Taking<T> parent) {
+                    super(s, parent);
+                }
+
+                @Override
+                public boolean tryAdvance(Consumer<? super T> action) {
+                    boolean test = true;
+                    if (takeOrDrop &&               // If can take
+                        checkCancelOnCount() && // and if not cancelled
+                        s.tryAdvance(this) &&   // and if advanced one element
+                        (test = p.test(t))) {   // and test on element passes
+                        action.accept(t);           // then accept element
+                        return true;
+                    }
+                    else {
+                        // Taking is finished
+                        takeOrDrop = false;
+                        // Cancel all further traversal and splitting operations
+                        // only if test of element failed (short-circuited)
+                        if (!test)
+                            cancel.set(true);
+                        return false;
+                    }
+                }
+
+                @Override
+                public Spliterator<T> trySplit() {
+                    // Do not split if all operations are cancelled
+                    return cancel.get() ? null : super.trySplit();
+                }
+
+                @Override
+                Spliterator<T> makeSpliterator(Spliterator<T> s) {
+                    return new Taking<>(s, this);
+                }
+            }
+
+            static final class Dropping<T> extends OfRef<T> {
+                Dropping(Spliterator<T> s, boolean noSplitting, Predicate<? super T> p) {
+                    super(s, noSplitting, p);
+                }
+
+                Dropping(Spliterator<T> s, Dropping<T> parent) {
+                    super(s, parent);
+                }
+
+                @Override
+                public boolean tryAdvance(Consumer<? super T> action) {
+                    if (takeOrDrop) {
+                        takeOrDrop = false;
+                        boolean adv;
+                        boolean dropped = false;
+                        while ((adv = s.tryAdvance(this)) &&  // If advanced one element
+                               checkCancelOnCount() &&        // and if not cancelled
+                               p.test(t)) {                   // and test on element passes
+                            dropped = true;                   // then drop element
+                        }
+
+                        // Report advanced element, if any
+                        if (adv) {
+                            // Cancel all further dropping if one or more elements
+                            // were previously dropped
+                            if (dropped)
+                                cancel.set(true);
+                            action.accept(t);
+                        }
+                        return adv;
+                    }
+                    else {
+                        return s.tryAdvance(action);
+                    }
+                }
+
+                @Override
+                Spliterator<T> makeSpliterator(Spliterator<T> s) {
+                    return new Dropping<>(s, this);
+                }
+            }
+        }
+
+        static abstract class OfInt extends UnorderedWhileSpliterator<Integer, Spliterator.OfInt> implements IntConsumer, Spliterator.OfInt {
+            final IntPredicate p;
+            int t;
+
+            OfInt(Spliterator.OfInt s, boolean noSplitting, IntPredicate p) {
+                super(s, noSplitting);
+                this.p = p;
+            }
+
+            OfInt(Spliterator.OfInt s, UnorderedWhileSpliterator.OfInt parent) {
+                super(s, parent);
+                this.p = parent.p;
+            }
+
+            @Override
+            public void accept(int t) {
+                count = (count + 1) & CANCEL_CHECK_COUNT;
+                this.t = t;
+            }
+
+            static final class Taking extends UnorderedWhileSpliterator.OfInt {
+                Taking(Spliterator.OfInt s, boolean noSplitting, IntPredicate p) {
+                    super(s, noSplitting, p);
+                }
+
+                Taking(Spliterator.OfInt s, UnorderedWhileSpliterator.OfInt parent) {
+                    super(s, parent);
+                }
+
+                @Override
+                public boolean tryAdvance(IntConsumer action) {
+                    boolean test = true;
+                    if (takeOrDrop &&               // If can take
+                        checkCancelOnCount() && // and if not cancelled
+                        s.tryAdvance(this) &&   // and if advanced one element
+                        (test = p.test(t))) {   // and test on element passes
+                        action.accept(t);           // then accept element
+                        return true;
+                    }
+                    else {
+                        // Taking is finished
+                        takeOrDrop = false;
+                        // Cancel all further traversal and splitting operations
+                        // only if test of element failed (short-circuited)
+                        if (!test)
+                            cancel.set(true);
+                        return false;
+                    }
+                }
+
+                @Override
+                public Spliterator.OfInt trySplit() {
+                    // Do not split if all operations are cancelled
+                    return cancel.get() ? null : super.trySplit();
+                }
+
+                @Override
+                Spliterator.OfInt makeSpliterator(Spliterator.OfInt s) {
+                    return new Taking(s, this);
+                }
+            }
+
+            static final class Dropping extends UnorderedWhileSpliterator.OfInt {
+                Dropping(Spliterator.OfInt s, boolean noSplitting, IntPredicate p) {
+                    super(s, noSplitting, p);
+                }
+
+                Dropping(Spliterator.OfInt s, UnorderedWhileSpliterator.OfInt parent) {
+                    super(s, parent);
+                }
+
+                @Override
+                public boolean tryAdvance(IntConsumer action) {
+                    if (takeOrDrop) {
+                        takeOrDrop = false;
+                        boolean adv;
+                        boolean dropped = false;
+                        while ((adv = s.tryAdvance(this)) &&  // If advanced one element
+                               checkCancelOnCount() &&        // and if not cancelled
+                               p.test(t)) {                   // and test on element passes
+                            dropped = true;                   // then drop element
+                        }
+
+                        // Report advanced element, if any
+                        if (adv) {
+                            // Cancel all further dropping if one or more elements
+                            // were previously dropped
+                            if (dropped)
+                                cancel.set(true);
+                            action.accept(t);
+                        }
+                        return adv;
+                    }
+                    else {
+                        return s.tryAdvance(action);
+                    }
+                }
+
+                @Override
+                Spliterator.OfInt makeSpliterator(Spliterator.OfInt s) {
+                    return new Dropping(s, this);
+                }
+            }
+        }
+
+        static abstract class OfLong extends UnorderedWhileSpliterator<Long, Spliterator.OfLong> implements LongConsumer, Spliterator.OfLong {
+            final LongPredicate p;
+            long t;
+
+            OfLong(Spliterator.OfLong s, boolean noSplitting, LongPredicate p) {
+                super(s, noSplitting);
+                this.p = p;
+            }
+
+            OfLong(Spliterator.OfLong s, UnorderedWhileSpliterator.OfLong parent) {
+                super(s, parent);
+                this.p = parent.p;
+            }
+
+            @Override
+            public void accept(long t) {
+                count = (count + 1) & CANCEL_CHECK_COUNT;
+                this.t = t;
+            }
+
+            static final class Taking extends UnorderedWhileSpliterator.OfLong {
+                Taking(Spliterator.OfLong s, boolean noSplitting, LongPredicate p) {
+                    super(s, noSplitting, p);
+                }
+
+                Taking(Spliterator.OfLong s, UnorderedWhileSpliterator.OfLong parent) {
+                    super(s, parent);
+                }
+
+                @Override
+                public boolean tryAdvance(LongConsumer action) {
+                    boolean test = true;
+                    if (takeOrDrop &&               // If can take
+                        checkCancelOnCount() && // and if not cancelled
+                        s.tryAdvance(this) &&   // and if advanced one element
+                        (test = p.test(t))) {   // and test on element passes
+                        action.accept(t);           // then accept element
+                        return true;
+                    }
+                    else {
+                        // Taking is finished
+                        takeOrDrop = false;
+                        // Cancel all further traversal and splitting operations
+                        // only if test of element failed (short-circuited)
+                        if (!test)
+                            cancel.set(true);
+                        return false;
+                    }
+                }
+
+                @Override
+                public Spliterator.OfLong trySplit() {
+                    // Do not split if all operations are cancelled
+                    return cancel.get() ? null : super.trySplit();
+                }
+
+                @Override
+                Spliterator.OfLong makeSpliterator(Spliterator.OfLong s) {
+                    return new Taking(s, this);
+                }
+            }
+
+            static final class Dropping extends UnorderedWhileSpliterator.OfLong {
+                Dropping(Spliterator.OfLong s, boolean noSplitting, LongPredicate p) {
+                    super(s, noSplitting, p);
+                }
+
+                Dropping(Spliterator.OfLong s, UnorderedWhileSpliterator.OfLong parent) {
+                    super(s, parent);
+                }
+
+                @Override
+                public boolean tryAdvance(LongConsumer action) {
+                    if (takeOrDrop) {
+                        takeOrDrop = false;
+                        boolean adv;
+                        boolean dropped = false;
+                        while ((adv = s.tryAdvance(this)) &&  // If advanced one element
+                               checkCancelOnCount() &&        // and if not cancelled
+                               p.test(t)) {                   // and test on element passes
+                            dropped = true;                   // then drop element
+                        }
+
+                        // Report advanced element, if any
+                        if (adv) {
+                            // Cancel all further dropping if one or more elements
+                            // were previously dropped
+                            if (dropped)
+                                cancel.set(true);
+                            action.accept(t);
+                        }
+                        return adv;
+                    }
+                    else {
+                        return s.tryAdvance(action);
+                    }
+                }
+
+                @Override
+                Spliterator.OfLong makeSpliterator(Spliterator.OfLong s) {
+                    return new Dropping(s, this);
+                }
+            }
+        }
+
+        static abstract class OfDouble extends UnorderedWhileSpliterator<Double, Spliterator.OfDouble> implements DoubleConsumer, Spliterator.OfDouble {
+            final DoublePredicate p;
+            double t;
+
+            OfDouble(Spliterator.OfDouble s, boolean noSplitting, DoublePredicate p) {
+                super(s, noSplitting);
+                this.p = p;
+            }
+
+            OfDouble(Spliterator.OfDouble s, UnorderedWhileSpliterator.OfDouble parent) {
+                super(s, parent);
+                this.p = parent.p;
+            }
+
+            @Override
+            public void accept(double t) {
+                count = (count + 1) & CANCEL_CHECK_COUNT;
+                this.t = t;
+            }
+
+            static final class Taking extends UnorderedWhileSpliterator.OfDouble {
+                Taking(Spliterator.OfDouble s, boolean noSplitting, DoublePredicate p) {
+                    super(s, noSplitting, p);
+                }
+
+                Taking(Spliterator.OfDouble s, UnorderedWhileSpliterator.OfDouble parent) {
+                    super(s, parent);
+                }
+
+                @Override
+                public boolean tryAdvance(DoubleConsumer action) {
+                    boolean test = true;
+                    if (takeOrDrop &&               // If can take
+                        checkCancelOnCount() && // and if not cancelled
+                        s.tryAdvance(this) &&   // and if advanced one element
+                        (test = p.test(t))) {   // and test on element passes
+                        action.accept(t);           // then accept element
+                        return true;
+                    }
+                    else {
+                        // Taking is finished
+                        takeOrDrop = false;
+                        // Cancel all further traversal and splitting operations
+                        // only if test of element failed (short-circuited)
+                        if (!test)
+                            cancel.set(true);
+                        return false;
+                    }
+                }
+
+                @Override
+                public Spliterator.OfDouble trySplit() {
+                    // Do not split if all operations are cancelled
+                    return cancel.get() ? null : super.trySplit();
+                }
+
+                @Override
+                Spliterator.OfDouble makeSpliterator(Spliterator.OfDouble s) {
+                    return new Taking(s, this);
+                }
+            }
+
+            static final class Dropping extends UnorderedWhileSpliterator.OfDouble {
+                Dropping(Spliterator.OfDouble s, boolean noSplitting, DoublePredicate p) {
+                    super(s, noSplitting, p);
+                }
+
+                Dropping(Spliterator.OfDouble s, UnorderedWhileSpliterator.OfDouble parent) {
+                    super(s, parent);
+                }
+
+                @Override
+                public boolean tryAdvance(DoubleConsumer action) {
+                    if (takeOrDrop) {
+                        takeOrDrop = false;
+                        boolean adv;
+                        boolean dropped = false;
+                        while ((adv = s.tryAdvance(this)) &&  // If advanced one element
+                               checkCancelOnCount() &&        // and if not cancelled
+                               p.test(t)) {                   // and test on element passes
+                            dropped = true;                   // then drop element
+                        }
+
+                        // Report advanced element, if any
+                        if (adv) {
+                            // Cancel all further dropping if one or more elements
+                            // were previously dropped
+                            if (dropped)
+                                cancel.set(true);
+                            action.accept(t);
+                        }
+                        return adv;
+                    }
+                    else {
+                        return s.tryAdvance(action);
+                    }
+                }
+
+                @Override
+                Spliterator.OfDouble makeSpliterator(Spliterator.OfDouble s) {
+                    return new Dropping(s, this);
+                }
+            }
+        }
+    }
+
+
+    //
+
+    /**
+     * {@code ForkJoinTask} implementing takeWhile computation.
+     * <p>
+     * If the pipeline has encounter order then all tasks to the right of
+     * a task where traversal was short-circuited are cancelled.
+     * The results of completed (and cancelled) tasks are discarded.
+     * The result of merging a short-circuited left task and right task (which
+     * may or may not be short-circuited) is that left task.
+     * <p>
+     * If the pipeline has no encounter order then all tasks to the right of
+     * a task where traversal was short-circuited are cancelled.
+     * The results of completed (and possibly cancelled) tasks are not
+     * discarded, as there is no need to throw away computed results.
+     * The result of merging does not change if a left task was
+     * short-circuited.
+     * No attempt is made, once a leaf task stopped taking, for it to cancel
+     * all other tasks, and further more, short-circuit the computation with its
+     * result.
+     *
+     * @param <P_IN> Input element type to the stream pipeline
+     * @param <P_OUT> Output element type from the stream pipeline
+     */
+    @SuppressWarnings("serial")
+    private static final class TakeWhileTask<P_IN, P_OUT>
+            extends AbstractShortCircuitTask<P_IN, P_OUT, Node<P_OUT>, TakeWhileTask<P_IN, P_OUT>> {
+        private final AbstractPipeline<P_OUT, P_OUT, ?> op;
+        private final IntFunction<P_OUT[]> generator;
+        private final boolean isOrdered;
+        private long thisNodeSize;
+        // True if a short-circuited
+        private boolean shortCircuited;
+        // True if completed, must be set after the local result
+        private volatile boolean completed;
+
+        TakeWhileTask(AbstractPipeline<P_OUT, P_OUT, ?> op,
+                      PipelineHelper<P_OUT> helper,
+                      Spliterator<P_IN> spliterator,
+                      IntFunction<P_OUT[]> generator) {
+            super(helper, spliterator);
+            this.op = op;
+            this.generator = generator;
+            this.isOrdered = StreamOpFlag.ORDERED.isKnown(helper.getStreamAndOpFlags());
+        }
+
+        TakeWhileTask(TakeWhileTask<P_IN, P_OUT> parent, Spliterator<P_IN> spliterator) {
+            super(parent, spliterator);
+            this.op = parent.op;
+            this.generator = parent.generator;
+            this.isOrdered = parent.isOrdered;
+        }
+
+        @Override
+        protected TakeWhileTask<P_IN, P_OUT> makeChild(Spliterator<P_IN> spliterator) {
+            return new TakeWhileTask<>(this, spliterator);
+        }
+
+        @Override
+        protected final Node<P_OUT> getEmptyResult() {
+            return Nodes.emptyNode(op.getOutputShape());
+        }
+
+        @Override
+        protected final Node<P_OUT> doLeaf() {
+            Node.Builder<P_OUT> builder = helper.makeNodeBuilder(-1, generator);
+            Sink<P_OUT> s = op.opWrapSink(helper.getStreamAndOpFlags(), builder);
+
+            if (shortCircuited = helper.copyIntoWithCancel(helper.wrapSink(s), spliterator)) {
+                // Cancel later nodes if the predicate returned false
+                // during traversal
+                cancelLaterNodes();
+            }
+
+            Node<P_OUT> node = builder.build();
+            thisNodeSize = node.count();
+            return node;
+        }
+
+        @Override
+        public final void onCompletion(CountedCompleter<?> caller) {
+            if (!isLeaf()) {
+                Node<P_OUT> result;
+                shortCircuited = leftChild.shortCircuited | rightChild.shortCircuited;
+                if (isOrdered && canceled) {
+                    thisNodeSize = 0;
+                    result = getEmptyResult();
+                }
+                else if (isOrdered && leftChild.shortCircuited) {
+                    // If taking finished on the left node then
+                    // use the left node result
+                    thisNodeSize = leftChild.thisNodeSize;
+                    result = leftChild.getLocalResult();
+                }
+                else {
+                    thisNodeSize = leftChild.thisNodeSize + rightChild.thisNodeSize;
+                    result = merge();
+                }
+
+                setLocalResult(result);
+            }
+
+            completed = true;
+            super.onCompletion(caller);
+        }
+
+        Node<P_OUT> merge() {
+            if (leftChild.thisNodeSize == 0) {
+                // If the left node size is 0 then
+                // use the right node result
+                return rightChild.getLocalResult();
+            }
+            else if (rightChild.thisNodeSize == 0) {
+                // If the right node size is 0 then
+                // use the left node result
+                return leftChild.getLocalResult();
+            }
+            else {
+                // Combine the left and right nodes
+                return Nodes.conc(op.getOutputShape(),
+                                  leftChild.getLocalResult(), rightChild.getLocalResult());
+            }
+        }
+
+        @Override
+        protected void cancel() {
+            super.cancel();
+            if (isOrdered && completed)
+                // If the task is completed then clear the result, if any
+                // to aid GC
+                setLocalResult(getEmptyResult());
+        }
+    }
+
+    /**
+     * {@code ForkJoinTask} implementing dropWhile computation.
+     * <p>
+     * If the pipeline has encounter order then each leaf task will not
+     * drop elements but will obtain a count of the elements that would have
+     * been otherwise dropped. That count is used as an index to track
+     * elements to be dropped. Merging will update the index so it corresponds
+     * to the index that is the end of the global prefix of elements to be
+     * dropped. The root is truncated according to that index.
+     * <p>
+     * If the pipeline has no encounter order then each leaf task will drop
+     * elements. Leaf tasks are ordinarily merged. No truncation of the root
+     * node is required.
+     * No attempt is made, once a leaf task stopped dropping, for it to cancel
+     * all other tasks, and further more, short-circuit the computation with
+     * its result.
+     *
+     * @param <P_IN> Input element type to the stream pipeline
+     * @param <P_OUT> Output element type from the stream pipeline
+     */
+    @SuppressWarnings("serial")
+    private static final class DropWhileTask<P_IN, P_OUT>
+            extends AbstractTask<P_IN, P_OUT, Node<P_OUT>, DropWhileTask<P_IN, P_OUT>> {
+        private final AbstractPipeline<P_OUT, P_OUT, ?> op;
+        private final IntFunction<P_OUT[]> generator;
+        private final boolean isOrdered;
+        private long thisNodeSize;
+        // The index from which elements of the node should be taken
+        // i.e. the node should be truncated from [takeIndex, thisNodeSize)
+        // Equivalent to the count of dropped elements
+        private long index;
+
+        DropWhileTask(AbstractPipeline<P_OUT, P_OUT, ?> op,
+                      PipelineHelper<P_OUT> helper,
+                      Spliterator<P_IN> spliterator,
+                      IntFunction<P_OUT[]> generator) {
+            super(helper, spliterator);
+            assert op instanceof DropWhileOp;
+            this.op = op;
+            this.generator = generator;
+            this.isOrdered = StreamOpFlag.ORDERED.isKnown(helper.getStreamAndOpFlags());
+        }
+
+        DropWhileTask(DropWhileTask<P_IN, P_OUT> parent, Spliterator<P_IN> spliterator) {
+            super(parent, spliterator);
+            this.op = parent.op;
+            this.generator = parent.generator;
+            this.isOrdered = parent.isOrdered;
+        }
+
+        @Override
+        protected DropWhileTask<P_IN, P_OUT> makeChild(Spliterator<P_IN> spliterator) {
+            return new DropWhileTask<>(this, spliterator);
+        }
+
+        @Override
+        protected final Node<P_OUT> doLeaf() {
+            boolean isChild = !isRoot();
+            // If this not the root and pipeline is ordered and size is known
+            // then pre-size the builder
+            long sizeIfKnown = isChild && isOrdered && StreamOpFlag.SIZED.isPreserved(op.sourceOrOpFlags)
+                               ? op.exactOutputSizeIfKnown(spliterator)
+                               : -1;
+            Node.Builder<P_OUT> builder = helper.makeNodeBuilder(sizeIfKnown, generator);
+            @SuppressWarnings("unchecked")
+            DropWhileOp<P_OUT> dropOp = (DropWhileOp<P_OUT>) op;
+            // If this leaf is the root then there is no merging on completion
+            // and there is no need to retain dropped elements
+            DropWhileSink<P_OUT> s = dropOp.opWrapSink(builder, isOrdered && isChild);
+            helper.wrapAndCopyInto(s, spliterator);
+
+            Node<P_OUT> node = builder.build();
+            thisNodeSize = node.count();
+            index = s.getDropCount();
+            return node;
+        }
+
+        @Override
+        public final void onCompletion(CountedCompleter<?> caller) {
+            if (!isLeaf()) {
+                if (isOrdered) {
+                    index = leftChild.index;
+                    // If a contiguous sequence of dropped elements
+                    // include those of the right node, if any
+                    if (index == leftChild.thisNodeSize)
+                        index += rightChild.index;
+                }
+
+                thisNodeSize = leftChild.thisNodeSize + rightChild.thisNodeSize;
+                Node<P_OUT> result = merge();
+                setLocalResult(isRoot() ? doTruncate(result) : result);
+            }
+
+            super.onCompletion(caller);
+        }
+
+        private Node<P_OUT> merge() {
+            if (leftChild.thisNodeSize == 0) {
+                // If the left node size is 0 then
+                // use the right node result
+                return rightChild.getLocalResult();
+            }
+            else if (rightChild.thisNodeSize == 0) {
+                // If the right node size is 0 then
+                // use the left node result
+                return leftChild.getLocalResult();
+            }
+            else {
+                // Combine the left and right nodes
+                return Nodes.conc(op.getOutputShape(),
+                                  leftChild.getLocalResult(), rightChild.getLocalResult());
+            }
+        }
+
+        private Node<P_OUT> doTruncate(Node<P_OUT> input) {
+            return isOrdered
+                   ? input.truncate(index, input.count(), generator)
+                   : input;
+        }
+    }
+}
--- a/jdk/src/java.base/share/classes/java/util/zip/CRC32.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/zip/CRC32.java	Wed Jul 05 20:42:36 2017 +0200
@@ -26,7 +26,10 @@
 package java.util.zip;
 
 import java.nio.ByteBuffer;
+import java.util.Objects;
+
 import sun.nio.ch.DirectBuffer;
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 /**
  * A class that can be used to compute the CRC-32 of a data stream.
@@ -123,9 +126,49 @@
         return (long)crc & 0xffffffffL;
     }
 
+    @HotSpotIntrinsicCandidate
     private native static int update(int crc, int b);
-    private native static int updateBytes(int crc, byte[] b, int off, int len);
+
+    private static int updateBytes(int crc, byte[] b, int off, int len) {
+        updateBytesCheck(b, off, len);
+        return updateBytes0(crc, b, off, len);
+    }
+
+    @HotSpotIntrinsicCandidate
+    private native static int updateBytes0(int crc, byte[] b, int off, int len);
+
+    private static void updateBytesCheck(byte[] b, int off, int len) {
+        if (len <= 0) {
+            return;  // not an error because updateBytesImpl won't execute if len <= 0
+        }
+
+        Objects.requireNonNull(b);
+
+        if (off < 0 || off >= b.length) {
+            throw new ArrayIndexOutOfBoundsException(off);
+        }
 
-    private native static int updateByteBuffer(int adler, long addr,
-                                               int off, int len);
+        int endIndex = off + len - 1;
+        if (endIndex < 0 || endIndex >= b.length) {
+            throw new ArrayIndexOutOfBoundsException(endIndex);
+        }
+    }
+
+    private static int updateByteBuffer(int alder, long addr,
+                                        int off, int len) {
+        updateByteBufferCheck(addr);
+        return updateByteBuffer0(alder, addr, off, len);
+    }
+
+    @HotSpotIntrinsicCandidate
+    private native static int updateByteBuffer0(int alder, long addr,
+                                                int off, int len);
+
+    private static void updateByteBufferCheck(long addr) {
+        // Performs only a null check because bounds checks
+        // are not easy to do on raw addresses.
+        if (addr == 0L) {
+            throw new NullPointerException();
+        }
+    }
 }
--- a/jdk/src/java.base/share/classes/java/util/zip/CRC32C.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/zip/CRC32C.java	Wed Jul 05 20:42:36 2017 +0200
@@ -26,6 +26,8 @@
 
 import java.nio.ByteBuffer;
 import java.nio.ByteOrder;
+
+import jdk.internal.HotSpotIntrinsicCandidate;
 import sun.misc.Unsafe;
 import sun.nio.ch.DirectBuffer;
 
@@ -204,6 +206,7 @@
     /**
      * Updates the CRC-32C checksum with the specified array of bytes.
      */
+    @HotSpotIntrinsicCandidate
     private static int updateBytes(int crc, byte[] b, int off, int end) {
 
         // Do only byte reads for arrays so short they can't be aligned
@@ -278,6 +281,7 @@
     /**
      * Updates the CRC-32C checksum reading from the specified address.
      */
+    @HotSpotIntrinsicCandidate
     private static int updateDirectByteBuffer(int crc, long address,
                                               int off, int end) {
 
--- a/jdk/src/java.base/share/classes/javax/crypto/spec/SecretKeySpec.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/javax/crypto/spec/SecretKeySpec.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1998, 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
@@ -25,6 +25,7 @@
 
 package javax.crypto.spec;
 
+import java.security.MessageDigest;
 import java.security.spec.KeySpec;
 import java.util.Locale;
 import javax.crypto.SecretKey;
@@ -228,6 +229,6 @@
 
         byte[] thatKey = ((SecretKey)obj).getEncoded();
 
-        return java.util.Arrays.equals(this.key, thatKey);
+        return MessageDigest.isEqual(this.key, thatKey);
     }
 }
--- a/jdk/src/java.base/share/classes/javax/net/ssl/SSLEngineResult.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/javax/net/ssl/SSLEngineResult.java	Wed Jul 05 20:42:36 2017 +0200
@@ -156,8 +156,10 @@
          * This value is used to indicate that not-yet-interpreted data
          * has been previously received from the remote side, and does
          * not need to be received again.
+         * <P>
+         * This handshake status only applies to DTLS.
          *
-         * @since   1.9
+         * @since   9
          */
         NEED_UNWRAP_AGAIN;
     }
@@ -219,7 +221,7 @@
      *          arguments are null, or if {@code bytesConsumed} or
      *          {@code bytesProduced} is negative
      *
-     * @since   1.9
+     * @since   9
      */
     public SSLEngineResult(Status status, HandshakeStatus handshakeStatus,
             int bytesConsumed, int bytesProduced, long sequenceNumber) {
@@ -302,7 +304,7 @@
      *
      * @see     java.lang.Long#compareUnsigned(long, long)
      *
-     * @since   1.9
+     * @since   9
      */
     final public long sequenceNumber() {
         return sequenceNumber;
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/HotSpotIntrinsicCandidate.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,125 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.internal;
+
+import java.lang.annotation.*;
+
+/**
+ * The {@code @HotSpotIntrinsicCandidate} annotation is specific to the Oracle Java
+ * HotSpot Virtual Machine implementation and indicates that an annotated method
+ * may be (but is not guaranteed to be) intrinsified by the HotSpot VM. A method
+ * is intrinsified if the HotSpot VM replaces the annotated method with hand-written
+ * assembly and/or hand-written compiler IR -- a compiler intrinsic -- to improve
+ * performance. The {@code @HotSpotIntrinsicCandidate} annotation is internal to the
+ * Java libraries and is therefore not supposed to have any relevance for application
+ * code.
+ *
+ * Maintainers of the Java libraries must consider the following when
+ * modifying methods annotated with {@code @HotSpotIntrinsicCandidate}.
+ *
+ * <ul>
+ * <li>When modifying a method annotated with {@code @HotSpotIntrinsicCandidate},
+ * the corresponding intrinsic code in the HotSpot VM implementation must be
+ * updated to match the semantics of the annotated method.</li>
+ * <li>For some annotated methods, the corresponding intrinsic may omit some low-level
+ * checks that would be performed as a matter of course if the intrinsic is implemented
+ * using Java bytecodes. This is because individual Java bytecodes implicitly check
+ * for exceptions like {@code NullPointerException} and {@code ArrayStoreException}.
+ * If such a method is replaced by an intrinsic coded in assembly language, any
+ * checks performed as a matter of normal bytecode operation must be performed
+ * before entry into the assembly code. These checks must be performed, as
+ * appropriate, on all arguments to the intrinsic, and on other values (if any) obtained
+ * by the intrinsic through those arguments. The checks may be deduced by inspecting
+ * the non-intrinsic Java code for the method, and determining exactly which exceptions
+ * may be thrown by the code, including undeclared implicit {@code RuntimeException}s.
+ * Therefore, depending on the data accesses performed by the intrinsic,
+ * the checks may include:
+ *
+ *  <ul>
+ *  <li>null checks on references</li>
+ *  <li>range checks on primitive values used as array indexes</li>
+ *  <li>other validity checks on primitive values (e.g., for divide-by-zero conditions)</li>
+ *  <li>store checks on reference values stored into arrays</li>
+ *  <li>array length checks on arrays indexed from within the intrinsic</li>
+ *  <li>reference casts (when formal parameters are {@code Object} or some other weak type)</li>
+ *  </ul>
+ *
+ * </li>
+ *
+ * <li>Note that the receiver value ({@code this}) is passed as a extra argument
+ * to all non-static methods. If a non-static method is an intrinsic, the receiver
+ * value does not need a null check, but (as stated above) any values loaded by the
+ * intrinsic from object fields must also be checked. As a matter of clarity, it is
+ * better to make intrinisics be static methods, to make the dependency on {@code this}
+ * clear. Also, it is better to explicitly load all required values from object
+ * fields before entering the intrinsic code, and pass those values as explicit arguments.
+ * First, this may be necessary for null checks (or other checks). Second, if the
+ * intrinsic reloads the values from fields and operates on those without checks,
+ * race conditions may be able to introduce unchecked invalid values into the intrinsic.
+ * If the intrinsic needs to store a value back to an object field, that value should be
+ * returned explicitly from the intrinsic; if there are multiple return values, coders
+ * should consider buffering them in an array. Removing field access from intrinsics
+ * not only clarifies the interface with between the JVM and JDK; it also helps decouple
+ * the HotSpot and JDK implementations, since if JDK code before and after the intrinsic
+ * manages all field accesses, then intrinsics can be coded to be agnostic of object
+ * layouts.</li>
+ *
+ * Maintainers of the HotSpot VM must consider the following when modifying
+ * intrinsics.
+ *
+ * <ul>
+ * <li>When adding a new intrinsic, make sure that the corresponding method
+ * in the Java libraries is annotated with {@code @HotSpotIntrinsicCandidate}
+ * and that all possible call sequences that result in calling the intrinsic contain
+ * the checks omitted by the intrinsic (if any).</li>
+ * <li>When modifying an existing intrinsic, the Java libraries must be updated
+ * to match the semantics of the intrinsic and to execute all checks omitted
+ * by the intrinsic (if any).</li>
+ * </ul>
+ *
+ * Persons not directly involved with maintaining the Java libraries or the
+ * HotSpot VM can safely ignore the fact that a method is annotated with
+ * {@code @HotSpotIntrinsicCandidate}.
+ *
+ * The HotSpot VM defines (internally) a list of intrinsics. Not all intrinsic
+ * are available on all platforms supported by the HotSpot VM. Furthermore,
+ * the availability of an intrinsic on a given platform depends on the
+ * configuration of the HotSpot VM (e.g., the set of VM flags enabled).
+ * Therefore, annotating a method with {@code @HotSpotIntrinsicCandidate} does
+ * not guarantee that the marked method is intrinsified by the HotSpot VM.
+ *
+ * If the {@code CheckIntrinsics} VM flag is enabled, the HotSpot VM checks
+ * (when loading a class) that (1) all methods of that class that are also on
+ * the VM's list of intrinsics are annotated with {@code @HotSpotIntrinsicCandidate}
+ * and that (2) for all methods of that class annotated with
+ * {@code @HotSpotIntrinsicCandidate} there is an intrinsic in the list.
+ *
+ * @since 1.9
+ */
+@Target({ElementType.METHOD, ElementType.CONSTRUCTOR})
+@Retention(RetentionPolicy.RUNTIME)
+public @interface HotSpotIntrinsicCandidate {
+}
--- a/jdk/src/java.base/share/classes/jdk/internal/jimage/Archive.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/Archive.java	Wed Jul 05 20:42:36 2017 +0200
@@ -24,42 +24,95 @@
  */
 package jdk.internal.jimage;
 
+import java.io.IOException;
 import java.io.InputStream;
-import java.io.OutputStream;
-import java.nio.file.Path;
-import java.util.function.Consumer;
+import java.util.stream.Stream;
 
 /**
  * An Archive of all content, classes, resources, configuration files, and
  * other, for a module.
  */
 public interface Archive {
+
+    /**
+     * Entry is contained in an Archive
+     */
+    public abstract class Entry {
+
+        public static enum EntryType {
+
+            MODULE_NAME,
+            CLASS_OR_RESOURCE,
+            NATIVE_LIB,
+            NATIVE_CMD,
+            CONFIG,
+            SERVICE;
+        }
+
+        private final String name;
+        private final EntryType type;
+        private final Archive archive;
+        private final String path;
+
+        public Entry(Archive archive, String path, String name, EntryType type) {
+            this.archive = archive;
+            this.path = path;
+            this.name = name;
+            this.type = type;
+        }
+
+        public Archive archive() {
+            return archive;
+        }
+
+        public String path() {
+            return path;
+        }
+
+        public EntryType type() {
+            return type;
+        }
+
+        /**
+         * Returns the name of this entry.
+         */
+        public String name() {
+            return name;
+        }
+
+        @Override
+        public String toString() {
+            return "type " + type.name() + " path " + path;
+        }
+
+        /**
+         * Returns the number of uncompressed bytes for this entry.
+         */
+        public abstract long size();
+
+        public abstract InputStream stream() throws IOException;
+    }
+
     /**
      * The module name.
      */
     String moduleName();
 
     /**
-     * Visits all classes and resources.
+     * Stream of Entry.
+     * The stream of entries needs to be closed after use
+     * since it might cover lazy I/O based resources.
+     * So callers need to use a try-with-resources block.
      */
-    void visitResources(Consumer<Resource> consumer);
-
-    /**
-     * Visits all entries in the Archive.
-     */
-    void visitEntries(Consumer<Entry> consumer) ;
+    Stream<Entry> entries();
 
     /**
-     * An entries in the Archive.
+     * Open the archive
      */
-    interface Entry {
-        String getName();
-        InputStream getInputStream();
-        boolean isDirectory();
-    }
+    void open() throws IOException;
 
     /**
-     * A Consumer suitable for writing Entries from this Archive.
+     * Close the archive
      */
-    Consumer<Entry> defaultImageWriter(Path path, OutputStream out);
+    void close() throws IOException;
 }
--- a/jdk/src/java.base/share/classes/jdk/internal/jimage/BasicImageReader.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/BasicImageReader.java	Wed Jul 05 20:42:36 2017 +0200
@@ -24,63 +24,88 @@
  */
 package jdk.internal.jimage;
 
+import java.io.ByteArrayInputStream;
 import java.io.IOException;
+import java.io.File;
+import java.io.InputStream;
 import java.nio.ByteBuffer;
 import java.nio.ByteOrder;
 import java.nio.IntBuffer;
-import java.nio.MappedByteBuffer;
-import java.nio.channels.FileChannel;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.List;
+import java.util.Comparator;
+import java.util.stream.IntStream;
 
 public class BasicImageReader {
     private final String imagePath;
-    private final PReader preader;
+    private final ImageSubstrate substrate;
     private final ByteOrder byteOrder;
-    private final ImageHeader header;
-    private final int indexSize;
-    private final IntBuffer redirectBuffer;
-    private final IntBuffer offsetsBuffer;
-    private final ByteBuffer locationsBuffer;
-    private final ByteBuffer stringsBuffer;
-    private final ImageStrings strings;
+    private final ImageStringsReader strings;
 
-    protected BasicImageReader(String imagePath, ByteOrder byteOrder) throws IOException {
+    protected BasicImageReader(String imagePath, ByteOrder byteOrder)
+            throws IOException {
         this.imagePath = imagePath;
-        this.preader = PReader.open(imagePath);
+        this.substrate = openImageSubstrate(imagePath, byteOrder);
         this.byteOrder = byteOrder;
-        this.header = ImageHeader.readFrom(byteOrder, getIntBuffer(0, ImageHeader.getHeaderSize()));
-        this.indexSize = header.getIndexSize();
-        this.redirectBuffer = getIntBuffer(header.getRedirectOffset(), header.getRedirectSize());
-        this.offsetsBuffer = getIntBuffer(header.getOffsetsOffset(), header.getOffsetsSize());
-        this.locationsBuffer = getByteBuffer(header.getLocationsOffset(), header.getLocationsSize());
-        this.stringsBuffer = getByteBuffer(header.getStringsOffset(), header.getStringsSize());
-        this.strings = new ImageStrings(new ImageStream(stringsBuffer));
+        this.strings = new ImageStringsReader(this);
     }
 
     protected BasicImageReader(String imagePath) throws IOException {
         this(imagePath, ByteOrder.nativeOrder());
     }
 
+    private static ImageSubstrate openImageSubstrate(String imagePath, ByteOrder byteOrder)
+            throws IOException {
+        ImageSubstrate substrate;
+
+        try {
+            substrate = ImageNativeSubstrate.openImage(imagePath, byteOrder);
+        } catch (UnsatisfiedLinkError ex) {
+            substrate = ImageJavaSubstrate.openImage(imagePath, byteOrder);
+        }
+
+        return substrate;
+    }
+
     public static BasicImageReader open(String imagePath) throws IOException {
         return new BasicImageReader(imagePath, ByteOrder.nativeOrder());
     }
 
+    public static void releaseByteBuffer(ByteBuffer buffer) {
+        ImageBufferCache.releaseBuffer(buffer);
+    }
+
+    public ByteOrder getByteOrder() {
+        return byteOrder;
+    }
+
     public String imagePath() {
         return imagePath;
     }
 
+    public String imagePathName() {
+        int slash = imagePath().lastIndexOf(File.separator);
+
+        if (slash != -1) {
+            return imagePath().substring(slash + 1);
+        }
+
+        return imagePath();
+    }
+
     public boolean isOpen() {
-        return preader.isOpen();
+        return true;
     }
 
     public void close() throws IOException {
-        preader.close();
+        substrate.close();
     }
 
-    public ImageHeader getHeader() {
-        return header;
+    public ImageHeader getHeader() throws IOException {
+        return ImageHeader.readFrom(
+                getIndexIntBuffer(0, ImageHeader.getHeaderSize()));
+    }
+
+    public ImageStringsReader getStrings() {
+        return strings;
     }
 
     public ImageLocation findLocation(String name) {
@@ -92,148 +117,147 @@
     }
 
     public synchronized ImageLocation findLocation(UTF8String name) {
-        int count = header.getLocationCount();
-        int hash = name.hashCode() % count;
-        int redirect = getRedirect(hash);
-
-        if (redirect == 0) {
-            return null;
-        }
-
-        int index;
-
-        if (redirect < 0) {
-            // If no collision.
-            index = -redirect - 1;
-        } else {
-            // If collision, recompute hash code.
-            index = name.hashCode(redirect) % count;
-        }
-
-        int offset = getOffset(index);
-
-        if (offset == 0) {
-            return null;
-        }
-
-        ImageLocation location = getLocation(offset);
-
-        return location.verify(name) ? location : null;
+        return substrate.findLocation(name, strings);
     }
 
     public String[] getEntryNames() {
-        return getEntryNames(true);
-    }
-
-    public String[] getEntryNames(boolean sorted) {
-        int count = header.getLocationCount();
-        List<String> list = new ArrayList<>();
-
-        for (int i = 0; i < count; i++) {
-            int offset = getOffset(i);
-
-            if (offset != 0) {
-                ImageLocation location = ImageLocation.readFrom(locationsBuffer, offset, strings);
-                list.add(location.getFullnameString());
-            }
-        }
-
-        String[] array = list.toArray(new String[0]);
-
-        if (sorted) {
-            Arrays.sort(array);
-        }
-
-        return array;
+        return IntStream.of(substrate.attributeOffsets())
+                        .filter(o -> o != 0)
+                        .mapToObj(o -> ImageLocation.readFrom(this, o).getFullNameString())
+                        .sorted()
+                        .toArray(String[]::new);
     }
 
     protected ImageLocation[] getAllLocations(boolean sorted) {
-        int count = header.getLocationCount();
-        List<ImageLocation> list = new ArrayList<>();
-
-        for (int i = 0; i < count; i++) {
-            int offset = getOffset(i);
-
-            if (offset != 0) {
-                ImageLocation location = ImageLocation.readFrom(locationsBuffer, offset, strings);
-                list.add(location);
-            }
-        }
-
-        ImageLocation[] array = list.toArray(new ImageLocation[0]);
-
-        if (sorted) {
-            Arrays.sort(array, (ImageLocation loc1, ImageLocation loc2) ->
-                    loc1.getFullnameString().compareTo(loc2.getFullnameString()));
-        }
-
-        return array;
+        return IntStream.of(substrate.attributeOffsets())
+                        .filter(o -> o != 0)
+                        .mapToObj(o -> ImageLocation.readFrom(this, o))
+                        .sorted(Comparator.comparing(ImageLocation::getFullNameString))
+                        .toArray(ImageLocation[]::new);
     }
 
-    private IntBuffer getIntBuffer(long offset, long size) throws IOException {
-        MappedByteBuffer buffer = preader.channel().map(FileChannel.MapMode.READ_ONLY, offset, size);
+    private IntBuffer getIndexIntBuffer(long offset, long size)
+            throws IOException {
+        ByteBuffer buffer = substrate.getIndexBuffer(offset, size);
         buffer.order(byteOrder);
 
         return buffer.asIntBuffer();
     }
 
-    private ByteBuffer getByteBuffer(long offset, long size) throws IOException {
-        MappedByteBuffer buffer = preader.channel().map(FileChannel.MapMode.READ_ONLY, offset, size);
-        // order is not copied into the readonly copy.
-        ByteBuffer readOnly = buffer.asReadOnlyBuffer();
-        readOnly.order(byteOrder);
-        return readOnly;
+    ImageLocation getLocation(int offset) {
+        return ImageLocation.readFrom(this, offset);
     }
 
-    private int getRedirect(int index) {
-        return redirectBuffer.get(index);
-    }
-
-    private int getOffset(int index) {
-        return offsetsBuffer.get(index);
-    }
-
-    private ImageLocation getLocation(int offset) {
-        return ImageLocation.readFrom(locationsBuffer, offset, strings);
+    public long[] getAttributes(int offset) {
+        return substrate.getAttributes(offset);
     }
 
     public String getString(int offset) {
-        return strings.get(offset).toString();
+        return getUTF8String(offset).toString();
+    }
+
+    public UTF8String getUTF8String(int offset) {
+        return new UTF8String(substrate.getStringBytes(offset));
+    }
+
+    private byte[] getBufferBytes(ByteBuffer buffer, long size) {
+        assert size < Integer.MAX_VALUE;
+        byte[] bytes = new byte[(int)size];
+        buffer.get(bytes);
+
+        return bytes;
+    }
+
+    private byte[] getBufferBytes(long offset, long size) {
+        ByteBuffer buffer = substrate.getDataBuffer(offset, size);
+
+        return getBufferBytes(buffer, size);
     }
 
-    public byte[] getResource(ImageLocation loc) throws IOException {
+    public byte[] getResource(ImageLocation loc) {
+        long offset = loc.getContentOffset();
         long compressedSize = loc.getCompressedSize();
+        long uncompressedSize = loc.getUncompressedSize();
         assert compressedSize < Integer.MAX_VALUE;
+        assert uncompressedSize < Integer.MAX_VALUE;
+
+        if (substrate.supportsDataBuffer() && compressedSize == 0) {
+            return getBufferBytes(offset, uncompressedSize);
+        }
+
+        ByteBuffer uncompressedBuffer = ImageBufferCache.getBuffer(uncompressedSize);
+        boolean isRead;
 
-        if (compressedSize == 0) {
-            return preader.read((int)loc.getUncompressedSize(),
-                                indexSize + loc.getContentOffset());
+        if (compressedSize != 0) {
+            ByteBuffer compressedBuffer = ImageBufferCache.getBuffer(compressedSize);
+            isRead = substrate.read(offset, compressedBuffer, compressedSize,
+                                          uncompressedBuffer, uncompressedSize);
+            ImageBufferCache.releaseBuffer(compressedBuffer);
         } else {
-            byte[] buf = preader.read((int)compressedSize,
-                                      indexSize + loc.getContentOffset());
-            return ImageFile.Compressor.decompress(buf);
+            isRead = substrate.read(offset, uncompressedBuffer, uncompressedSize);
         }
+
+        byte[] bytes = isRead ? getBufferBytes(uncompressedBuffer,
+                                               uncompressedSize) : null;
+
+        ImageBufferCache.releaseBuffer(uncompressedBuffer);
+
+        return bytes;
     }
 
-    public byte[] getResource(String name) throws IOException {
+    public byte[] getResource(String name) {
         ImageLocation location = findLocation(name);
 
         return location != null ? getResource(location) : null;
     }
 
-    public List<String> getNames(String name) throws IOException {
-        return getNames(getResource(name));
+    public ByteBuffer getResourceBuffer(ImageLocation loc) {
+        long offset = loc.getContentOffset();
+        long compressedSize = loc.getCompressedSize();
+        long uncompressedSize = loc.getUncompressedSize();
+        assert compressedSize < Integer.MAX_VALUE;
+        assert uncompressedSize < Integer.MAX_VALUE;
+
+        if (substrate.supportsDataBuffer() && compressedSize == 0) {
+            return substrate.getDataBuffer(offset, uncompressedSize);
+        }
+
+        ByteBuffer uncompressedBuffer = ImageBufferCache.getBuffer(uncompressedSize);
+        boolean isRead;
+
+        if (compressedSize != 0) {
+            ByteBuffer compressedBuffer = ImageBufferCache.getBuffer(compressedSize);
+            isRead = substrate.read(offset, compressedBuffer, compressedSize,
+                                          uncompressedBuffer, uncompressedSize);
+            ImageBufferCache.releaseBuffer(compressedBuffer);
+        } else {
+            isRead = substrate.read(offset, uncompressedBuffer, uncompressedSize);
+        }
+
+        if (isRead) {
+            return uncompressedBuffer;
+        } else {
+            ImageBufferCache.releaseBuffer(uncompressedBuffer);
+
+            return null;
+        }
     }
 
-    public List<String> getNames(byte[] bytes) {
-        IntBuffer buffer = ByteBuffer.wrap(bytes).asIntBuffer();
-        List<String> names = new ArrayList<>();
+    public ByteBuffer getResourceBuffer(String name) {
+        ImageLocation location = findLocation(name);
+
+        return location != null ? getResourceBuffer(location) : null;
+    }
 
-        while (buffer.hasRemaining()) {
-            int offset = buffer.get();
-            names.add(getString(offset));
-        }
+    public InputStream getResourceStream(ImageLocation loc) {
+        byte[] bytes = getResource(loc);
 
-        return names;
+        return new ByteArrayInputStream(bytes);
+    }
+
+    public InputStream getResourceStream(String name) {
+        ImageLocation location = findLocation(name);
+
+        return location != null ? getResourceStream(location) : null;
     }
 }
--- a/jdk/src/java.base/share/classes/jdk/internal/jimage/BasicImageWriter.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/BasicImageWriter.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,67 +25,30 @@
 
 package jdk.internal.jimage;
 
-import java.io.PrintStream;
 import java.nio.ByteOrder;
 import java.util.ArrayList;
-import java.util.Arrays;
 import java.util.List;
 
 public final class BasicImageWriter {
+
+    public static final String IMAGE_EXT = ".jimage";
+    public static final String BOOT_NAME = "bootmodules";
+    public static final String BOOT_IMAGE_NAME = BOOT_NAME + IMAGE_EXT;
+
     private final static int RETRY_LIMIT = 1000;
 
     private ByteOrder byteOrder;
-    private ImageStrings strings;
-    private int count;
+    private ImageStringsWriter strings;
+    private int length;
     private int[] redirect;
-    private ImageLocation[] locations;
-    private List<ImageLocation> input;
+    private ImageLocationWriter[] locations;
+    private List<ImageLocationWriter> input;
     private ImageStream headerStream;
     private ImageStream redirectStream;
     private ImageStream locationOffsetStream;
     private ImageStream locationStream;
     private ImageStream allIndexStream;
 
-    static class ImageBucket implements Comparable<ImageBucket> {
-        final List<ImageLocation> list;
-
-        ImageBucket() {
-            this.list = new ArrayList<>();
-        }
-
-        void add(ImageLocation location) {
-            list.add(location);
-        }
-
-        int getSize() {
-            return list.size();
-        }
-
-        List<ImageLocation> getList() {
-            return list;
-        }
-
-        ImageLocation getFirst() {
-            assert !list.isEmpty() : "bucket should never be empty";
-            return list.get(0);
-        }
-
-        @Override
-        public int hashCode() {
-            return getFirst().hashCode();
-        }
-
-        @Override
-        public boolean equals(Object obj) {
-            return this == obj;
-        }
-
-        @Override
-        public int compareTo(ImageBucket o) {
-            return o.getSize() - getSize();
-        }
-    }
-
     public BasicImageWriter() {
         this(ByteOrder.nativeOrder());
     }
@@ -93,7 +56,7 @@
     public BasicImageWriter(ByteOrder byteOrder) {
         this.byteOrder = byteOrder;
         this.input = new ArrayList<>();
-        this.strings = new ImageStrings();
+        this.strings = new ImageStringsWriter();
         this.headerStream = new ImageStream(byteOrder);
         this.redirectStream = new ImageStream(byteOrder);
         this.locationOffsetStream = new ImageStream(byteOrder);
@@ -101,6 +64,10 @@
         this.allIndexStream = new ImageStream(byteOrder);
     }
 
+    public ByteOrder getByteOrder() {
+        return byteOrder;
+    }
+
     public int addString(String string) {
         return addString(new UTF8String(string));
     }
@@ -109,104 +76,48 @@
         return strings.add(string);
     }
 
-    public void addLocation(String fullname, long contentOffset, long compressedSize, long uncompressedSize) {
-        ImageLocation location = ImageLocation.newLocation(new UTF8String(fullname), strings, contentOffset, compressedSize, uncompressedSize);
+    public String getString(int offset) {
+        UTF8String utf8 = strings.get(offset);
+        return utf8 != null? utf8.toString() : null;
+    }
+
+    public void addLocation(String fullname, long contentOffset,
+            long compressedSize, long uncompressedSize) {
+        ImageLocationWriter location =
+                ImageLocationWriter.newLocation(new UTF8String(fullname), strings,
+                        contentOffset, compressedSize, uncompressedSize);
         input.add(location);
-        count++;
+        length++;
+    }
+
+    ImageLocationWriter[] getLocations() {
+        return locations;
+    }
+
+    int getLocationsCount() {
+        return input.size();
     }
 
     private void generatePerfectHash() {
-        redo:
-        while(true) {
-            redirect = new int[count];
-            locations = new ImageLocation[count];
-
-            ImageBucket[] sorted = createBuckets();
-
-            int free = 0;
-
-            for (ImageBucket bucket : sorted) {
-                if (bucket.getSize() != 1) {
-                    if (!packCollidedEntries(bucket, count)) {
-                        count = (count + 1) | 1;
+        PerfectHashBuilder<ImageLocationWriter> builder =
+            new PerfectHashBuilder<>(
+                new PerfectHashBuilder.Entry<ImageLocationWriter>().getClass(),
+                new PerfectHashBuilder.Bucket<ImageLocationWriter>().getClass());
 
-                        continue redo;
-                    }
-                } else {
-                    for ( ; free < count && locations[free] != null; free++) {}
-                    assert free < count : "no free slots";
-                    locations[free] = bucket.getFirst();
-                    redirect[bucket.hashCode() % count] = -1 - free;
-                    free++;
-                }
-            }
-
-            break;
-        }
-    }
-
-    private ImageBucket[] createBuckets() {
-        ImageBucket[] buckets = new ImageBucket[count];
-
-        input.stream().forEach((location) -> {
-            int index = location.hashCode() % count;
-            ImageBucket bucket = buckets[index];
-
-            if (bucket == null) {
-                buckets[index] = bucket = new ImageBucket();
-            }
-
-            bucket.add(location);
+        input.forEach((location) -> {
+            builder.put(location.getFullName(), location);
         });
 
-        ImageBucket[] sorted = Arrays.asList(buckets).stream()
-                .filter((bucket) -> (bucket != null))
-                .sorted()
-                .toArray(ImageBucket[]::new);
-
-        return sorted;
-    }
-
-    private boolean packCollidedEntries(ImageBucket bucket, int count) {
-        List<Integer> undo = new ArrayList<>();
-        int base = UTF8String.HASH_MULTIPLIER + 1;
-
-        int retry = 0;
-
-        redo:
-        while (true) {
-            for (ImageLocation location : bucket.getList()) {
-                int index = location.hashCode(base) % count;
-
-                if (locations[index] != null) {
-                    undo.stream().forEach((i) -> {
-                        locations[i] = null;
-                    });
+        builder.generate();
 
-                    undo.clear();
-                    base++;
-
-                    if (base == 0) {
-                        base = 1;
-                    }
-
-                    if (++retry > RETRY_LIMIT) {
-                        return false;
-                    }
+        length = builder.getCount();
+        redirect = builder.getRedirect();
+        PerfectHashBuilder.Entry<ImageLocationWriter>[] order = builder.getOrder();
+        locations = new ImageLocationWriter[length];
 
-                    continue redo;
-                }
-
-                locations[index] = location;
-                undo.add(index);
-            }
-
-            redirect[bucket.hashCode() % count] = base;
-
-            break;
+        for (int i = 0; i < length; i++) {
+            locations[i] = order[i].getValue();
         }
-
-        return true;
     }
 
     private void prepareStringBytes() {
@@ -214,17 +125,17 @@
     }
 
     private void prepareRedirectBytes() {
-        for (int i = 0; i < count; i++) {
+        for (int i = 0; i < length; i++) {
             redirectStream.putInt(redirect[i]);
         }
     }
 
     private void prepareLocationBytes() {
         // Reserve location offset zero for empty locations
-        locationStream.put(ImageLocation.ATTRIBUTE_END << 3);
+        locationStream.put(ImageLocationWriter.ATTRIBUTE_END << 3);
 
-        for (int i = 0; i < count; i++) {
-            ImageLocation location = locations[i];
+        for (int i = 0; i < length; i++) {
+            ImageLocationWriter location = locations[i];
 
             if (location != null) {
                 location.writeTo(locationStream);
@@ -235,14 +146,16 @@
     }
 
     private void prepareOffsetBytes() {
-        for (int i = 0; i < count; i++) {
-            ImageLocation location = locations[i];
-            locationOffsetStream.putInt(location != null ? location.getLocationOffset() : 0);
+        for (int i = 0; i < length; i++) {
+            ImageLocationWriter location = locations[i];
+            int offset = location != null ? location.getLocationOffset() : 0;
+            locationOffsetStream.putInt(offset);
         }
     }
 
     private void prepareHeaderBytes() {
-        ImageHeader header = new ImageHeader(count, locationStream.getSize(), strings.getSize());
+        ImageHeader header = new ImageHeader(input.size(), length,
+                locationStream.getSize(), strings.getSize());
         header.writeTo(headerStream);
     }
 
@@ -268,33 +181,15 @@
         return allIndexStream.toArray();
     }
 
-    ImageLocation find(UTF8String key) {
-        int index = key.hashCode() % count;
-        index = redirect[index];
+    ImageLocationWriter find(UTF8String key) {
+        int index = redirect[key.hashCode() % length];
 
         if (index < 0) {
             index = -index - 1;
-            ImageLocation location = locations[index];
-
-            return location;
         } else {
-            index = key.hashCode(index) % count;
-            ImageLocation location = locations[index];
-
-            return location;
+            index = key.hashCode(index) % length;
         }
-    }
 
-    public void statistics() {
-        getBytes();
-        PrintStream out = System.out;
-        out.println("Count: " + count);
-        out.println("Header bytes size: " + headerStream.getSize());
-        out.println("Redirect bytes size: " + redirectStream.getSize());
-        out.println("Offset bytes size: " + locationOffsetStream.getSize());
-        out.println("Location bytes size: " + locationStream.getSize());
-        out.println("String count: " + strings.getCount());
-        out.println("String bytes size: " + strings.getSize());
-        out.println("Total bytes size: " + allIndexStream.getSize());
+        return locations[index];
     }
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ExternalFilesWriter.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,105 @@
+/*
+ * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.internal.jimage;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.UncheckedIOException;
+import java.nio.file.FileAlreadyExistsException;
+import java.nio.file.Files;
+import java.nio.file.Path;
+import java.util.function.Consumer;
+import jdk.internal.jimage.Archive.Entry;
+
+/**
+ * A Consumer suitable for processing non resources Archive Entry and writing it to the
+ * appropriate location.
+ */
+class ExternalFilesWriter implements Consumer<Entry> {
+    private final Path root;
+
+    ExternalFilesWriter(Path root) {
+        this.root = root;
+    }
+
+    @Override
+    public void accept(Entry entry) {
+        String name = entry.path();
+        try {
+            String filename = entry.path();
+            try (InputStream in = entry.stream()) {
+                switch (entry.type()) {
+                    case NATIVE_LIB:
+                        writeEntry(in, destFile(nativeDir(filename), filename));
+                        break;
+                    case NATIVE_CMD:
+                        Path path = destFile("bin", filename);
+                        writeEntry(in, path);
+                        path.toFile().setExecutable(true);
+                        break;
+                    case CONFIG:
+                        writeEntry(in, destFile("conf", filename));
+                        break;
+                    case MODULE_NAME:
+                        // skip
+                        break;
+                    case SERVICE:
+                        //throw new UnsupportedOperationException(name + " in " + zipfile.toString()); //TODO
+                        throw new UnsupportedOperationException(name + " in " + name);
+                    default:
+                        //throw new InternalError("unexpected entry: " + name + " " + zipfile.toString()); //TODO
+                        throw new InternalError("unexpected entry: " + name + " " + name);
+                }
+            }
+        } catch (FileAlreadyExistsException x) {
+            System.err.println("File already exists (skipped) " + name);
+        } catch (IOException x) {
+            throw new UncheckedIOException(x);
+        }
+    }
+
+    private Path destFile(String dir, String filename) {
+        return root.resolve(dir).resolve(filename);
+    }
+
+    private void writeEntry(InputStream in, Path dstFile) throws IOException {
+        Files.createDirectories(dstFile.getParent());
+        Files.copy(in, dstFile);
+    }
+
+    private static String nativeDir(String filename) {
+        if (System.getProperty("os.name").startsWith("Windows")) {
+            if (filename.endsWith(".dll") || filename.endsWith(".diz")
+                || filename.endsWith(".pdb") || filename.endsWith(".map")) {
+                return "bin";
+            } else {
+                return "lib";
+            }
+        } else {
+            return "lib";
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageBufferCache.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,123 @@
+/*
+ * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.internal.jimage;
+
+import java.nio.ByteBuffer;
+import java.util.ArrayList;
+
+class ImageBufferCache {
+    private static final int MAX_FREE_BUFFERS = 3;
+    private static final int LARGE_BUFFER = 0x10000;
+    private static final ThreadLocal<ArrayList<ImageBufferCache>>
+            threadLocal = new ThreadLocal<>();
+
+    private final ByteBuffer buffer;
+    private boolean isUsed;
+
+    static ByteBuffer getBuffer(long size) {
+        assert size < Integer.MAX_VALUE;
+        ByteBuffer buffer = null;
+
+        if (size > LARGE_BUFFER) {
+            buffer = ByteBuffer.allocateDirect((int)((size + 0xFFF) & ~0xFFF));
+        } else {
+            ArrayList<ImageBufferCache> buffers = threadLocal.get();
+
+            if (buffers == null) {
+                buffers = new ArrayList<>(MAX_FREE_BUFFERS);
+                threadLocal.set(buffers);
+            }
+
+            int i = 0, j = buffers.size();
+            for (ImageBufferCache imageBuffer : buffers) {
+                if (size <= imageBuffer.capacity()) {
+                    j = i;
+
+                    if (!imageBuffer.isUsed) {
+                        imageBuffer.isUsed = true;
+                        buffer = imageBuffer.buffer;
+
+                        break;
+                    }
+                } else {
+                    break;
+                }
+
+                i++;
+            }
+
+            if (buffer == null) {
+                ImageBufferCache imageBuffer = new ImageBufferCache((int)size);
+                buffers.add(j, imageBuffer);
+                buffer = imageBuffer.buffer;
+            }
+        }
+
+        buffer.rewind();
+        buffer.limit((int)size);
+
+        return buffer;
+    }
+
+    static void releaseBuffer(ByteBuffer buffer) {
+        ArrayList<ImageBufferCache> buffers = threadLocal.get();
+
+        if (buffers == null ) {
+            return;
+        }
+
+        if (buffer.capacity() > LARGE_BUFFER) {
+            return;
+        }
+
+        int i = 0, j = buffers.size();
+        for (ImageBufferCache imageBuffer : buffers) {
+            if (!imageBuffer.isUsed) {
+                j = Math.min(j, i);
+            }
+
+            if (imageBuffer.buffer == buffer) {
+                imageBuffer.isUsed = false;
+                j = Math.min(j, i);
+
+                break;
+            }
+        }
+
+        if (buffers.size() > MAX_FREE_BUFFERS && j != buffers.size()) {
+            buffers.remove(j);
+        }
+    }
+
+    private ImageBufferCache(int needed) {
+        this.buffer = ByteBuffer.allocateDirect((needed + 0xFFF) & ~0xFFF);
+        this.isUsed = true;
+        this.buffer.limit(needed);
+    }
+
+    private long capacity() {
+        return buffer.capacity();
+    }
+}
--- a/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageFile.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,288 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.  Oracle designates this
- * particular file as subject to the "Classpath" exception as provided
- * by Oracle in the LICENSE file that accompanied this code.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-package jdk.internal.jimage;
-
-import java.io.BufferedOutputStream;
-import java.io.ByteArrayOutputStream;
-import java.io.DataOutputStream;
-import java.io.IOException;
-import java.io.OutputStream;
-import java.nio.ByteOrder;
-import java.nio.file.Files;
-import java.nio.file.Path;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-import java.util.function.Consumer;
-import java.util.function.Function;
-import java.util.stream.Collectors;
-import java.util.zip.DataFormatException;
-import java.util.zip.Deflater;
-import java.util.zip.Inflater;
-import jdk.internal.jimage.ImageModules.Loader;
-import jdk.internal.jimage.ImageModules.ModuleIndex;
-
-/**
- * An image (native endian.)
- * <pre>{@code
- * {
- *   u4 magic;
- *   u2 major_version;
- *   u2 minor_version;
- *   u4 location_count;
- *   u4 location_attributes_size;
- *   u4 strings_size;
- *   u4 redirect[location_count];
- *   u4 offsets[location_count];
- *   u1 location_attributes[location_attributes_size];
- *   u1 strings[strings_size];
- *   u1 content[if !EOF];
- * }
- * }</pre>
- */
-public final class ImageFile {
-    private static final String JAVA_BASE = "java.base";
-    private static final String IMAGE_EXT = ".jimage";
-    private static final String JAR_EXT = ".jar";
-    private final Path root;
-    private final Path mdir;
-    private final Map<String, List<Resource>> resourcesForModule = new HashMap<>();
-
-    private ImageFile(Path path) {
-        this.root = path;
-        this.mdir = root.resolve(path.getFileSystem().getPath("lib", "modules"));
-    }
-
-    public static ImageFile open(Path path) throws IOException {
-        ImageFile lib = new ImageFile(path);
-        return lib.open();
-    }
-
-    private ImageFile open() throws IOException {
-        Path path = mdir.resolve("bootmodules" + IMAGE_EXT);
-
-        ImageReader reader = new ImageReader(path.toString());
-        ImageHeader header = reader.getHeader();
-
-        if (header.getMagic() != ImageHeader.MAGIC) {
-            if (header.getMagic() == ImageHeader.BADMAGIC) {
-                throw new IOException(path + ": Image may be not be native endian");
-            } else {
-                throw new IOException(path + ": Invalid magic number");
-            }
-        }
-
-        if (header.getMajorVersion() > ImageHeader.MAJOR_VERSION ||
-            (header.getMajorVersion() == ImageHeader.MAJOR_VERSION &&
-             header.getMinorVersion() > ImageHeader.MINOR_VERSION)) {
-            throw new IOException("invalid version number");
-        }
-
-        return this;
-    }
-
-    public static ImageFile create(Path output,
-                                   Set<Archive> archives,
-                                   ImageModules modules)
-        throws IOException
-    {
-        return ImageFile.create(output, archives, modules, ByteOrder.nativeOrder());
-    }
-
-    public static ImageFile create(Path output,
-                                   Set<Archive> archives,
-                                   ImageModules modules,
-                                   ByteOrder byteOrder)
-        throws IOException
-    {
-        ImageFile lib = new ImageFile(output);
-        // get all resources
-        lib.readModuleEntries(modules, archives);
-        // write to modular image
-        lib.writeImage(modules, archives, byteOrder);
-        return lib;
-    }
-
-    private void writeImage(ImageModules modules,
-                            Set<Archive> archives,
-                            ByteOrder byteOrder)
-        throws IOException
-    {
-        // name to Archive file
-        Map<String, Archive> nameToArchive =
-            archives.stream()
-                  .collect(Collectors.toMap(Archive::moduleName, Function.identity()));
-
-        Files.createDirectories(mdir);
-        for (Loader l : Loader.values()) {
-            Set<String> mods = modules.getModules(l);
-
-            try (OutputStream fos = Files.newOutputStream(mdir.resolve(l.getName() + IMAGE_EXT));
-                    BufferedOutputStream bos = new BufferedOutputStream(fos);
-                    DataOutputStream out = new DataOutputStream(bos)) {
-                // store index in addition of the class loader map for boot loader
-                BasicImageWriter writer = new BasicImageWriter(byteOrder);
-                Set<String> duplicates = new HashSet<>();
-
-                // build package map for modules and add as resources
-                ModuleIndex mindex = modules.buildModuleIndex(l, writer);
-                long offset = mindex.size();
-
-                // the order of traversing the resources and the order of
-                // the module content being written must be the same
-                for (String mn : mods) {
-                    for (Resource res : resourcesForModule.get(mn)) {
-                        String path = res.name();
-                        long uncompressedSize = res.size();
-                        long compressedSize = res.csize();
-                        long onFileSize = compressedSize != 0 ? compressedSize : uncompressedSize;
-
-                        if (duplicates.contains(path)) {
-                            System.err.format("duplicate resource \"%s\", skipping%n", path);
-                            // TODO Need to hang bytes on resource and write from resource not zip.
-                            // Skipping resource throws off writing from zip.
-                            offset += onFileSize;
-                            continue;
-                        }
-                        duplicates.add(path);
-                        writer.addLocation(path, offset, compressedSize, uncompressedSize);
-                        offset += onFileSize;
-                    }
-                }
-
-                // write header and indices
-                byte[] bytes = writer.getBytes();
-                out.write(bytes, 0, bytes.length);
-
-                // write module table and packages
-                mindex.writeTo(out);
-
-                // write module content
-                for (String mn : mods) {
-                    writeModule(nameToArchive.get(mn), out);
-                }
-            }
-        }
-    }
-
-    private void readModuleEntries(ImageModules modules,
-                                   Set<Archive> archives)
-        throws IOException
-    {
-        for (Archive archive : archives) {
-            List<Resource> res = new ArrayList<>();
-            archive.visitResources(x-> res.add(x));
-
-            String mn = archive.moduleName();
-            resourcesForModule.put(mn, res);
-
-            Set<String> pkgs = res.stream().map(Resource::name)
-                    .filter(n -> n.endsWith(".class"))
-                    .map(this::toPackage)
-                    .distinct()
-                    .collect(Collectors.toSet());
-            modules.setPackages(mn, pkgs);
-        }
-    }
-
-    private String toPackage(String name) {
-        int index = name.lastIndexOf('/');
-        if (index > 0) {
-            return name.substring(0, index).replace('/', '.');
-        } else {
-            // ## unnamed package
-            System.err.format("Warning: %s in unnamed package%n", name);
-            return "";
-        }
-    }
-
-    private void writeModule(Archive archive,
-                             OutputStream out)
-        throws IOException
-    {
-          Consumer<Archive.Entry> consumer = archive.defaultImageWriter(root, out);
-          archive.visitEntries(consumer);
-    }
-
-
-    static class Compressor {
-        public static byte[] compress(byte[] bytesIn) {
-            Deflater deflater = new Deflater();
-            deflater.setInput(bytesIn);
-            ByteArrayOutputStream stream = new ByteArrayOutputStream(bytesIn.length);
-            byte[] buffer = new byte[1024];
-
-            deflater.finish();
-            while (!deflater.finished()) {
-                int count = deflater.deflate(buffer);
-                stream.write(buffer, 0, count);
-            }
-
-            try {
-                stream.close();
-            } catch (IOException ex) {
-                return bytesIn;
-            }
-
-            byte[] bytesOut = stream.toByteArray();
-            deflater.end();
-
-            return bytesOut;
-        }
-
-        public static byte[] decompress(byte[] bytesIn) {
-            Inflater inflater = new Inflater();
-            inflater.setInput(bytesIn);
-            ByteArrayOutputStream stream = new ByteArrayOutputStream(bytesIn.length);
-            byte[] buffer = new byte[1024];
-
-            while (!inflater.finished()) {
-                int count;
-
-                try {
-                    count = inflater.inflate(buffer);
-                } catch (DataFormatException ex) {
-                    return null;
-                }
-
-                stream.write(buffer, 0, count);
-            }
-
-            try {
-                stream.close();
-            } catch (IOException ex) {
-                return null;
-            }
-
-            byte[] bytesOut = stream.toByteArray();
-            inflater.end();
-
-            return bytesOut;
-        }
-    }
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageFileCreator.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,355 @@
+/*
+ * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.internal.jimage;
+
+import java.io.BufferedOutputStream;
+import java.io.ByteArrayOutputStream;
+import java.io.DataOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.nio.ByteBuffer;
+import java.nio.ByteOrder;
+import java.nio.file.Files;
+import java.nio.file.Path;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Objects;
+import java.util.Set;
+import java.util.function.Consumer;
+import java.util.function.Function;
+import java.util.stream.Collectors;
+import java.util.stream.Stream;
+import jdk.internal.jimage.Archive.Entry;
+import jdk.internal.jimage.Archive.Entry.EntryType;
+import static jdk.internal.jimage.BasicImageWriter.BOOT_NAME;
+import static jdk.internal.jimage.BasicImageWriter.IMAGE_EXT;
+
+/**
+ * An image (native endian.)
+ * <pre>{@code
+ * {
+ *   u4 magic;
+ *   u2 major_version;
+ *   u2 minor_version;
+ *   u4 resource_count;
+ *   u4 table_length;
+ *   u4 location_attributes_size;
+ *   u4 strings_size;
+ *   u4 redirect[table_length];
+ *   u4 offsets[table_length];
+ *   u1 location_attributes[location_attributes_size];
+ *   u1 strings[strings_size];
+ *   u1 content[if !EOF];
+ * }
+ * }</pre>
+ */
+public final class ImageFileCreator {
+    private final Path root;
+    private final Path mdir;
+    private final Map<String, List<Entry>> entriesForModule = new HashMap<>();
+    private ImageFileCreator(Path path) {
+        this.root = path;
+        this.mdir = root.resolve(path.getFileSystem().getPath("lib", "modules"));
+    }
+
+    public static ImageFileCreator create(Path output,
+            Set<Archive> archives)
+            throws IOException {
+        return create(output, BOOT_NAME, archives, ByteOrder.nativeOrder());
+    }
+
+    public static ImageFileCreator create(Path output,
+            Set<Archive> archives,
+            ByteOrder byteOrder)
+            throws IOException {
+        return create(output, BOOT_NAME, archives, byteOrder);
+    }
+
+    public static ImageFileCreator create(Path output,
+                                   String fileName,
+                                   Set<Archive> archives,
+                                   ByteOrder byteOrder)
+        throws IOException
+    {
+        ImageFileCreator image = new ImageFileCreator(output);
+        // get all entries
+        Map<String, Set<String>> modulePackagesMap = new HashMap<>();
+        image.readAllEntries(modulePackagesMap, archives);
+        // write to modular image
+        image.writeImage(fileName, modulePackagesMap, archives, byteOrder);
+        return image;
+    }
+
+    private void readAllEntries(Map<String, Set<String>> modulePackagesMap,
+                                  Set<Archive> archives) {
+        archives.stream().forEach((archive) -> {
+            Map<Boolean, List<Entry>> es;
+            try(Stream<Entry> entries = archive.entries()) {
+                es = entries.collect(Collectors.partitioningBy(n -> n.type()
+                        == EntryType.CLASS_OR_RESOURCE));
+            }
+            String mn = archive.moduleName();
+            List<Entry> all = new ArrayList<>();
+            all.addAll(es.get(false));
+            all.addAll(es.get(true));
+            entriesForModule.put(mn, all);
+            // Extract package names
+            Set<String> pkgs = es.get(true).stream().map(Entry::name)
+                    .filter(n -> isClassPackage(n))
+                    .map(ImageFileCreator::toPackage)
+                    .collect(Collectors.toSet());
+            modulePackagesMap.put(mn, pkgs);
+        });
+    }
+
+    public static boolean isClassPackage(String path) {
+        return path.endsWith(".class");
+    }
+
+    public static boolean isResourcePackage(String path) {
+        path = path.substring(1);
+        path = path.substring(path.indexOf("/")+1);
+        return !path.startsWith("META-INF/");
+    }
+
+    public static void recreateJimage(Path jimageFile,
+            Set<Archive> archives,
+            Map<String, Set<String>> modulePackages)
+            throws IOException {
+        Map<String, List<Entry>> entriesForModule
+                = archives.stream().collect(Collectors.toMap(
+                                Archive::moduleName,
+                                a -> {
+                                    try(Stream<Entry> entries = a.entries()) {
+                                        return entries.collect(Collectors.toList());
+                                    }
+                                }));
+        Map<String, Archive> nameToArchive
+                = archives.stream()
+                .collect(Collectors.toMap(Archive::moduleName, Function.identity()));
+        ByteOrder order = ByteOrder.nativeOrder();
+        ResourcePoolImpl resources = createResources(modulePackages, nameToArchive,
+                (Entry t) -> {
+            throw new UnsupportedOperationException("Not supported, no external file "
+                    + "in a jimage file");
+        }, entriesForModule, order);
+        String fileName = jimageFile.getRoot().toString();
+        generateJImage(jimageFile, fileName, resources, order);
+    }
+
+    private void writeImage(String fileName,
+            Map<String, Set<String>> modulePackagesMap,
+            Set<Archive> archives,
+            ByteOrder byteOrder)
+            throws IOException {
+        Files.createDirectories(mdir);
+        ExternalFilesWriter filesWriter = new ExternalFilesWriter(root);
+        // name to Archive file
+        Map<String, Archive> nameToArchive
+                = archives.stream()
+                .collect(Collectors.toMap(Archive::moduleName, Function.identity()));
+        ResourcePoolImpl resources = createResources(modulePackagesMap,
+                nameToArchive, filesWriter,
+                entriesForModule, byteOrder);
+        generateJImage(mdir.resolve(fileName + IMAGE_EXT), fileName, resources,
+                byteOrder);
+    }
+
+    private static void generateJImage(Path img,
+            String fileName,
+            ResourcePoolImpl resources,
+            ByteOrder byteOrder
+    ) throws IOException {
+        BasicImageWriter writer = new BasicImageWriter(byteOrder);
+
+        Map<String, Set<String>> modulePackagesMap = resources.getModulePackages();
+
+        try (OutputStream fos = Files.newOutputStream(img);
+                BufferedOutputStream bos = new BufferedOutputStream(fos);
+                DataOutputStream out = new DataOutputStream(bos)) {
+            Set<String> duplicates = new HashSet<>();
+            ImageModuleDataWriter moduleData =
+            ImageModuleDataWriter.buildModuleData(writer, modulePackagesMap);
+            moduleData.addLocation(fileName, writer);
+            long offset = moduleData.size();
+
+            List<ResourcePool.Resource> content = new ArrayList<>();
+            List<String> paths = new ArrayList<>();
+                 // the order of traversing the resources and the order of
+            // the module content being written must be the same
+            for (ResourcePool.Resource res : resources.getResources()) {
+                String path = res.getPath();
+                int index = path.indexOf("/META-INF/");
+                if (index != -1) {
+                    path = path.substring(index + 1);
+                }
+
+                content.add(res);
+                long uncompressedSize = res.getLength();
+                long compressedSize = 0;
+                if (res instanceof ResourcePool.CompressedResource) {
+                    ResourcePool.CompressedResource comp =
+                            (ResourcePool.CompressedResource) res;
+                    compressedSize = res.getLength();
+                    uncompressedSize = comp.getUncompressedSize();
+                }
+                long onFileSize = res.getLength();
+
+                if (duplicates.contains(path)) {
+                    System.err.format("duplicate resource \"%s\", skipping%n",
+                            path);
+                     // TODO Need to hang bytes on resource and write
+                    // from resource not zip.
+                    // Skipping resource throws off writing from zip.
+                    offset += onFileSize;
+                    continue;
+                }
+                duplicates.add(path);
+                writer.addLocation(path, offset, compressedSize, uncompressedSize);
+                paths.add(path);
+                offset += onFileSize;
+            }
+
+            ImageResourcesTree tree = new ImageResourcesTree(offset, writer, paths);
+
+            // write header and indices
+            byte[] bytes = writer.getBytes();
+            out.write(bytes, 0, bytes.length);
+
+            // write module meta data
+            moduleData.writeTo(out);
+
+            // write module content
+            for(ResourcePool.Resource res : content) {
+                byte[] buf = res.getByteArray();
+                out.write(buf, 0, buf.length);
+            }
+
+            tree.addContent(out);
+        }
+    }
+
+    private static ResourcePoolImpl createResources(Map<String, Set<String>> modulePackagesMap,
+            Map<String, Archive> nameToArchive,
+            Consumer<Entry> externalFileHandler,
+            Map<String, List<Entry>> entriesForModule,
+            ByteOrder byteOrder) throws IOException {
+        ResourcePoolImpl resources = new ResourcePoolImpl(byteOrder);
+        Set<String> mods = modulePackagesMap.keySet();
+        for (String mn : mods) {
+            for (Entry entry : entriesForModule.get(mn)) {
+                String path = entry.name();
+                if (entry.type() == EntryType.CLASS_OR_RESOURCE) {
+                    if (!entry.path().endsWith(BOOT_NAME)) {
+                        try (InputStream stream = entry.stream()) {
+                            byte[] bytes = readAllBytes(stream);
+                            path = "/" + mn + "/" + path;
+                            try {
+                                resources.addResource(new ResourcePool.Resource(path,
+                                        ByteBuffer.wrap(bytes)));
+                            } catch (Exception ex) {
+                                throw new IOException(ex);
+                            }
+                        }
+                    }
+                } else {
+                    externalFileHandler.accept(entry);
+                }
+            }
+            // Done with this archive, close it.
+            Archive archive = nameToArchive.get(mn);
+            archive.close();
+        }
+        return resources;
+    }
+
+    private static final int BUF_SIZE = 8192;
+
+    private static byte[] readAllBytes(InputStream is) throws IOException {
+        ByteArrayOutputStream baos = new ByteArrayOutputStream();
+        byte[] buf = new byte[BUF_SIZE];
+        while (true) {
+            int n = is.read(buf);
+            if (n < 0) {
+                break;
+            }
+            baos.write(buf, 0, n);
+        }
+        return baos.toByteArray();
+    }
+
+    /**
+     * Helper method that splits a Resource path onto 3 items: module, parent
+     * and resource name.
+     *
+     * @param path
+     * @return An array containing module, parent and name.
+     */
+    public static String[] splitPath(String path) {
+        Objects.requireNonNull(path);
+        String noRoot = path.substring(1);
+        int pkgStart = noRoot.indexOf("/");
+        String module = noRoot.substring(0, pkgStart);
+        List<String> result = new ArrayList<>();
+        result.add(module);
+        String pkg = noRoot.substring(pkgStart + 1);
+        String resName;
+        int pkgEnd = pkg.lastIndexOf("/");
+        if (pkgEnd == -1) { // No package.
+            resName = pkg;
+        } else {
+            resName = pkg.substring(pkgEnd + 1);
+        }
+
+        pkg = toPackage(pkg, false);
+        result.add(pkg);
+        result.add(resName);
+
+        String[] array = new String[result.size()];
+        return result.toArray(array);
+    }
+
+    private static String toPackage(String name) {
+        String pkg = toPackage(name, true);
+        return pkg;
+    }
+
+    private static String toPackage(String name, boolean log) {
+        int index = name.lastIndexOf('/');
+        if (index > 0) {
+            return name.substring(0, index).replace('/', '.');
+        } else {
+            // ## unnamed package
+            if (log) {
+                System.err.format("Warning: %s in unnamed package%n", name);
+            }
+            return "";
+        }
+    }
+}
--- a/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageHeader.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageHeader.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,67 +25,76 @@
 
 package jdk.internal.jimage;
 
-import java.nio.ByteOrder;
+import java.nio.ByteBuffer;
 import java.nio.IntBuffer;
 
 public final class ImageHeader {
     public static final int MAGIC = 0xCAFEDADA;
     public static final int BADMAGIC = 0xDADAFECA;
-    public static final short MAJOR_VERSION = 0;
-    public static final short MINOR_VERSION = 1;
+    public static final int MAJOR_VERSION = 1;
+    public static final int MINOR_VERSION = 0;
 
     private final int magic;
-    private final short majorVersion;
-    private final short minorVersion;
-    private final int locationCount;
+    private final int majorVersion;
+    private final int minorVersion;
+    private final int flags;
+    private final int resourceCount;
+    private final int tableLength;
     private final int locationsSize;
     private final int stringsSize;
 
-    ImageHeader(int locationCount, int locationsSize, int stringsSize) {
-        this(MAGIC, MAJOR_VERSION, MINOR_VERSION, locationCount, locationsSize, stringsSize);
+    public ImageHeader(int resourceCount, int tableCount,
+            int locationsSize, int stringsSize) {
+        this(MAGIC, MAJOR_VERSION, MINOR_VERSION, 0, resourceCount,
+                tableCount, locationsSize, stringsSize);
     }
 
-    ImageHeader(int magic, short majorVersion, short minorVersion, int locationCount,
-                int locationsSize, int stringsSize)
+    public ImageHeader(int magic, int majorVersion, int minorVersion,
+                int flags, int resourceCount,
+                int tableLength, int locationsSize, int stringsSize)
     {
         this.magic = magic;
         this.majorVersion = majorVersion;
         this.minorVersion = minorVersion;
-        this.locationCount = locationCount;
+        this.flags = flags;
+        this.resourceCount = resourceCount;
+        this.tableLength = tableLength;
         this.locationsSize = locationsSize;
         this.stringsSize = stringsSize;
     }
 
-    static int getHeaderSize() {
-       return 4 +
-              2 + 2 +
-              4 +
-              4 +
-              4;
+    public static int getHeaderSize() {
+       return 7 * 4;
     }
 
-    static ImageHeader readFrom(ByteOrder byteOrder, IntBuffer buffer) {
+    static ImageHeader readFrom(IntBuffer buffer) {
         int magic = buffer.get(0);
         int version = buffer.get(1);
-        short majorVersion = (short)(byteOrder == ByteOrder.BIG_ENDIAN ?
-            version >>> 16 : (version & 0xFFFF));
-        short minorVersion = (short)(byteOrder == ByteOrder.BIG_ENDIAN ?
-            (version & 0xFFFF) : version >>> 16);
-        int locationCount = buffer.get(2);
-        int locationsSize = buffer.get(3);
-        int stringsSize = buffer.get(4);
+        int majorVersion = version >>> 16;
+        int minorVersion = version & 0xFFFF;
+        int flags = buffer.get(2);
+        int resourceCount = buffer.get(3);
+        int tableLength = buffer.get(4);
+        int locationsSize = buffer.get(5);
+        int stringsSize = buffer.get(6);
 
-        return new ImageHeader(magic, majorVersion, minorVersion, locationCount,
-                               locationsSize, stringsSize);
+        return new ImageHeader(magic, majorVersion, minorVersion, flags,
+            resourceCount, tableLength, locationsSize, stringsSize);
     }
 
     void writeTo(ImageStream stream) {
-        stream.putInt(magic);
-        stream.putShort(majorVersion);
-        stream.putShort(minorVersion);
-        stream.putInt(locationCount);
-        stream.putInt(locationsSize);
-        stream.putInt(stringsSize);
+        stream.ensure(getHeaderSize());
+        writeTo(stream.getBuffer());
+    }
+
+    public void writeTo(ByteBuffer buffer) {
+        buffer.putInt(magic);
+        buffer.putInt(majorVersion << 16 | minorVersion);
+        buffer.putInt(flags);
+        buffer.putInt(resourceCount);
+        buffer.putInt(tableLength);
+        buffer.putInt(locationsSize);
+        buffer.putInt(stringsSize);
     }
 
     public int getMagic() {
@@ -100,16 +109,24 @@
         return minorVersion;
     }
 
-    public int getLocationCount() {
-        return locationCount;
+    public int getFlags() {
+        return flags;
+    }
+
+    public int getResourceCount() {
+        return resourceCount;
+    }
+
+    public int getTableLength() {
+        return tableLength;
     }
 
     public int getRedirectSize() {
-        return locationCount* 4;
+        return tableLength * 4;
     }
 
     public int getOffsetsSize() {
-        return locationCount* 4;
+        return tableLength * 4;
     }
 
     public int getLocationsSize() {
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageJavaSubstrate.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,242 @@
+/*
+ * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.internal.jimage;
+
+import java.io.IOException;
+import java.nio.ByteBuffer;
+import java.nio.ByteOrder;
+import java.nio.IntBuffer;
+import java.nio.channels.FileChannel;
+import java.nio.file.Paths;
+import static java.nio.file.StandardOpenOption.READ;
+import jdk.internal.jimage.decompressor.Decompressor;
+
+final class ImageJavaSubstrate implements ImageSubstrate {
+
+    private final String imagePath;
+    private final ByteOrder byteOrder;
+    private final FileChannel channel;
+    private final ImageHeader header;
+    private final long indexSize;
+    private final int[] redirect;
+    private final int[] offsets;
+    private final byte[] locations;
+    private final byte[] strings;
+
+    private final Decompressor decompressor = new Decompressor();
+
+  private ImageJavaSubstrate(String imagePath, ByteOrder byteOrder)
+          throws IOException {
+        this.imagePath = imagePath;
+        this.byteOrder = byteOrder;
+        channel = FileChannel.open(Paths.get(imagePath), READ);
+
+        int headerSize = ImageHeader.getHeaderSize();
+        ByteBuffer buffer = getIndexBuffer(0, headerSize);
+        header = ImageHeader.readFrom(buffer.asIntBuffer());
+
+        if (header.getMagic() != ImageHeader.MAGIC ||
+            header.getMajorVersion() != ImageHeader.MAJOR_VERSION ||
+            header.getMinorVersion() != ImageHeader.MINOR_VERSION) {
+            throw new IOException("Image not found \"" + imagePath + "\"");
+        }
+
+        indexSize = header.getIndexSize();
+
+        redirect = readIntegers(header.getRedirectOffset(),
+                                header.getRedirectSize());
+        offsets = readIntegers(header.getOffsetsOffset(),
+                               header.getOffsetsSize());
+        locations = readBytes(header.getLocationsOffset(),
+                              header.getLocationsSize());
+        strings = readBytes(header.getStringsOffset(),
+                            header.getStringsSize());
+    }
+
+    static ImageSubstrate openImage(String imagePath, ByteOrder byteOrder)
+            throws IOException {
+        return new ImageJavaSubstrate(imagePath, byteOrder);
+    }
+
+    @Override
+    public void close() {
+        try {
+            channel.close();
+        } catch (IOException ex) {
+            // Mostly harmless
+        }
+    }
+
+    @Override
+    public boolean supportsDataBuffer() {
+        return false;
+    }
+
+    private int[] readIntegers(long offset, long size) {
+        assert size < Integer.MAX_VALUE;
+        IntBuffer buffer = readBuffer(offset, size).asIntBuffer();
+        int[] integers = new int[(int)size / 4];
+        buffer.get(integers);
+
+        return integers;
+    }
+
+    private byte[] readBytes(long offset, long size) {
+        assert size < Integer.MAX_VALUE;
+        ByteBuffer buffer = readBuffer(offset, size);
+        byte[] bytes = new byte[(int)size];
+        buffer.get(bytes);
+
+        return bytes;
+    }
+
+    private ByteBuffer readBuffer(long offset, long size) {
+        assert size < Integer.MAX_VALUE;
+        ByteBuffer buffer = ByteBuffer.allocate((int)size);
+        buffer.order(byteOrder);
+
+        if (!readBuffer(buffer, offset, size)) {
+            return null;
+        }
+
+        return buffer;
+    }
+
+    private boolean readBuffer(ByteBuffer buffer, long offset, long size) {
+        assert size < Integer.MAX_VALUE;
+        assert buffer.limit() == size;
+        int read = 0;
+
+        try {
+            read = channel.read(buffer, offset);
+            buffer.rewind();
+        } catch (IOException ex) {
+            // fall thru
+        }
+
+        return read == size;
+    }
+
+    @Override
+    public ByteBuffer getIndexBuffer(long offset, long size) {
+        assert size < Integer.MAX_VALUE;
+        return readBuffer(offset, size);
+    }
+
+    @Override
+    public ByteBuffer getDataBuffer(long offset, long size) {
+        assert size < Integer.MAX_VALUE;
+        return getIndexBuffer(indexSize + offset, size);
+    }
+
+    @Override
+    public boolean read(long offset,
+                 ByteBuffer compressedBuffer, long compressedSize,
+                 ByteBuffer uncompressedBuffer, long uncompressedSize) {
+        assert compressedSize < Integer.MAX_VALUE;
+        assert uncompressedSize < Integer.MAX_VALUE;
+        boolean isRead = readBuffer(compressedBuffer,
+                                    indexSize + offset, compressedSize);
+        if (isRead) {
+            byte[] bytesIn = new byte[(int)compressedSize];
+            compressedBuffer.get(bytesIn);
+            byte[] bytesOut;
+            try {
+                bytesOut = decompressor.decompressResource(byteOrder, (int strOffset) -> {
+                    return new UTF8String(getStringBytes(strOffset)).toString();
+                }, bytesIn);
+            } catch (IOException ex) {
+                throw new RuntimeException(ex);
+            }
+            uncompressedBuffer.put(bytesOut);
+            uncompressedBuffer.rewind();
+        }
+
+        return isRead;
+    }
+
+    @Override
+    public boolean read(long offset,
+                 ByteBuffer uncompressedBuffer, long uncompressedSize) {
+        assert uncompressedSize < Integer.MAX_VALUE;
+        boolean isRead = readBuffer(uncompressedBuffer,
+                                    indexSize + offset, uncompressedSize);
+
+        return isRead;
+    }
+
+    @Override
+    public byte[] getStringBytes(int offset) {
+        if (offset == 0) {
+            return new byte[0];
+        }
+
+        int length = strings.length - offset;
+
+        for (int i = offset; i < strings.length; i++) {
+            if (strings[i] == 0) {
+                length = i - offset;
+                break;
+            }
+        }
+
+        byte[] bytes = new byte[length];
+        System.arraycopy(strings, offset, bytes, 0, length);
+
+        return bytes;
+    }
+
+    @Override
+    public long[] getAttributes(int offset) {
+        return ImageLocationBase.decompress(locations, offset);
+    }
+
+    @Override
+    public ImageLocation findLocation(UTF8String name, ImageStringsReader strings) {
+        int count = header.getTableLength();
+        int index = redirect[name.hashCode() % count];
+
+        if (index < 0) {
+            index = -index - 1;
+        } else {
+            index = name.hashCode(index) % count;
+        }
+
+        long[] attributes = getAttributes(offsets[index]);
+
+        ImageLocation imageLocation = new ImageLocation(attributes, strings);
+
+        if (!imageLocation.verify(name)) {
+            return null;
+        }
+
+        return imageLocation;
+   }
+
+    @Override
+    public int[] attributeOffsets() {
+        return offsets;
+    }
+}
--- a/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageLocation.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageLocation.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,369 +25,15 @@
 
 package jdk.internal.jimage;
 
-import java.nio.ByteBuffer;
-
-public final class ImageLocation {
-    final static int ATTRIBUTE_END = 0;
-    final static int ATTRIBUTE_BASE = 1;
-    final static int ATTRIBUTE_PARENT = 2;
-    final static int ATTRIBUTE_EXTENSION = 3;
-    final static int ATTRIBUTE_OFFSET = 4;
-    final static int ATTRIBUTE_COMPRESSED = 5;
-    final static int ATTRIBUTE_UNCOMPRESSED = 6;
-    final static int ATTRIBUTE_COUNT = 7;
-
-    private int locationOffset;
-    private long[] attributes;
-    private byte[] bytes;
-    private final ImageStrings strings;
-
-    private ImageLocation(ImageStrings strings) {
-        this.strings = strings;
-    }
-
-    void writeTo(ImageStream stream) {
-        compress();
-        locationOffset = stream.getPosition();
-        stream.put(bytes, 0, bytes.length);
-    }
-
-    static ImageLocation readFrom(ByteBuffer locationsBuffer, int offset, ImageStrings strings) {
-        final long[] attributes = new long[ATTRIBUTE_COUNT];
-
-        for (int i = offset; true; ) {
-            int data = locationsBuffer.get(i++) & 0xFF;
-            int kind = attributeKind(data);
-            assert ATTRIBUTE_END <= kind && kind < ATTRIBUTE_COUNT : "Invalid attribute kind";
-
-            if (kind == ATTRIBUTE_END) {
-                break;
-            }
-
-            int length = attributeLength(data);
-            long value = 0;
-
-            for (int j = 0; j < length; j++) {
-                value <<= 8;
-                value |= locationsBuffer.get(i++) & 0xFF;
-            }
-
-            attributes[kind] = value;
-        }
-
-        ImageLocation location =  new ImageLocation(strings);
-        location.attributes = attributes;
-
-        return location;
-    }
-
-    private static int attributeLength(int data) {
-        return (data & 0x7) + 1;
-    }
-
-    private static int attributeKind(int data) {
-        return data >>> 3;
-    }
-
-    public boolean verify(UTF8String name) {
-        UTF8String match = UTF8String.match(name, getParent());
-
-        if (match == null) {
-            return false;
-        }
-
-        match = UTF8String.match(match, getBase());
-
-        if (match == null) {
-            return false;
-        }
-
-        match = UTF8String.match(match, getExtension());
-
-        return match != null && match.length() == 0;
-    }
-
-
-    long getAttribute(int kind) {
-        assert ATTRIBUTE_END < kind && kind < ATTRIBUTE_COUNT : "Invalid attribute kind";
-        decompress();
-
-        return attributes[kind];
-    }
-
-    UTF8String getAttributeUTF8String(int kind) {
-        assert ATTRIBUTE_END < kind && kind < ATTRIBUTE_COUNT : "Invalid attribute kind";
-        decompress();
-
-        return strings.get((int)attributes[kind]);
-    }
-
-    String getAttributeString(int kind) {
-        return getAttributeUTF8String(kind).toString();
-    }
-
-    ImageLocation addAttribute(int kind, long value) {
-        assert ATTRIBUTE_END < kind && kind < ATTRIBUTE_COUNT : "Invalid attribute kind";
-        decompress();
-        attributes[kind] = value;
-        return this;
-    }
-
-    private void decompress() {
-        if (attributes == null) {
-            attributes = new long[ATTRIBUTE_COUNT];
-        }
-
-        if (bytes != null) {
-            for (int i = 0; i < bytes.length; ) {
-                int data = bytes[i++] & 0xFF;
-                int kind = attributeKind(data);
-
-                if (kind == ATTRIBUTE_END) {
-                    break;
-                }
-
-                assert ATTRIBUTE_END < kind && kind < ATTRIBUTE_COUNT : "Invalid attribute kind";
-                int length = attributeLength(data);
-                long value = 0;
-
-                for (int j = 0; j < length; j++) {
-                    value <<= 8;
-                    value |= bytes[i++] & 0xFF;
-                }
-
-                 attributes[kind] = value;
-            }
-
-            bytes = null;
-        }
-    }
-
-    private void compress() {
-        if (bytes == null) {
-            ImageStream stream = new ImageStream(16);
-
-            for (int kind = ATTRIBUTE_END + 1; kind < ATTRIBUTE_COUNT; kind++) {
-                long value = attributes[kind];
-
-                if (value != 0) {
-                    int n = (63 - Long.numberOfLeadingZeros(value)) >> 3;
-                    stream.put((kind << 3) | n);
-
-                    for (int i = n; i >= 0; i--) {
-                        stream.put((int)(value >> (i << 3)));
-                    }
-                }
-            }
-
-            stream.put(ATTRIBUTE_END << 3);
-            bytes = stream.toArray();
-            attributes = null;
-        }
+public final class ImageLocation  extends ImageLocationBase {
+    ImageLocation(long[] attributes, ImageStringsReader strings) {
+        super(attributes, strings);
     }
 
-    static ImageLocation newLocation(UTF8String fullname, ImageStrings strings, long contentOffset, long compressedSize, long uncompressedSize) {
-        UTF8String base;
-        UTF8String extension = extension(fullname);
-        int parentOffset = ImageStrings.EMPTY_OFFSET;
-        int extensionOffset = ImageStrings.EMPTY_OFFSET;
-        int baseOffset;
-
-        if (extension.length() != 0) {
-            UTF8String parent = parent(fullname);
-            base = base(fullname);
-            parentOffset = strings.add(parent);
-            extensionOffset = strings.add(extension);
-        } else {
-            base = fullname;
-        }
-
-        baseOffset = strings.add(base);
-
-        return new ImageLocation(strings)
-               .addAttribute(ATTRIBUTE_BASE, baseOffset)
-               .addAttribute(ATTRIBUTE_PARENT, parentOffset)
-               .addAttribute(ATTRIBUTE_EXTENSION, extensionOffset)
-               .addAttribute(ATTRIBUTE_OFFSET, contentOffset)
-               .addAttribute(ATTRIBUTE_COMPRESSED, compressedSize)
-               .addAttribute(ATTRIBUTE_UNCOMPRESSED, uncompressedSize);
-    }
-
-    @Override
-    public int hashCode() {
-        return getExtension().hashCode(getBase().hashCode(getParent().hashCode()));
-    }
-
-    int hashCode(int base) {
-        return getExtension().hashCode(getBase().hashCode(getParent().hashCode(base)));
-    }
-
-    @Override
-    public boolean equals(Object obj) {
-        if (this == obj) {
-            return true;
-        }
-
-        if (!(obj instanceof ImageLocation)) {
-            return false;
-        }
-
-        ImageLocation other = (ImageLocation)obj;
-
-        return getBaseOffset() == other.getBaseOffset() &&
-               getParentOffset() == other.getParentOffset() &&
-               getExtensionOffset() == other.getExtensionOffset();
-    }
-
-    static UTF8String parent(UTF8String fullname) {
-        int slash = fullname.lastIndexOf('/');
-
-        return slash == UTF8String.NOT_FOUND ? UTF8String.EMPTY_STRING : fullname.substring(0, slash + 1);
-    }
-
-    static UTF8String extension(UTF8String fullname) {
-        int dot = fullname.lastIndexOf('.');
-
-        return dot == UTF8String.NOT_FOUND ? UTF8String.EMPTY_STRING : fullname.substring(dot);
-    }
-
-    static UTF8String base(UTF8String fullname) {
-        int slash = fullname.lastIndexOf('/');
-
-        if (slash != UTF8String.NOT_FOUND) {
-            fullname = fullname.substring(slash + 1);
-        }
-
-        int dot = fullname.lastIndexOf('.');
-
-        if (dot != UTF8String.NOT_FOUND) {
-            fullname = fullname.substring(0, dot);
-        }
-
-        return fullname;
-    }
-
-    int getLocationOffset() {
-        return locationOffset;
-    }
-
-    UTF8String getBase() {
-        return getAttributeUTF8String(ATTRIBUTE_BASE);
-    }
-
-    public String getBaseString() {
-        return  getBase().toString();
-    }
-
-    int getBaseOffset() {
-        return (int)getAttribute(ATTRIBUTE_BASE);
-    }
-
-    UTF8String getParent() {
-        return getAttributeUTF8String(ATTRIBUTE_PARENT);
-    }
+    static ImageLocation readFrom(BasicImageReader reader, int offset) {
+        long[] attributes = reader.getAttributes(offset);
+        ImageStringsReader strings = reader.getStrings();
 
-    public String getParentString() {
-        return getParent().toString();
-    }
-
-    int getParentOffset() {
-        return (int)getAttribute(ATTRIBUTE_PARENT);
-    }
-
-    UTF8String getExtension() {
-        return getAttributeUTF8String(ATTRIBUTE_EXTENSION);
-    }
-
-    public String getExtensionString() {
-        return getExtension().toString();
-    }
-
-    int getExtensionOffset() {
-        return (int)getAttribute(ATTRIBUTE_EXTENSION);
-    }
-
-    UTF8String getName() {
-        return getBase().concat(getExtension());
-    }
-
-    String getNameString() {
-        return getName().toString();
-    }
-
-    UTF8String getFullname() {
-        return getParent().concat(getBase(), getExtension());
-    }
-
-    String getFullnameString() {
-        return getFullname().toString();
-    }
-
-    public long getContentOffset() {
-        return getAttribute(ATTRIBUTE_OFFSET);
-    }
-
-    public long getCompressedSize() {
-        return getAttribute(ATTRIBUTE_COMPRESSED);
-    }
-
-    public long getUncompressedSize() {
-        return getAttribute(ATTRIBUTE_UNCOMPRESSED);
-    }
-
-    @Override
-    public String toString() {
-        final StringBuilder sb = new StringBuilder();
-        decompress();
-
-        for (int kind = ATTRIBUTE_END + 1; kind < ATTRIBUTE_COUNT; kind++) {
-            long value = attributes[kind];
-
-            if (value == 0) {
-                continue;
-            }
-
-            switch (kind) {
-                case ATTRIBUTE_BASE:
-                    sb.append("Base: ");
-                    sb.append(value);
-                    sb.append(' ');
-                    sb.append(strings.get((int)value).toString());
-                    break;
-
-                case ATTRIBUTE_PARENT:
-                    sb.append("Parent: ");
-                    sb.append(value);
-                    sb.append(' ');
-                    sb.append(strings.get((int)value).toString());
-                    break;
-
-                case ATTRIBUTE_EXTENSION:
-                    sb.append("Extension: ");
-                    sb.append(value);
-                    sb.append(' ');
-                    sb.append(strings.get((int)value).toString());
-                    break;
-
-                case ATTRIBUTE_OFFSET:
-                    sb.append("Offset: ");
-                    sb.append(value);
-                    break;
-
-                case ATTRIBUTE_COMPRESSED:
-                    sb.append("Compressed: ");
-                    sb.append(value);
-                    break;
-
-                case ATTRIBUTE_UNCOMPRESSED:
-                    sb.append("Uncompressed: ");
-                    sb.append(value);
-                    break;
-           }
-
-           sb.append("; ");
-        }
-
-        return sb.toString();
+        return new ImageLocation(attributes, strings);
     }
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageLocationBase.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,264 @@
+/*
+ * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.internal.jimage;
+
+public class ImageLocationBase {
+    final static int ATTRIBUTE_END = 0;
+    final static int ATTRIBUTE_MODULE = 1;
+    final static int ATTRIBUTE_PARENT = 2;
+    final static int ATTRIBUTE_BASE = 3;
+    final static int ATTRIBUTE_EXTENSION = 4;
+    final static int ATTRIBUTE_OFFSET = 5;
+    final static int ATTRIBUTE_COMPRESSED = 6;
+    final static int ATTRIBUTE_UNCOMPRESSED = 7;
+    final static int ATTRIBUTE_COUNT = 8;
+
+    protected final long[] attributes;
+
+    protected final ImageStrings strings;
+
+    protected ImageLocationBase(long[] attributes, ImageStrings strings) {
+        this.attributes = attributes;
+        this.strings = strings;
+    }
+
+    ImageStrings getStrings() {
+        return strings;
+    }
+
+    private static int attributeLength(int data) {
+        return (data & 0x7) + 1;
+    }
+
+    private static int attributeKind(int data) {
+        return data >>> 3;
+    }
+
+    static long[] decompress(byte[] bytes) {
+        return decompress(bytes, 0);
+    }
+
+    static long[] decompress(byte[] bytes, int offset) {
+        long[] attributes = new long[ATTRIBUTE_COUNT];
+
+        if (bytes != null) {
+            for (int i = offset; i < bytes.length; ) {
+                int data = bytes[i++] & 0xFF;
+                int kind = attributeKind(data);
+
+                if (kind == ATTRIBUTE_END) {
+                    break;
+                }
+
+                assert ATTRIBUTE_END < kind &&
+                       kind < ATTRIBUTE_COUNT : "Invalid attribute kind";
+                int length = attributeLength(data);
+                long value = 0;
+
+                for (int j = 0; j < length; j++) {
+                    value <<= 8;
+                    value |= bytes[i++] & 0xFF;
+                }
+
+                 attributes[kind] = value;
+            }
+        }
+
+        return attributes;
+    }
+
+    static byte[] compress(long[] attributes) {
+        ImageStream stream = new ImageStream(16);
+
+        for (int kind = ATTRIBUTE_END + 1; kind < ATTRIBUTE_COUNT; kind++) {
+            long value = attributes[kind];
+
+            if (value != 0) {
+                int n = (63 - Long.numberOfLeadingZeros(value)) >> 3;
+                stream.put((kind << 3) | n);
+
+                for (int i = n; i >= 0; i--) {
+                    stream.put((int)(value >> (i << 3)));
+                }
+            }
+        }
+
+        stream.put(ATTRIBUTE_END << 3);
+
+        return stream.toArray();
+     }
+
+    public boolean verify(UTF8String name) {
+        return UTF8String.equals(getFullName(), name);
+    }
+
+    protected long getAttribute(int kind) {
+        assert ATTRIBUTE_END < kind &&
+               kind < ATTRIBUTE_COUNT : "Invalid attribute kind";
+
+        return attributes[kind];
+    }
+
+    protected UTF8String getAttributeUTF8String(int kind) {
+        assert ATTRIBUTE_END < kind &&
+               kind < ATTRIBUTE_COUNT : "Invalid attribute kind";
+
+        return getStrings().get((int)attributes[kind]);
+    }
+
+    protected String getAttributeString(int kind) {
+        return getAttributeUTF8String(kind).toString();
+    }
+
+    UTF8String getModule() {
+        return getAttributeUTF8String(ATTRIBUTE_MODULE);
+    }
+
+    public String getModuleString() {
+        return getModule().toString();
+    }
+
+    int getModuleOffset() {
+        return (int)getAttribute(ATTRIBUTE_MODULE);
+    }
+
+    UTF8String getBase() {
+        return getAttributeUTF8String(ATTRIBUTE_BASE);
+    }
+
+    public String getBaseString() {
+        return  getBase().toString();
+    }
+
+    int getBaseOffset() {
+        return (int)getAttribute(ATTRIBUTE_BASE);
+    }
+
+    UTF8String getParent() {
+        return getAttributeUTF8String(ATTRIBUTE_PARENT);
+    }
+
+    public String getParentString() {
+        return getParent().toString();
+    }
+
+    int getParentOffset() {
+        return (int)getAttribute(ATTRIBUTE_PARENT);
+    }
+
+    UTF8String getExtension() {
+        return getAttributeUTF8String(ATTRIBUTE_EXTENSION);
+    }
+
+    public String getExtensionString() {
+        return getExtension().toString();
+    }
+
+    int getExtensionOffset() {
+        return (int)getAttribute(ATTRIBUTE_EXTENSION);
+    }
+
+    UTF8String getFullName() {
+        return getFullName(false);
+    }
+
+    UTF8String getFullName(boolean modulesPrefix) {
+        // Note: Consider a UTF8StringBuilder.
+        UTF8String fullName = UTF8String.EMPTY_STRING;
+
+        if (getModuleOffset() != 0) {
+            fullName = fullName.concat(
+                // TODO The use of UTF8String.MODULES_STRING does not belong here.
+                modulesPrefix? UTF8String.MODULES_STRING :
+                               UTF8String.EMPTY_STRING,
+                UTF8String.SLASH_STRING,
+                getModule(),
+                UTF8String.SLASH_STRING);
+        }
+
+        if (getParentOffset() != 0) {
+            fullName = fullName.concat(getParent(),
+                                       UTF8String.SLASH_STRING);
+        }
+
+        fullName = fullName.concat(getBase());
+
+        if (getExtensionOffset() != 0) {
+                fullName = fullName.concat(UTF8String.DOT_STRING,
+                                           getExtension());
+        }
+
+        return fullName;
+    }
+
+    UTF8String buildName(boolean includeModule, boolean includeParent,
+            boolean includeName) {
+        // Note: Consider a UTF8StringBuilder.
+        UTF8String name = UTF8String.EMPTY_STRING;
+
+        if (includeModule && getModuleOffset() != 0) {
+            name = name.concat(UTF8String.MODULES_STRING,
+                               UTF8String.SLASH_STRING,
+                               getModule());
+        }
+
+        if (includeParent && getParentOffset() != 0) {
+            name = name.concat(UTF8String.SLASH_STRING,
+                                       getParent());
+        }
+
+        if (includeName) {
+            if (includeModule || includeParent) {
+                name = name.concat(UTF8String.SLASH_STRING);
+            }
+
+            name = name.concat(getBase());
+
+            if (getExtensionOffset() != 0) {
+                name = name.concat(UTF8String.DOT_STRING,
+                                           getExtension());
+            }
+        }
+
+        return name;
+    }
+
+    String getFullNameString() {
+        return getFullName().toString();
+    }
+
+    public long getContentOffset() {
+        return getAttribute(ATTRIBUTE_OFFSET);
+    }
+
+    public long getCompressedSize() {
+        return getAttribute(ATTRIBUTE_COMPRESSED);
+    }
+
+    public long getUncompressedSize() {
+        return getAttribute(ATTRIBUTE_UNCOMPRESSED);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageLocationWriter.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,140 @@
+/*
+ * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.internal.jimage;
+
+public final class ImageLocationWriter extends ImageLocationBase {
+    private int locationOffset;
+
+    private ImageLocationWriter(ImageStringsWriter strings) {
+        super(new long[ATTRIBUTE_COUNT], strings);
+    }
+
+    void writeTo(ImageStream stream) {
+        byte[] bytes = ImageLocation.compress(attributes);
+        locationOffset = stream.getPosition();
+        stream.put(bytes, 0, bytes.length);
+    }
+
+    private ImageLocationWriter addAttribute(int kind, long value) {
+        assert ATTRIBUTE_END < kind &&
+               kind < ATTRIBUTE_COUNT : "Invalid attribute kind";
+        attributes[kind] = value;
+        return this;
+    }
+
+    private ImageLocationWriter addAttribute(int kind, UTF8String value) {
+        return addAttribute(kind, strings.add(value));
+    }
+
+    static ImageLocationWriter newLocation(UTF8String fullName,
+            ImageStringsWriter strings,
+            long contentOffset, long compressedSize, long uncompressedSize) {
+        UTF8String moduleName = UTF8String.EMPTY_STRING;
+        UTF8String parentName = UTF8String.EMPTY_STRING;
+        UTF8String baseName;
+        UTF8String extensionName = UTF8String.EMPTY_STRING;
+
+        int offset = fullName.indexOf('/', 1);
+        if (fullName.length() >= 2 && fullName.charAt(0) == '/' && offset != -1) {
+            moduleName = fullName.substring(1, offset - 1);
+            fullName = fullName.substring(offset + 1);
+        }
+
+        offset = fullName.lastIndexOf('/');
+        if (offset != -1) {
+            parentName = fullName.substring(0, offset);
+            fullName = fullName.substring(offset + 1);
+        }
+
+        offset = fullName.lastIndexOf('.');
+        if (offset != -1) {
+            baseName = fullName.substring(0, offset);
+            extensionName = fullName.substring(offset + 1);
+        } else {
+            baseName = fullName;
+        }
+
+        return new ImageLocationWriter(strings)
+               .addAttribute(ATTRIBUTE_MODULE, moduleName)
+               .addAttribute(ATTRIBUTE_PARENT, parentName)
+               .addAttribute(ATTRIBUTE_BASE, baseName)
+               .addAttribute(ATTRIBUTE_EXTENSION, extensionName)
+               .addAttribute(ATTRIBUTE_OFFSET, contentOffset)
+               .addAttribute(ATTRIBUTE_COMPRESSED, compressedSize)
+               .addAttribute(ATTRIBUTE_UNCOMPRESSED, uncompressedSize);
+    }
+
+    @Override
+    public int hashCode() {
+        return hashCode(UTF8String.HASH_MULTIPLIER);
+    }
+
+    int hashCode(int seed) {
+        int hash = seed;
+
+        if (getModuleOffset() != 0) {
+            hash = UTF8String.SLASH_STRING.hashCode(hash);
+            hash = getModule().hashCode(hash);
+            hash = UTF8String.SLASH_STRING.hashCode(hash);
+        }
+
+        if (getParentOffset() != 0) {
+            hash = getParent().hashCode(hash);
+            hash = UTF8String.SLASH_STRING.hashCode(hash);
+        }
+
+        hash = getBase().hashCode(hash);
+
+        if (getExtensionOffset() != 0) {
+            hash = UTF8String.DOT_STRING.hashCode(hash);
+            hash = getExtension().hashCode(hash);
+        }
+
+        return hash;
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj) {
+            return true;
+        }
+
+        if (!(obj instanceof ImageLocationWriter)) {
+            return false;
+        }
+
+        ImageLocation other = (ImageLocation)obj;
+
+        return getModuleOffset() == other.getModuleOffset() &&
+               getParentOffset() == other.getParentOffset() &&
+               getBaseOffset() == other.getBaseOffset() &&
+               getExtensionOffset() == other.getExtensionOffset();
+    }
+
+    int getLocationOffset() {
+        return locationOffset;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageModuleData.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,288 @@
+/*
+ * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.internal.jimage;
+
+import java.nio.ByteBuffer;
+import java.nio.IntBuffer;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+
+/*
+ * Manage module meta data.
+ *
+ * NOTE: needs revision.
+ * Each loader requires set of module meta data to identify which modules and
+ * packages are managed by that loader.  Currently, there is one image file per
+ * loader, so only one  module meta data resource per file.
+ *
+ * Each element in the module meta data is a native endian 4 byte integer.  Note
+ * that entries with zero offsets for string table entries should be ignored (
+ * padding for hash table lookup.)
+ *
+ * Format:
+ *    Count of package to module entries
+ *    Count of module to package entries
+ *    Perfect Hash redirect table[Count of package to module entries]
+ *    Package to module entries[Count of package to module entries]
+ *        Offset to package name in string table
+ *        Offset to module name in string table
+ *    Perfect Hash redirect table[Count of module to package entries]
+ *    Module to package entries[Count of module to package entries]
+ *        Offset to module name in string table
+ *        Count of packages in module
+ *        Offset to first package in packages table
+ *    Packages[]
+ *        Offset to package name in string table
+ */
+
+final public class ImageModuleData {
+    public final static String META_DATA_EXTENSION = ".jdata";
+    public final static String SEPARATOR = "\t";
+    public final static int NOT_FOUND = -1;
+    private final static int ptmCountOffset = 0;
+    private final static int mtpCountOffset = 1;
+    private final static int ptmRedirectOffset = 2;
+    private final static int dataNameOffset = 0;
+    private final static int ptmDataWidth = 2;
+    private final static int ptmDataModuleOffset = 1;
+    private final static int mtpDataWidth = 3;
+    private final static int mtpDataCountOffset = 1;
+    private final static int mtpDataOffsetOffset = 2;
+
+    private final BasicImageReader reader;
+    private final IntBuffer intBuffer;
+    private final int ptmRedirectLength;
+    private final int mtpRedirectLength;
+    private final int ptmDataOffset;
+    private final int mtpRedirectOffset;
+    private final int mtpDataOffset;
+    private final int mtpPackagesOffset;
+
+    public ImageModuleData(BasicImageReader reader) {
+         this(reader, getBytes(reader));
+    }
+
+    public ImageModuleData(BasicImageReader reader, byte[] bytes) {
+        this.reader = reader;
+
+        ByteBuffer byteBuffer = ByteBuffer.wrap(bytes).order(reader.getByteOrder());
+        this.intBuffer = byteBuffer.asIntBuffer();
+
+        this.ptmRedirectLength = get(ptmCountOffset);
+        this.mtpRedirectLength = get(mtpCountOffset);
+
+        this.ptmDataOffset = ptmRedirectOffset + ptmRedirectLength;
+        this.mtpRedirectOffset = ptmDataOffset + ptmRedirectLength * ptmDataWidth;
+        this.mtpDataOffset = mtpRedirectOffset + mtpRedirectLength;
+        this.mtpPackagesOffset = mtpDataOffset + mtpRedirectLength * mtpDataWidth;
+    }
+
+    private static byte[] getBytes(BasicImageReader reader) {
+        String loaderName = reader.imagePathName();
+
+        if (loaderName.endsWith(BasicImageWriter.IMAGE_EXT)) {
+            loaderName = loaderName.substring(0, loaderName.length() -
+                    BasicImageWriter.IMAGE_EXT.length());
+        }
+
+        byte[] bytes = reader.getResource(getModuleDataName(loaderName));
+
+        if (bytes == null) {
+            throw new InternalError("module data missing");
+        }
+
+        return bytes;
+    }
+
+    public List<String> fromModulePackages() {
+        List<String> lines = new ArrayList<>();
+
+        for (int i = 0; i < mtpRedirectLength; i++) {
+            int index = mtpDataOffset + i * mtpDataWidth;
+            int offset = get(index + dataNameOffset);
+
+            if (offset != 0) {
+                StringBuilder sb = new StringBuilder();
+
+                sb.append(getString(offset));
+
+                int count = get(index + mtpDataCountOffset);
+                int base = get(index + mtpDataOffsetOffset) + mtpPackagesOffset;
+
+                for (int j = 0; j < count; j++) {
+                    sb.append(SEPARATOR);
+                    sb.append(stringAt(base + j));
+                }
+
+                lines.add(sb.toString());
+            }
+        }
+
+        return lines;
+    }
+
+    public static String getModuleDataName(String loaderName) {
+        return loaderName + META_DATA_EXTENSION;
+    }
+
+    private int get(int index) {
+        return intBuffer.get(index);
+    }
+
+    private String getString(int offset) {
+        return reader.getString(offset);
+    }
+
+    private String stringAt(int index) {
+        return reader.getString(get(index));
+    }
+
+    private UTF8String getUTF8String(int offset) {
+        return reader.getUTF8String(offset);
+    }
+
+    private UTF8String utf8StringAt(int index) {
+        return reader.getUTF8String(get(index));
+    }
+
+    private int find(UTF8String name, int baseOffset, int length, int width) {
+        if (length == 0) {
+            return NOT_FOUND;
+        }
+
+        int hashCode = name.hashCode();
+        int index = hashCode % length;
+        int value = get(baseOffset + index);
+
+        if (value > 0 ) {
+            hashCode = name.hashCode(value);
+            index = hashCode % length;
+        } else if (value < 0) {
+            index = -1 - value;
+        } else {
+            return NOT_FOUND;
+        }
+
+        index = baseOffset + length + index * width;
+
+        if (!utf8StringAt(index + dataNameOffset).equals(name)) {
+            return NOT_FOUND;
+        }
+
+        return index;
+    }
+
+    public String packageToModule(String packageName) {
+        UTF8String moduleName = packageToModule(new UTF8String(packageName));
+
+        return moduleName != null ? moduleName.toString() : null;
+    }
+
+    public UTF8String packageToModule(UTF8String packageName) {
+        int index = find(packageName, ptmRedirectOffset, ptmRedirectLength, ptmDataWidth);
+
+        if (index != NOT_FOUND) {
+            return utf8StringAt(index + ptmDataModuleOffset);
+        }
+
+        return null;
+    }
+
+    public List<String> moduleToPackages(String moduleName) {
+        int index = find(new UTF8String(moduleName), mtpRedirectOffset,
+                mtpRedirectLength, mtpDataWidth);
+
+        if (index != NOT_FOUND) {
+            int count = get(index + mtpDataCountOffset);
+            int base = get(index + mtpDataOffsetOffset) + mtpPackagesOffset;
+            List<String> packages = new ArrayList<>(count);
+
+            for (int i = 0; i < count; i++) {
+                packages.add(stringAt(base + i));
+            }
+
+            return packages;
+        }
+
+        return null;
+    }
+
+    public List<String> allPackageNames() {
+        List<String> packages = new ArrayList<>();
+
+        for (int i = 0; i < ptmRedirectLength; i++) {
+            int offset = get(ptmDataOffset + i * ptmDataWidth + dataNameOffset);
+
+            if (offset != 0) {
+                packages.add(getString(offset));
+            }
+        }
+
+        return packages;
+    }
+
+    public Set<String> allModuleNames() {
+        Set<String> modules = new HashSet<>();
+
+        for (int i = 0; i < mtpRedirectLength; i++) {
+            int index = mtpDataOffset + i * mtpDataWidth;
+            int offset = get(index + dataNameOffset);
+
+            if (offset != 0) {
+                modules.add(getString(offset));
+            }
+        }
+
+        return modules;
+    }
+
+    public Map<String, String> packageModuleMap() {
+        Map<String, String> map = new HashMap<>();
+
+        for (int i = 0; i < mtpRedirectLength; i++) {
+            int index = mtpDataOffset + i * mtpDataWidth;
+            int offset = get(index + dataNameOffset);
+
+            if (offset != 0) {
+                String moduleName = getString(offset);
+
+                int count = get(index + mtpDataCountOffset);
+                int base = get(index + mtpDataOffsetOffset) + mtpPackagesOffset;
+
+                for (int j = 0; j < count; j++) {
+                    map.put(stringAt(base + j), moduleName);
+                }
+            }
+        }
+
+        return map;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageModuleDataWriter.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,172 @@
+/*
+ * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.internal.jimage;
+
+import java.io.DataOutputStream;
+import java.io.IOException;
+import java.util.Arrays;
+import java.util.LinkedHashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+import java.util.function.Function;
+import java.util.stream.Collectors;
+
+public class ImageModuleDataWriter {
+    final byte[] bytes;
+
+    public ImageModuleDataWriter(BasicImageWriter writer,
+            Map<String, List<String>> modulePackages) {
+        PerfectHashBuilder<String> packageToModule = new PerfectHashBuilder<>(
+                new PerfectHashBuilder.Entry<String>().getClass(),
+                new PerfectHashBuilder.Bucket<String>().getClass());
+        PerfectHashBuilder<List<String>> moduleToPackages = new PerfectHashBuilder<>(
+                new PerfectHashBuilder.Entry<List<String>>().getClass(),
+                new PerfectHashBuilder.Bucket<List<String>>().getClass());
+
+        modulePackages.entrySet().stream().forEach((entry) -> {
+            String moduleName = entry.getKey();
+            List<String> packages = entry.getValue();
+            packages.stream().forEach((packageName) -> {
+                packageToModule.put(packageName, moduleName);
+            });
+
+            moduleToPackages.put(moduleName, packages);
+        });
+
+        packageToModule.generate();
+        moduleToPackages.generate();
+
+        bytes = getBytes(writer, packageToModule, moduleToPackages);
+    }
+
+    public static ImageModuleDataWriter buildModuleData(BasicImageWriter writer,
+            Map<String, Set<String>> modulePackagesMap) {
+        Set<String> modules = modulePackagesMap.keySet();
+
+        Map<String, List<String>> modulePackages = new LinkedHashMap<>();
+        modules.stream().sorted().forEach((moduleName) -> {
+            List<String> localPackages = modulePackagesMap.get(moduleName).stream()
+                    .map(pn -> pn.replace('.', '/'))
+                    .sorted()
+                    .collect(Collectors.toList());
+            modulePackages.put(moduleName, localPackages);
+        });
+
+        return new ImageModuleDataWriter(writer, modulePackages);
+    }
+
+    public static Map<String, List<String>> toModulePackages(List<String> lines) {
+        Map<String, List<String>> modulePackages = new LinkedHashMap<>();
+
+        for (String line : lines) {
+            String[] parts = line.split(ImageModuleData.SEPARATOR);
+            String moduleName = parts[0];
+            List<String> packages = Arrays.asList(Arrays.copyOfRange(parts, 1, parts.length));
+            modulePackages.put(moduleName, packages);
+        }
+
+        return modulePackages;
+    }
+
+    public void addLocation(String name, BasicImageWriter writer) {
+        writer.addLocation(ImageModuleData.getModuleDataName(name), 0, 0, bytes.length);
+    }
+
+    private byte[] getBytes(BasicImageWriter writer,
+            PerfectHashBuilder<String> packageToModule,
+            PerfectHashBuilder<List<String>> moduleToPackages) {
+        ImageStream stream = new ImageStream(writer.getByteOrder());
+
+        // Empty jimage
+        if (packageToModule.getCount() == 0) {
+            stream.putInt(0);
+            stream.putInt(0);
+            return stream.toArray();
+        }
+
+        int[] ptmRedirect = packageToModule.getRedirect();
+        int[] mtpRedirect = moduleToPackages.getRedirect();
+        PerfectHashBuilder.Entry<String>[] ptmOrder = packageToModule.getOrder();
+        PerfectHashBuilder.Entry<List<String>>[] mtpOrder = moduleToPackages.getOrder();
+
+        stream.putInt(ptmRedirect.length);
+        stream.putInt(mtpRedirect.length);
+
+        for (int value : ptmRedirect) {
+            stream.putInt(value);
+        }
+
+        for (PerfectHashBuilder.Entry<String> entry : ptmOrder) {
+            if (entry != null) {
+                stream.putInt(writer.addString(entry.getKey()));
+                stream.putInt(writer.addString(entry.getValue()));
+            } else {
+                stream.putInt(0);
+                stream.putInt(0);
+            }
+        }
+
+        for (int value : mtpRedirect) {
+            stream.putInt(value);
+        }
+
+        int index = 0;
+
+        for (PerfectHashBuilder.Entry<List<String>> entry : mtpOrder) {
+            if (entry != null) {
+                int count = entry.getValue().size();
+                stream.putInt(writer.addString(entry.getKey()));
+                stream.putInt(count);
+                stream.putInt(index);
+                index += count;
+            } else {
+                stream.putInt(0);
+                stream.putInt(0);
+                stream.putInt(0);
+            }
+        }
+
+        for (PerfectHashBuilder.Entry<List<String>> entry : mtpOrder) {
+            if (entry != null) {
+                List<String> value = entry.getValue();
+                value.stream().forEach((packageName) -> {
+                    stream.putInt(writer.addString(packageName));
+                });
+            }
+        }
+
+        return stream.toArray();
+    }
+
+    public void writeTo(DataOutputStream out) throws IOException {
+         out.write(bytes, 0, bytes.length);
+    }
+
+    public int size() {
+        return bytes.length;
+    }
+}
--- a/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageModules.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,180 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.  Oracle designates this
- * particular file as subject to the "Classpath" exception as provided
- * by Oracle in the LICENSE file that accompanied this code.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package jdk.internal.jimage;
-
-import java.io.DataOutputStream;
-import java.io.IOException;
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.LinkedHashMap;
-import java.util.LinkedHashSet;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-import java.util.stream.Collectors;
-
-import static jdk.internal.jimage.PackageModuleMap.*;
-
-public class ImageModules {
-    protected final Map<Loader, LoaderModuleData> loaders = new LinkedHashMap<>();
-    protected final Map<String, Set<String>> localPkgs = new HashMap<>();
-
-    protected ImageModules() {}
-
-    public ImageModules(Set<String> bootModules,
-                        Set<String> extModules,
-                        Set<String> appModules) throws IOException {
-        mapModulesToLoader(Loader.BOOT_LOADER, bootModules);
-        mapModulesToLoader(Loader.EXT_LOADER, extModules);
-        mapModulesToLoader(Loader.APP_LOADER, appModules);
-    }
-
-    public Map<String, Set<String>> packages() {
-        return localPkgs;
-    }
-
-    // ## FIXME: should be package-private
-    // When jlink legacy format support is removed, it should
-    // use the package table in the jimage.
-    public void setPackages(String mn, Set<String> pkgs) {
-        localPkgs.put(mn, pkgs);
-    }
-
-    /*
-     * Returns the name of modules mapped to a given class loader in the image
-     */
-    public Set<String> getModules(Loader type) {
-        if (loaders.containsKey(type)) {
-            return loaders.get(type).modules();
-        } else {
-            return Collections.emptySet();
-        }
-    }
-
-    private void mapModulesToLoader(Loader loader, Set<String> modules) {
-        if (modules.isEmpty())
-            return;
-
-        // put java.base first
-        Set<String> mods = new LinkedHashSet<>();
-        modules.stream()
-               .filter(m -> m.equals("java.base"))
-               .forEach(mods::add);
-        modules.stream().sorted()
-               .filter(m -> !m.equals("java.base"))
-               .forEach(mods::add);
-        loaders.put(loader, new LoaderModuleData(loader, mods));
-    }
-
-    enum Loader {
-        BOOT_LOADER(0, "bootmodules"),
-        EXT_LOADER(1, "extmodules"),
-        APP_LOADER(2, "appmodules");  // ## may be more than 1 loader
-
-        final int id;
-        final String name;
-        Loader(int id, String name) {
-            this.id = id;
-            this.name = name;
-        }
-
-        String getName() {
-            return name;
-        }
-        static Loader get(int id) {
-            switch (id) {
-                case 0: return BOOT_LOADER;
-                case 1: return EXT_LOADER;
-                case 2: return APP_LOADER;
-                default:
-                    throw new IllegalArgumentException("invalid loader id: " + id);
-            }
-        }
-        public int id() { return id; }
-    }
-
-    public class LoaderModuleData {
-        private final Loader loader;
-        private final Set<String> modules;
-        LoaderModuleData(Loader loader, Set<String> modules) {
-            this.loader = loader;
-            this.modules = Collections.unmodifiableSet(modules);
-        }
-
-        Set<String> modules() {
-            return modules;
-        }
-        Loader loader() { return loader; }
-    }
-
-    ModuleIndex buildModuleIndex(Loader type, BasicImageWriter writer) {
-        return new ModuleIndex(getModules(type), writer);
-    }
-
-    /*
-     * Generate module name table and the package map as resources
-     * in the modular image
-     */
-    public class ModuleIndex {
-        final Map<String, Integer> moduleOffsets = new LinkedHashMap<>();
-        final Map<String, List<Integer>> packageOffsets = new HashMap<>();
-        final int size;
-        public ModuleIndex(Set<String> mods, BasicImageWriter writer) {
-            // module name offsets
-            writer.addLocation(MODULES_ENTRY, 0, 0, mods.size() * 4);
-            long offset = mods.size() * 4;
-            for (String mn : mods) {
-                moduleOffsets.put(mn, writer.addString(mn));
-                List<Integer> poffsets = localPkgs.get(mn).stream()
-                        .map(pn -> pn.replace('.', '/'))
-                        .map(writer::addString)
-                        .collect(Collectors.toList());
-                // package name offsets per module
-                String entry = mn + "/" + PACKAGES_ENTRY;
-                int bytes = poffsets.size() * 4;
-                writer.addLocation(entry, offset, 0, bytes);
-                offset += bytes;
-                packageOffsets.put(mn, poffsets);
-            }
-            this.size = (int) offset;
-        }
-
-        void writeTo(DataOutputStream out) throws IOException {
-            for (int moffset : moduleOffsets.values()) {
-                out.writeInt(moffset);
-            }
-            for (String mn : moduleOffsets.keySet()) {
-                for (int poffset : packageOffsets.get(mn)) {
-                    out.writeInt(poffset);
-                }
-            }
-        }
-
-        int size() {
-            return size;
-        }
-    }
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageNativeSubstrate.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,134 @@
+/*
+ * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.internal.jimage;
+
+import java.io.IOException;
+import java.nio.ByteBuffer;
+import java.nio.ByteOrder;
+import sun.misc.JavaNioAccess;
+import sun.misc.SharedSecrets;
+
+final class ImageNativeSubstrate implements ImageSubstrate {
+    private static final JavaNioAccess NIOACCESS =
+            SharedSecrets.getJavaNioAccess();
+
+    private final long id;
+    private final long indexAddress;
+    private final long dataAddress;
+
+    native static long openImage(String imagePath, boolean bigEndian);
+    native static void closeImage(long id);
+    native static long getIndexAddress(long id);
+    native static long getDataAddress(long id);
+    native static boolean readCompressed(long id, long offset,
+            ByteBuffer compressedBuffer, long compressedSize,
+            ByteBuffer uncompressedBuffer, long uncompressedSize);
+    native static boolean read(long id, long offset,
+            ByteBuffer uncompressedBuffer, long uncompressedSize);
+    native static byte[] getStringBytes(long id, int offset);
+    native static long[] getAttributes(long id, int offset);
+    native static long[] findAttributes(long id, byte[] path);
+    native static int[] attributeOffsets(long id);
+
+    static ByteBuffer newDirectByteBuffer(long address, long capacity) {
+        assert capacity < Integer.MAX_VALUE;
+        return NIOACCESS.newDirectByteBuffer(address, (int)capacity, null);
+    }
+
+    private ImageNativeSubstrate(long id) {
+        this.id = id;
+        this.indexAddress = getIndexAddress(id);
+        this.dataAddress = getDataAddress(id);
+    }
+
+    static ImageSubstrate openImage(String imagePath, ByteOrder byteOrder)
+            throws IOException {
+        long id = openImage(imagePath, byteOrder == ByteOrder.BIG_ENDIAN);
+
+        if (id == 0) {
+             throw new IOException("Image not found \"" + imagePath + "\"");
+        }
+
+        return new ImageNativeSubstrate(id);
+    }
+
+    @Override
+    public void close() {
+        closeImage(id);
+    }
+
+    @Override
+    public ByteBuffer getIndexBuffer(long offset, long size) {
+        return newDirectByteBuffer(indexAddress + offset, size);
+    }
+
+    @Override
+    public ByteBuffer getDataBuffer(long offset, long size) {
+        return dataAddress != 0 ?
+                newDirectByteBuffer(dataAddress + offset, size) : null;
+    }
+
+    @Override
+    public boolean supportsDataBuffer() {
+        return dataAddress != 0;
+    }
+
+    @Override
+    public boolean read(long offset,
+                 ByteBuffer compressedBuffer, long compressedSize,
+                 ByteBuffer uncompressedBuffer, long uncompressedSize) {
+        return readCompressed(id, offset,
+                    compressedBuffer, compressedSize,
+                    uncompressedBuffer, uncompressedSize);
+    }
+
+    @Override
+    public boolean read(long offset,
+                 ByteBuffer uncompressedBuffer, long uncompressedSize) {
+        return read(id, offset, uncompressedBuffer, uncompressedSize);
+    }
+
+    @Override
+    public byte[] getStringBytes(int offset) {
+        return getStringBytes(id, offset);
+    }
+
+    @Override
+    public long[] getAttributes(int offset) {
+        return getAttributes(id, offset);
+    }
+
+    @Override
+    public ImageLocation findLocation(UTF8String name, ImageStringsReader strings) {
+        long[] attributes = findAttributes(id, name.getBytes());
+
+        return attributes != null ? new ImageLocation(attributes, strings) : null;
+    }
+
+    @Override
+    public int[] attributeOffsets() {
+        return attributeOffsets(id);
+    }
+}
--- a/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageReader.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageReader.java	Wed Jul 05 20:42:36 2017 +0200
@@ -26,12 +26,10 @@
 
 import java.io.IOException;
 import java.io.UncheckedIOException;
-import java.net.URI;
 import java.nio.ByteBuffer;
 import java.nio.ByteOrder;
 import java.nio.IntBuffer;
 import java.nio.file.Files;
-import java.nio.file.FileSystem;
 import java.nio.file.attribute.BasicFileAttributes;
 import java.nio.file.attribute.FileTime;
 import java.nio.file.Paths;
@@ -42,13 +40,11 @@
 import java.util.List;
 import java.util.Map;
 import java.util.function.Consumer;
-import java.util.function.Supplier;
+import static jdk.internal.jimage.UTF8String.*;
 
 public class ImageReader extends BasicImageReader {
     // well-known strings needed for image file system.
-    static final UTF8String ROOT = new UTF8String("/");
-    static final UTF8String META_INF = new UTF8String("/META-INF");
-    static final UTF8String PACKAGES_OFFSETS = new UTF8String("packages.offsets");
+    static final UTF8String ROOT_STRING = UTF8String.SLASH_STRING;
 
     // attributes of the .jimage file. jimage file does not contain
     // attributes for the individual resources (yet). We use attributes
@@ -56,15 +52,18 @@
     // Iniitalized lazily, see {@link #imageFileAttributes()}.
     private BasicFileAttributes imageFileAttributes;
 
-    private final Map<String, String> packageMap;
+    private final ImageModuleData moduleData;
 
     // directory management implementation
     private final Map<UTF8String, Node> nodes;
     private volatile Directory rootDir;
 
+    private Directory packagesDir;
+    private Directory modulesDir;
+
     ImageReader(String imagePath, ByteOrder byteOrder) throws IOException {
         super(imagePath, byteOrder);
-        this.packageMap = PackageModuleMap.readFrom(this);
+        this.moduleData = new ImageModuleData(this);
         this.nodes = Collections.synchronizedMap(new HashMap<>());
     }
 
@@ -89,11 +88,42 @@
         clearNodes();
     }
 
+    @Override
+    public ImageLocation findLocation(UTF8String name) {
+        ImageLocation location = super.findLocation(name);
+
+        // NOTE: This should be removed when module system is up in full.
+        if (location == null) {
+            int index = name.lastIndexOf('/');
+
+            if (index != -1) {
+                UTF8String packageName = name.substring(0, index);
+                UTF8String moduleName = moduleData.packageToModule(packageName);
+
+                if (moduleName != null) {
+                    UTF8String fullName = UTF8String.SLASH_STRING.concat(moduleName,
+                            UTF8String.SLASH_STRING, name);
+                    location = super.findLocation(fullName);
+                }
+            } else {
+                // No package, try all modules.
+                for (String mod : moduleData.allModuleNames()) {
+                    location = super.findLocation("/" + mod + "/" + name);
+                    if (location != null) {
+                        break;
+                    }
+                }
+            }
+        }
+
+        return location;
+    }
+
     /**
      * Return the module name that contains the given package name.
      */
-    public String getModule(String pkg) {
-        return packageMap.get(pkg);
+    public String getModule(String packageName) {
+        return moduleData.packageToModule(packageName);
     }
 
     // jimage file does not store directory structure. We build nodes
@@ -101,14 +131,13 @@
     // Node can be a directory or a resource
     public static abstract class Node {
         private static final int ROOT_DIR = 0b0000_0000_0000_0001;
-        private static final int MODULE_DIR = 0b0000_0000_0000_0010;
-        private static final int METAINF_DIR = 0b0000_0000_0000_0100;
-        private static final int TOPLEVEL_PKG_DIR = 0b0000_0000_0000_1000;
-        private static final int HIDDEN = 0b0000_0000_0001_0000;
+        private static final int PACKAGES_DIR = 0b0000_0000_0000_0010;
+        private static final int MODULES_DIR = 0b0000_0000_0000_0100;
 
         private int flags;
         private final UTF8String name;
         private final BasicFileAttributes fileAttrs;
+        private boolean completed;
 
         Node(UTF8String name, BasicFileAttributes fileAttrs) {
             assert name != null;
@@ -117,6 +146,19 @@
             this.fileAttrs = fileAttrs;
         }
 
+        /**
+         * A node is completed when all its direct children have been built.
+         *
+         * @return
+         */
+        public boolean isCompleted() {
+            return completed;
+        }
+
+        public void setCompleted(boolean completed) {
+            this.completed = completed;
+        }
+
         public final void setIsRootDir() {
             flags |= ROOT_DIR;
         }
@@ -125,40 +167,20 @@
             return (flags & ROOT_DIR) != 0;
         }
 
-        public final void setIsModuleDir() {
-            flags |= MODULE_DIR;
-        }
-
-        public final boolean isModuleDir() {
-            return (flags & MODULE_DIR) != 0;
-        }
-
-        public final void setIsMetaInfDir() {
-            flags |= METAINF_DIR;
-        }
-
-        public final boolean isMetaInfDir() {
-            return (flags & METAINF_DIR) != 0;
+        public final void setIsPackagesDir() {
+            flags |= PACKAGES_DIR;
         }
 
-        public final void setIsTopLevelPackageDir() {
-            flags |= TOPLEVEL_PKG_DIR;
-        }
-
-        public final boolean isTopLevelPackageDir() {
-            return (flags & TOPLEVEL_PKG_DIR) != 0;
+        public final boolean isPackagesDir() {
+            return (flags & PACKAGES_DIR) != 0;
         }
 
-        public final void setIsHidden() {
-            flags |= HIDDEN;
+        public final void setIsModulesDir() {
+            flags |= MODULES_DIR;
         }
 
-        public final boolean isHidden() {
-            return (flags & HIDDEN) != 0;
-        }
-
-        public final boolean isVisible() {
-            return !isHidden();
+        public final boolean isModulesDir() {
+            return (flags & MODULES_DIR) != 0;
         }
 
         public final UTF8String getName() {
@@ -169,6 +191,20 @@
             return fileAttrs;
         }
 
+        // resolve this Node (if this is a soft link, get underlying Node)
+        public final Node resolveLink() {
+            return resolveLink(false);
+        }
+
+        public Node resolveLink(boolean recursive) {
+            return this;
+        }
+
+        // is this a soft link Node?
+        public boolean isLink() {
+            return false;
+        }
+
         public boolean isDirectory() {
             return false;
         }
@@ -242,16 +278,20 @@
     }
 
     // directory node - directory has full path name without '/' at end.
-    public static final class Directory extends Node {
+    static final class Directory extends Node {
         private final List<Node> children;
 
-        @SuppressWarnings("LeakingThisInConstructor")
-        Directory(Directory parent, UTF8String name, BasicFileAttributes fileAttrs) {
+        private Directory(Directory parent, UTF8String name, BasicFileAttributes fileAttrs) {
             super(name, fileAttrs);
             children = new ArrayList<>();
+        }
+
+        static Directory create(Directory parent, UTF8String name, BasicFileAttributes fileAttrs) {
+            Directory dir = new Directory(parent, name, fileAttrs);
             if (parent != null) {
-                parent.addChild(this);
+                parent.addChild(dir);
             }
+            return dir;
         }
 
         @Override
@@ -259,6 +299,7 @@
             return true;
         }
 
+        @Override
         public List<Node> getChildren() {
             return Collections.unmodifiableList(children);
         }
@@ -281,19 +322,33 @@
 
     // "resource" is .class or any other resource (compressed/uncompressed) in a jimage.
     // full path of the resource is the "name" of the resource.
-    public static class Resource extends Node {
+    static class Resource extends Node {
         private final ImageLocation loc;
 
-        @SuppressWarnings("LeakingThisInConstructor")
-        Resource(Directory parent, ImageLocation loc, BasicFileAttributes fileAttrs) {
-            this(parent, ROOT.concat(loc.getFullname()), loc, fileAttrs);
+        private Resource(Directory parent, ImageLocation loc, BasicFileAttributes fileAttrs) {
+            this(parent, loc.getFullName(true), loc, fileAttrs);
         }
 
-        @SuppressWarnings("LeakingThisInConstructor")
-        Resource(Directory parent, UTF8String name, ImageLocation loc, BasicFileAttributes fileAttrs) {
+        private Resource(Directory parent, UTF8String name, ImageLocation loc, BasicFileAttributes fileAttrs) {
             super(name, fileAttrs);
             this.loc = loc;
-            parent.addChild(this);
+         }
+
+        static Resource create(Directory parent, ImageLocation loc, BasicFileAttributes fileAttrs) {
+            Resource resource = new Resource(parent, loc, fileAttrs);
+            parent.addChild(resource);
+            return resource;
+        }
+
+        static Resource create(Directory parent, UTF8String name, ImageLocation loc, BasicFileAttributes fileAttrs) {
+            Resource resource = new Resource(parent, name, loc, fileAttrs);
+            parent.addChild(resource);
+            return resource;
+        }
+
+        @Override
+        public boolean isCompleted() {
+            return true;
         }
 
         @Override
@@ -327,6 +382,37 @@
         }
     }
 
+    // represents a soft link to another Node
+    static class LinkNode extends Node {
+        private final Node link;
+
+        private LinkNode(Directory parent, UTF8String name, Node link) {
+            super(name, link.getFileAttributes());
+            this.link = link;
+        }
+
+        static LinkNode create(Directory parent, UTF8String name, Node link) {
+            LinkNode linkNode = new LinkNode(parent, name, link);
+            parent.addChild(linkNode);
+            return linkNode;
+        }
+
+        @Override
+        public boolean isCompleted() {
+            return true;
+        }
+
+        @Override
+        public Node resolveLink(boolean recursive) {
+            return recursive && (link instanceof LinkNode)? ((LinkNode)link).resolveLink(true) : link;
+        }
+
+        @Override
+        public boolean isLink() {
+            return true;
+        }
+    }
+
     // directory management interface
     public Directory getRootDirectory() {
         return buildRootDirectory();
@@ -340,9 +426,154 @@
         return findNode(new UTF8String(name));
     }
 
+    /**
+     * To visit sub tree resources.
+     */
+    interface LocationVisitor {
+
+        void visit(ImageLocation loc);
+    }
+
+    /**
+     * Lazily build a node from a name.
+     */
+    private final class NodeBuilder {
+
+        private static final int SIZE_OF_OFFSET = 4;
+
+        private final UTF8String name;
+
+        private NodeBuilder(UTF8String name) {
+            this.name = name;
+        }
+
+        private Node buildNode() {
+            Node n = null;
+            boolean isPackages = false;
+            boolean isModules = false;
+            String strName = name.toString();
+            if (strName.startsWith("" + PACKAGES_STRING)) {
+                isPackages = true;
+            } else {
+                if (strName.startsWith("" + MODULES_STRING)) {
+                    isModules = true;
+                }
+            }
+            if (!isModules && !isPackages) {
+                return null;
+            }
+
+            ImageLocation loc = findLocation(name);
+
+            if (loc != null) { // A sub tree node
+                if (isPackages) {
+                    n = handlePackages(strName, loc);
+                } else { // modules sub tree
+                    n = handleModulesSubTree(strName, loc);
+                }
+            } else { // Asking for a resource? /modules/java.base/java/lang/Object.class
+                if (isModules) {
+                    n = handleResource(strName, loc);
+                }
+            }
+            return n;
+        }
+
+        private void visitLocation(ImageLocation loc, LocationVisitor visitor) {
+            byte[] offsets = getResource(loc);
+            ByteBuffer buffer = ByteBuffer.wrap(offsets);
+            buffer.order(getByteOrder());
+            IntBuffer intBuffer = buffer.asIntBuffer();
+            for (int i = 0; i < offsets.length / SIZE_OF_OFFSET; i++) {
+                int offset = intBuffer.get(i);
+                ImageLocation pkgLoc = getLocation(offset);
+                visitor.visit(pkgLoc);
+            }
+        }
+
+        private Node handlePackages(String name, ImageLocation loc) {
+            long size = loc.getUncompressedSize();
+            Node n = null;
+            // Only possiblities are /packages, /packages/package/module
+            if (name.equals("" + PACKAGES_STRING)) {
+                visitLocation(loc, (childloc) -> {
+                    findNode(childloc.getFullName());
+                });
+                packagesDir.setCompleted(true);
+                n = packagesDir;
+            } else {
+                if (size != 0) { // children are links to module
+                    String pkgName = getBaseExt(loc);
+                    Directory pkgDir = newDirectory(packagesDir,
+                            packagesDir.getName().concat(SLASH_STRING, new UTF8String(pkgName)));
+                    visitLocation(loc, (childloc) -> {
+                        findNode(childloc.getFullName());
+                    });
+                    pkgDir.setCompleted(true);
+                    n = pkgDir;
+                } else { // Link to module
+                    String pkgName = loc.getParentString();
+                    String modName = getBaseExt(loc);
+                    Node targetNode = findNode(MODULES_STRING + "/" + modName);
+                    if (targetNode != null) {
+                        UTF8String pkgDirName = packagesDir.getName().concat(SLASH_STRING, new UTF8String(pkgName));
+                        Directory pkgDir = (Directory) nodes.get(pkgDirName);
+                        Node linkNode = newLinkNode(pkgDir,
+                                pkgDir.getName().concat(SLASH_STRING, new UTF8String(modName)), targetNode);
+                        n = linkNode;
+                    }
+                }
+            }
+            return n;
+        }
+
+        private Node handleModulesSubTree(String name, ImageLocation loc) {
+            Node n;
+            Directory dir = makeDirectories(loc.getFullName());
+            visitLocation(loc, (childloc) -> {
+                String path = childloc.getFullNameString();
+                if (path.startsWith(MODULES_STRING.toString())) { // a package
+                    makeDirectories(childloc.getFullName());
+                } else { // a resource
+                    makeDirectories(childloc.buildName(true, true, false));
+                    newResource(dir, childloc);
+                }
+            });
+            dir.setCompleted(true);
+            n = dir;
+            return n;
+        }
+
+        private Node handleResource(String name, ImageLocation loc) {
+            Node n = null;
+            String locationPath = name.substring((MODULES_STRING).length());
+            ImageLocation resourceLoc = findLocation(locationPath);
+            if (resourceLoc != null) {
+                Directory dir = makeDirectories(resourceLoc.buildName(true, true, false));
+                Resource res = newResource(dir, resourceLoc);
+                n = res;
+            }
+            return n;
+        }
+
+        private String getBaseExt(ImageLocation loc) {
+            String base = loc.getBaseString();
+            String ext = loc.getExtensionString();
+            if (ext != null && !ext.isEmpty()) {
+                base = base + "." + ext;
+            }
+            return base;
+        }
+    }
+
     public synchronized Node findNode(UTF8String name) {
         buildRootDirectory();
-        return nodes.get(name);
+        Node n = nodes.get(name);
+        if (n == null || !n.isCompleted()) {
+            NodeBuilder builder = new NodeBuilder(name);
+            n = builder.buildNode();
+        }
+        return n;
     }
 
     private synchronized void clearNodes() {
@@ -375,65 +606,61 @@
         // FIXME no time information per resource in jimage file (yet?)
         // we use file attributes of jimage itself.
         // root directory
-        rootDir = new Directory(null, ROOT, imageFileAttributes());
+        rootDir = newDirectory(null, ROOT_STRING);
         rootDir.setIsRootDir();
-        nodes.put(rootDir.getName(), rootDir);
 
-        ImageLocation[] locs = getAllLocations(true);
-        for (ImageLocation loc : locs) {
-            UTF8String parent = loc.getParent();
-            // directory where this location goes as child
-            Directory dir;
-            if (parent == null || parent.isEmpty()) {
-                // top level entry under root
-                dir = rootDir;
-            } else {
-                int idx = parent.lastIndexOf('/');
-                assert idx != -1 : "invalid parent string";
-                UTF8String name = ROOT.concat(parent.substring(0, idx));
-                dir = (Directory) nodes.get(name);
-                if (dir == null) {
-                    // make all parent directories (as needed)
-                    dir = makeDirectories(parent);
-                }
-            }
-            Resource entry = new Resource(dir, loc, imageFileAttributes());
-            nodes.put(entry.getName(), entry);
-        }
+        // /packages dir
+        packagesDir = newDirectory(rootDir, PACKAGES_STRING);
+        packagesDir.setIsPackagesDir();
 
-        Node metaInf = nodes.get(META_INF);
-        if (metaInf instanceof Directory) {
-            metaInf.setIsMetaInfDir();
-            ((Directory)metaInf).walk(Node::setIsHidden);
-        }
+        // /modules dir
+        modulesDir = newDirectory(rootDir, MODULES_STRING);
+        modulesDir.setIsModulesDir();
 
-        fillPackageModuleInfo();
-
+        rootDir.setCompleted(true);
         return rootDir;
     }
 
     private Directory newDirectory(Directory parent, UTF8String name) {
-        Directory dir = new Directory(parent, name, imageFileAttributes());
+        Directory dir = Directory.create(parent, name, imageFileAttributes());
         nodes.put(dir.getName(), dir);
         return dir;
     }
 
-    private Directory makeDirectories(UTF8String parent) {
-        assert !parent.isEmpty() : "non empty parent expected";
+    private Resource newResource(Directory parent, ImageLocation loc) {
+        Resource res = Resource.create(parent, loc, imageFileAttributes());
+        nodes.put(res.getName(), res);
+        return res;
+    }
+
+    private LinkNode newLinkNode(Directory dir, UTF8String name, Node link) {
+        LinkNode linkNode = LinkNode.create(dir, name, link);
+        nodes.put(linkNode.getName(), linkNode);
+        return linkNode;
+    }
+
+    private List<UTF8String> dirs(UTF8String parent) {
+        List<UTF8String> splits = new ArrayList<>();
 
-        int idx = parent.indexOf('/');
-        assert idx != -1 : "invalid parent string";
-        UTF8String name = ROOT.concat(parent.substring(0, idx));
-        Directory top = (Directory) nodes.get(name);
-        if (top == null) {
-            top = newDirectory(rootDir, name);
+        for (int i = 1; i < parent.length(); i++) {
+            if (parent.byteAt(i) == '/') {
+                splits.add(parent.substring(0, i));
+            }
         }
-        Directory last = top;
-        while ((idx = parent.indexOf('/', idx + 1)) != -1) {
-            name = ROOT.concat(parent.substring(0, idx));
-            Directory nextDir = (Directory) nodes.get(name);
+
+        splits.add(parent);
+
+        return splits;
+    }
+
+    private Directory makeDirectories(UTF8String parent) {
+        Directory last = rootDir;
+        List<UTF8String> dirs = dirs(parent);
+
+        for (UTF8String dir : dirs) {
+            Directory nextDir = (Directory) nodes.get(dir);
             if (nextDir == null) {
-                nextDir = newDirectory(last, name);
+                nextDir = newDirectory(last, dir);
             }
             last = nextDir;
         }
@@ -441,54 +668,6 @@
         return last;
     }
 
-    private void fillPackageModuleInfo() {
-        assert rootDir != null;
-
-        packageMap.entrySet().stream().sorted((x, y)->x.getKey().compareTo(y.getKey())).forEach((entry) -> {
-              UTF8String moduleName = new UTF8String("/" + entry.getValue());
-              UTF8String fullName = moduleName.concat(new UTF8String(entry.getKey() + "/"));
-              if (! nodes.containsKey(fullName)) {
-                  Directory module = (Directory) nodes.get(moduleName);
-                  assert module != null : "module directory missing " + moduleName;
-                  module.setIsModuleDir();
-
-                  // hide "packages.offsets" in module directories
-                  Node packagesOffsets = nodes.get(moduleName.concat(ROOT, PACKAGES_OFFSETS));
-                  if (packagesOffsets != null) {
-                      packagesOffsets.setIsHidden();
-                  }
-
-                  // package name without front '/'
-                  UTF8String pkgName = new UTF8String(entry.getKey() + "/");
-                  int idx = -1;
-                  Directory moduleSubDir = module;
-                  while ((idx = pkgName.indexOf('/', idx + 1)) != -1) {
-                      UTF8String subPkg = pkgName.substring(0, idx);
-                      UTF8String moduleSubDirName = moduleName.concat(ROOT, subPkg);
-                      Directory tmp = (Directory) nodes.get(moduleSubDirName);
-                      if (tmp == null) {
-                          moduleSubDir = newDirectory(moduleSubDir, moduleSubDirName);
-                      } else {
-                          moduleSubDir = tmp;
-                      }
-                  }
-                  // copy pkgDir "resources"
-                  Directory pkgDir = (Directory) nodes.get(ROOT.concat(pkgName.substring(0, pkgName.length() - 1)));
-                  pkgDir.setIsTopLevelPackageDir();
-                  pkgDir.walk(n -> n.setIsHidden());
-                  for (Node child : pkgDir.getChildren()) {
-                      if (child.isResource()) {
-                          ImageLocation loc = child.getLocation();
-                          BasicFileAttributes imageFileAttrs = child.getFileAttributes();
-                          UTF8String rsName = moduleName.concat(child.getName());
-                          Resource rs = new Resource(moduleSubDir, rsName, loc, imageFileAttrs);
-                          nodes.put(rs.getName(), rs);
-                      }
-                  }
-              }
-        });
-    }
-
     public byte[] getResource(Node node) throws IOException {
         if (node.isResource()) {
             return super.getResource(node.getLocation());
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageReaderFactory.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,79 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.internal.jimage;
+
+import java.io.IOException;
+import java.io.UncheckedIOException;
+import java.nio.file.Path;
+import java.nio.file.Paths;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.Map;
+
+/**
+ * Factory to get ImageReader
+ */
+public class ImageReaderFactory {
+    private ImageReaderFactory() {}
+
+    private static final String JAVA_HOME = System.getProperty("java.home");
+    private static final Path BOOT_MODULES_JIMAGE =
+        Paths.get(JAVA_HOME, "lib", "modules", "bootmodules.jimage");
+
+    private static final Map<Path, ImageReader> readers = new ConcurrentHashMap<>();
+
+    /**
+     * Returns an {@code ImageReader} to read from the given image file
+     */
+    public static ImageReader get(Path jimage) throws IOException {
+        ImageReader reader = readers.get(jimage);
+        if (reader != null) {
+            return reader;
+        }
+        reader = ImageReader.open(jimage.toString());
+        // potential race with other threads opening the same URL
+        ImageReader r = readers.putIfAbsent(jimage, reader);
+        if (r == null) {
+            return reader;
+        } else {
+            reader.close();
+            return r;
+        }
+    }
+
+    /**
+     * Returns the {@code ImageReader} to read the image file in this
+     * run-time image.
+     *
+     * @throws UncheckedIOException if an I/O error occurs
+     */
+    public static ImageReader getImageReader() {
+        try {
+            return get(BOOT_MODULES_JIMAGE);
+        } catch (IOException ioe) {
+            throw new UncheckedIOException(ioe);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageResourcesTree.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,341 @@
+/*
+ * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.internal.jimage;
+
+import java.io.DataOutputStream;
+import java.io.IOException;
+import java.nio.ByteBuffer;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+import java.util.TreeMap;
+import java.util.TreeSet;
+
+/**
+ * A class to build a sorted tree of Resource paths as a tree of ImageLocation.
+ *
+ */
+// XXX Public only due to the JImageTask / JImageTask code duplication
+public final class ImageResourcesTree {
+
+    private static final String MODULES = "modules";
+    private static final String PACKAGES = "packages";
+    public static final String MODULES_STRING = UTF8String.MODULES_STRING.toString();
+    public static final String PACKAGES_STRING = UTF8String.PACKAGES_STRING.toString();
+
+    public static boolean isTreeInfoResource(String path) {
+        return path.startsWith(PACKAGES_STRING) || path.startsWith(MODULES_STRING);
+    }
+
+    /**
+     * Path item tree node.
+     */
+    private static final class Node {
+
+        private final String name;
+        private final Map<String, Node> children = new TreeMap<>();
+        private final Node parent;
+        private ImageLocationWriter loc;
+        private boolean isResource;
+
+        private Node(String name, Node parent) {
+            this.name = name;
+            this.parent = parent;
+
+            if (parent != null) {
+                parent.children.put(name, this);
+            }
+        }
+
+        public String getPath() {
+            if (parent == null) {
+                return "/";
+            }
+            return buildPath(this);
+        }
+
+        public String getName() {
+            return name;
+        }
+
+        public Node getChildren(String name) {
+            Node item = children.get(name);
+            return item;
+        }
+
+        private static String buildPath(Node item) {
+            if (item == null) {
+                return null;
+            }
+            String path = buildPath(item.parent);
+            if (path == null) {
+                return item.getName();
+            } else {
+                return path + "/" + item.getName();
+            }
+        }
+    }
+
+    /**
+     * Tree of nodes.
+     */
+    private static final class Tree {
+
+        private final Map<String, Node> directAccess = new HashMap<>();
+        private final List<String> paths;
+        private final Node root;
+        private Node modules;
+        private Node packages;
+
+        private Tree(List<String> paths) {
+            this.paths = paths;
+            root = new Node("", null);
+            buildTree();
+        }
+
+        private void buildTree() {
+            modules = new Node(MODULES, root);
+            directAccess.put(modules.getPath(), modules);
+
+            Map<String, Set<String>> moduleToPackage = new TreeMap<>();
+            Map<String, Set<String>> packageToModule = new TreeMap<>();
+
+            for (String p : paths) {
+                if (!p.startsWith("/")) {
+                    continue;
+                }
+                String[] split = p.split("/");
+                Node current = modules;
+                String module = null;
+                for (int i = 0; i < split.length; i++) {
+                    String s = split[i];
+                    if (!s.isEmpty()) {
+                        if (module == null) {
+                            module = s;
+                        }
+                        Node n = current.children.get(s);
+                        if (n == null) {
+                            n = new Node(s, current);
+                            if (i == split.length - 1) { // Leaf
+                                n.isResource = true;
+                                String pkg = toPackageName(n.parent);
+                                if (pkg != null && !pkg.startsWith("META-INF")) {
+                                    Set<String> pkgs = moduleToPackage.get(module);
+                                    if (pkgs == null) {
+                                        pkgs = new TreeSet<>();
+                                        moduleToPackage.put(module, pkgs);
+                                    }
+                                    pkgs.add(pkg);
+                                }
+                            } else { // put only sub trees, no leaf
+                                directAccess.put(n.getPath(), n);
+                                String pkg = toPackageName(n);
+                                if (pkg != null && !pkg.startsWith("META-INF")) {
+                                    Set<String> mods = packageToModule.get(pkg);
+                                    if (mods == null) {
+                                        mods = new TreeSet<>();
+                                        packageToModule.put(pkg, mods);
+                                    }
+                                    mods.add(module);
+
+                                }
+                            }
+                        }
+                        current = n;
+                    }
+                }
+            }
+            packages = new Node(PACKAGES, root);
+            directAccess.put(packages.getPath(), packages);
+            for (Map.Entry<String, Set<String>> entry : moduleToPackage.entrySet()) {
+                for (String pkg : entry.getValue()) {
+                    Node pkgNode = new Node(pkg, packages);
+                    directAccess.put(pkgNode.getPath(), pkgNode);
+
+                    Node modNode = new Node(entry.getKey(), pkgNode);
+                    directAccess.put(modNode.getPath(), modNode);
+                }
+            }
+            for (Map.Entry<String, Set<String>> entry : packageToModule.entrySet()) {
+                Node pkgNode = new Node(entry.getKey(), packages);
+                directAccess.put(pkgNode.getPath(), pkgNode);
+                for (String module : entry.getValue()) {
+                    Node modNode = new Node(module, pkgNode);
+                    directAccess.put(modNode.getPath(), modNode);
+                }
+            }
+        }
+
+        public String toResourceName(Node node) {
+            if (!node.children.isEmpty()) {
+                throw new RuntimeException("Node is not a resource");
+            }
+            return removeRadical(node);
+        }
+
+        public String getModule(Node node) {
+            if (node.parent == null || node.getName().equals(MODULES) ||
+                node.getName().startsWith(PACKAGES)) {
+                return null;
+            }
+            String path = removeRadical(node);
+            // "/xxx/...";
+            path = path.substring(1);
+            int i = path.indexOf("/");
+            if (i == -1) {
+                return path;
+            } else {
+                return path.substring(0, i);
+            }
+        }
+
+        public String toPackageName(Node node) {
+            if (node.parent == null) {
+                return null;
+            }
+            String path = removeRadical(node.getPath(), "/" + MODULES + "/");
+            String module = getModule(node);
+            if (path.equals(module)) {
+                return null;
+            }
+            String pkg = removeRadical(path, module + "/");
+            return pkg.replaceAll("/", ".");
+        }
+
+        public String removeRadical(Node node) {
+            String s = node.getPath();
+            return removeRadical(node.getPath(), "/" + MODULES);
+        }
+
+        private String removeRadical(String path, String str) {
+            return path.substring(str.length());
+        }
+
+        public Node getRoot() {
+            return root;
+        }
+
+        public Map<String, Node> getMap() {
+            return directAccess;
+        }
+    }
+
+    private static final class LocationsAdder {
+
+        private long offset;
+        private final List<byte[]> content = new ArrayList<>();
+        private final BasicImageWriter writer;
+        private final Tree tree;
+
+        LocationsAdder(Tree tree, long offset, BasicImageWriter writer) {
+            this.tree = tree;
+            this.offset = offset;
+            this.writer = writer;
+            addLocations(tree.getRoot());
+        }
+
+        private int addLocations(Node current) {
+            int[] ret = new int[current.children.size()];
+            int i = 0;
+            for (java.util.Map.Entry<String, Node> entry : current.children.entrySet()) {
+                ret[i] = addLocations(entry.getValue());
+                i += 1;
+            }
+            if (current != tree.getRoot() && !current.isResource) {
+                int size = ret.length * 4;
+                writer.addLocation(current.getPath(), offset, 0, size);
+                offset += size;
+            }
+            return 0;
+        }
+
+        private List<byte[]> computeContent() {
+            // Map used to associate Tree item with locations offset.
+            Map<String, ImageLocationWriter> outLocations = new HashMap<>();
+            for (ImageLocationWriter wr : writer.getLocations()) {
+                outLocations.put(wr.getFullNameString(), wr);
+            }
+            // Attach location to node
+            for (Map.Entry<String, ImageLocationWriter> entry : outLocations.entrySet()) {
+                Node item = tree.getMap().get(entry.getKey());
+                if (item != null) {
+                    item.loc = entry.getValue();
+                }
+            }
+            computeContent(tree.getRoot(), outLocations);
+            return content;
+        }
+
+        private int computeContent(Node current, Map<String, ImageLocationWriter> outLocations) {
+            int[] ret = new int[current.children.size()];
+            int i = 0;
+            for (java.util.Map.Entry<String, Node> entry : current.children.entrySet()) {
+                ret[i] = computeContent(entry.getValue(), outLocations);
+                i += 1;
+            }
+            if (ret.length > 0) {
+                int size = ret.length * 4;
+                ByteBuffer buff = ByteBuffer.allocate(size);
+                buff.order(writer.getByteOrder());
+                for (int val : ret) {
+                    buff.putInt(val);
+                }
+                byte[] arr = buff.array();
+                content.add(arr);
+            } else {
+                if (current.isResource) {
+                    // A resource location, remove "/modules"
+                    String s = tree.toResourceName(current);
+                    current.loc = outLocations.get(s);
+                } else {
+                    // "/packages" leaf node, empty "/packages" or empty "/modules" paths
+                    current.loc = outLocations.get(current.getPath());
+                }
+            }
+            return current == tree.getRoot() ? 0 : current.loc.getLocationOffset();
+        }
+    }
+
+    private final List<String> paths;
+    private final LocationsAdder adder;
+
+    public ImageResourcesTree(long offset, BasicImageWriter writer, List<String> paths) {
+        this.paths = new ArrayList<>();
+        this.paths.addAll(paths);
+        Collections.sort(this.paths);
+        Tree tree = new Tree(this.paths);
+        adder = new LocationsAdder(tree, offset, writer);
+    }
+
+    public void addContent(DataOutputStream out) throws IOException {
+        List<byte[]> content = adder.computeContent();
+        for (byte[] c : content) {
+            out.write(c, 0, c.length);
+        }
+    }
+}
--- a/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageStream.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageStream.java	Wed Jul 05 20:42:36 2017 +0200
@@ -72,7 +72,7 @@
         return this;
     }
 
-    private void ensure(int needs) {
+    void ensure(int needs) {
         assert 0 <= needs : "Negative needs";
 
         if (needs > buffer.remaining()) {
--- a/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageStrings.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageStrings.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,83 +25,8 @@
 
 package jdk.internal.jimage;
 
-import java.nio.ByteBuffer;
-import java.util.HashMap;
-
-class ImageStrings {
-    private static final int NOT_FOUND = -1;
-    static final int EMPTY_OFFSET = 0;
-
-    private final HashMap<UTF8String, Integer> stringToOffsetMap;
-    private final ImageStream stream;
-
-    ImageStrings() {
-        this.stringToOffsetMap = new HashMap<>();
-        this.stream = new ImageStream();
-
-        // Reserve 0 offset for empty string.
-        int offset = addString(UTF8String.EMPTY_STRING);
-        assert offset == 0 : "Empty string not zero offset";
-        // Reserve 1 offset for frequently used ".class".
-        addString(UTF8String.CLASS_STRING);
-    }
-
-    ImageStrings(ImageStream stream) {
-        this.stringToOffsetMap = new HashMap<>();
-        this.stream = stream;
-    }
-
-    private int addString(final UTF8String string) {
-        int offset = stream.getPosition();
-        string.writeTo(stream);
-        stream.put('\0');
-        stringToOffsetMap.put(string, offset);
-
-        return offset;
-    }
-
-    int add(final UTF8String string) {
-        int offset = find(string);
+interface ImageStrings {
+    public UTF8String get(int offset);
 
-        return offset == NOT_FOUND ? addString(string) : offset;
-    }
-
-    int find(final UTF8String string) {
-        Integer offset = stringToOffsetMap.get(string);
-
-        return offset != null ? offset : NOT_FOUND;
-    }
-
-    UTF8String get(int offset) {
-        ByteBuffer buffer = stream.getBuffer();
-        assert 0 <= offset && offset < buffer.capacity() : "String buffer offset out of range";
-        int zero = NOT_FOUND;
-        for (int i = offset; i < buffer.capacity(); i++) {
-            if (buffer.get(i) == '\0') {
-                zero = i;
-                break;
-            }
-        }
-        assert zero != UTF8String.NOT_FOUND;
-        int length = zero - offset;
-        byte[] bytes = new byte[length];
-        int mark = buffer.position();
-        buffer.position(offset);
-        buffer.get(bytes);
-        buffer.position(mark);
-
-        return new UTF8String(bytes, 0, length);
-    }
-
-    ImageStream getStream() {
-        return stream;
-    }
-
-    int getSize() {
-        return stream.getSize();
-    }
-
-    int getCount() {
-        return stringToOffsetMap.size();
-    }
+    public int add(final UTF8String string);
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageStringsReader.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,44 @@
+/*
+ * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.internal.jimage;
+
+class ImageStringsReader implements ImageStrings {
+    private final BasicImageReader reader;
+
+    ImageStringsReader(BasicImageReader reader) {
+        this.reader = reader;
+    }
+
+    @Override
+    public UTF8String get(int offset) {
+        return reader.getUTF8String(offset);
+    }
+
+    @Override
+    public int add(final UTF8String string) {
+        throw new InternalError("Can not add strings at runtime");
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageStringsWriter.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,105 @@
+/*
+ * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.internal.jimage;
+
+import java.nio.ByteBuffer;
+import java.util.HashMap;
+
+class ImageStringsWriter implements ImageStrings {
+    private static final int NOT_FOUND = -1;
+    static final int EMPTY_OFFSET = 0;
+    static final UTF8String CLASS_STRING = new UTF8String("class");
+
+    private final HashMap<UTF8String, Integer> stringToOffsetMap;
+    private final ImageStream stream;
+
+    ImageStringsWriter() {
+        this.stringToOffsetMap = new HashMap<>();
+        this.stream = new ImageStream();
+
+        // Reserve 0 offset for empty string.
+        int offset = addString(UTF8String.EMPTY_STRING);
+        assert offset == 0 : "Empty string not zero offset";
+        // Reserve 1 offset for frequently used ".class".
+        addString(CLASS_STRING);
+    }
+
+    private int addString(final UTF8String string) {
+        int offset = stream.getPosition();
+        string.writeTo(stream);
+        stream.put('\0');
+        stringToOffsetMap.put(string, offset);
+
+        return offset;
+    }
+
+    @Override
+    public int add(final UTF8String string) {
+        int offset = find(string);
+
+        return offset == NOT_FOUND ? addString(string) : offset;
+    }
+
+    int find(final UTF8String string) {
+        Integer offset = stringToOffsetMap.get(string);
+
+        return offset != null ? offset : NOT_FOUND;
+    }
+
+    @Override
+    public UTF8String get(int offset) {
+        ByteBuffer buffer = stream.getBuffer();
+        assert 0 <= offset && offset < buffer.capacity() : "String buffer offset out of range";
+        int zero = NOT_FOUND;
+        for (int i = offset; i < buffer.capacity(); i++) {
+            if (buffer.get(i) == '\0') {
+                zero = i;
+                break;
+            }
+        }
+        assert zero != UTF8String.NOT_FOUND;
+        int length = zero - offset;
+        byte[] bytes = new byte[length];
+        int mark = buffer.position();
+        buffer.position(offset);
+        buffer.get(bytes);
+        buffer.position(mark);
+
+        return new UTF8String(bytes, 0, length);
+    }
+
+    ImageStream getStream() {
+        return stream;
+    }
+
+    int getSize() {
+        return stream.getSize();
+    }
+
+    int getCount() {
+        return stringToOffsetMap.size();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ImageSubstrate.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,45 @@
+/*
+ * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.internal.jimage;
+
+import java.io.Closeable;
+import java.nio.ByteBuffer;
+
+interface ImageSubstrate extends Closeable {
+    @Override
+    void close();
+    boolean supportsDataBuffer();
+    ByteBuffer getIndexBuffer(long offset, long size);
+    ByteBuffer getDataBuffer(long offset, long size);
+    boolean read(long offset,
+                          ByteBuffer compressedBuffer, long compressedSize,
+                          ByteBuffer uncompressedBuffer, long uncompressedSize);
+    boolean read(long offset,
+                          ByteBuffer uncompressedBuffer, long uncompressedSize);
+    byte[] getStringBytes(int offset);
+    long[] getAttributes(int offset);
+    ImageLocation findLocation(UTF8String name, ImageStringsReader strings);
+    int[] attributeOffsets();
+}
--- a/jdk/src/java.base/share/classes/jdk/internal/jimage/PReader.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,139 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.  Oracle designates this
- * particular file as subject to the "Classpath" exception as provided
- * by Oracle in the LICENSE file that accompanied this code.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package jdk.internal.jimage;
-
-import java.io.Closeable;
-import java.io.IOException;
-import java.io.RandomAccessFile;
-import java.nio.channels.FileChannel;
-import java.lang.reflect.Constructor;
-import java.lang.reflect.InvocationTargetException;
-
-/**
- * Supports reading a file from given positions (offsets) in the file.
- */
-
-public abstract class PReader implements Closeable {
-    private final FileChannel fc;
-
-    protected PReader(FileChannel fc) {
-        this.fc = fc;
-    }
-
-    /**
-     * Returns the {@code FileChannel}.
-     */
-    final FileChannel channel() {
-        return fc;
-    }
-
-    /**
-     * Closes this {@code PReader} and the underlying file.
-     */
-    @Override
-    public final void close() throws IOException {
-        fc.close();
-    }
-
-    /**
-     * Returns {@code true} if this {@code PReader} and the underlying file is
-     * open.
-     */
-    public final boolean isOpen() {
-        return fc.isOpen();
-    }
-
-    /**
-     * Returns {@code len} bytes from a given position in the file. The bytes
-     * are returned as a byte array.
-     *
-     * @throws IOException if an I/O error occurs
-     */
-    public abstract byte[] read(int len, long position) throws IOException;
-
-    /**
-     * Opens the given file, returning a {@code PReader} to read from the file.
-     *
-     * @implNote Returns a {@code PReader} that supports concurrent pread operations
-     * if possible, otherwise a simple {@code PReader} that doesn't support
-     * concurrent operations.
-     */
-    static PReader open(String file) throws IOException {
-        Class<?> clazz;
-        try {
-            clazz = Class.forName("jdk.internal.jimage.concurrent.ConcurrentPReader");
-        } catch (ClassNotFoundException e) {
-            return new SimplePReader(file);
-        }
-        try {
-            Constructor<?> ctor = clazz.getConstructor(String.class);
-            return (PReader) ctor.newInstance(file);
-        } catch (InvocationTargetException e) {
-            Throwable cause = e.getCause();
-            if (cause instanceof IOException)
-                throw (IOException) cause;
-            if (cause instanceof Error)
-                throw (Error) cause;
-            if (cause instanceof RuntimeException)
-                throw (RuntimeException) cause;
-            throw new Error(e);
-        } catch (NoSuchMethodException | IllegalAccessException |
-                InstantiationException e) {
-            throw new InternalError(e);
-        }
-    }
-}
-
-/**
- * Simple PReader implementation based on {@code RandomAccessFile}.
- *
- * @implNote This class cannot use FileChannel read methods to do the
- * positional reads because FileChannel is interruptible.
- */
-class SimplePReader extends PReader {
-    private final RandomAccessFile raf;
-
-    private SimplePReader(RandomAccessFile raf) throws IOException {
-        super(raf.getChannel());
-        this.raf = raf;
-    }
-
-    SimplePReader(String file) throws IOException {
-        this(new RandomAccessFile(file, "r"));
-    }
-
-    @Override
-    public byte[] read(int len, long position) throws IOException {
-        synchronized (this) {
-            byte[] bytes = new byte[len];
-            raf.seek(position);
-            int n = raf.read(bytes);
-            if (n != len)
-                throw new InternalError("short read, not handled yet");
-            return bytes;
-        }
-    }
-}
--- a/jdk/src/java.base/share/classes/jdk/internal/jimage/PackageModuleMap.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,62 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.  Oracle designates this
- * particular file as subject to the "Classpath" exception as provided
- * by Oracle in the LICENSE file that accompanied this code.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package jdk.internal.jimage;
-
-import java.io.IOException;
-import java.nio.ByteBuffer;
-import java.nio.IntBuffer;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-
-// Utility to read module info from .jimage file.
-
-public final class PackageModuleMap {
-    private PackageModuleMap() {}
-
-    public static final String MODULES_ENTRY = "module/modules.offsets";
-    public static final String PACKAGES_ENTRY = "packages.offsets";
-
-    /*
-     * Returns a package-to-module map.
-     *
-     * The package name is in binary name format.
-     */
-    static Map<String,String> readFrom(ImageReader reader) throws IOException {
-        Map<String,String> result = new HashMap<>();
-        List<String> moduleNames = reader.getNames(MODULES_ENTRY);
-
-        for (String moduleName : moduleNames) {
-            List<String> packageNames = reader.getNames(moduleName + "/" + PACKAGES_ENTRY);
-
-            for (String packageName : packageNames) {
-                result.put(packageName, moduleName);
-            }
-        }
-        return result;
-    }
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/PerfectHashBuilder.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,255 @@
+/*
+ * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+*/
+
+package jdk.internal.jimage;
+
+import java.lang.reflect.Array;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.LinkedHashMap;
+import java.util.List;
+import java.util.Map;
+
+public class PerfectHashBuilder<E> {
+    private final static int RETRY_LIMIT = 1000;
+
+    private Class<?> entryComponent;
+    private Class<?> bucketComponent;
+
+    private final Map<UTF8String, Entry<E>> map = new LinkedHashMap<>();
+    private int[] redirect;
+    private Entry<E>[] order;
+    private int count = 0;
+
+    @SuppressWarnings("EqualsAndHashcode")
+    public static class Entry<E> {
+        private final UTF8String key;
+        private final E value;
+
+        Entry() {
+            this("", null);
+        }
+
+        Entry(String key, E value) {
+            this(new UTF8String(key), value);
+        }
+
+        Entry(UTF8String key, E value) {
+            this.key = key;
+            this.value = value;
+        }
+
+        UTF8String getKey() {
+            return key;
+        }
+
+        E getValue() {
+            return value;
+        }
+
+        int hashCode(int seed) {
+            return key.hashCode(seed);
+        }
+
+        @Override
+        public int hashCode() {
+            return key.hashCode();
+        }
+    }
+
+    static class Bucket<E> implements Comparable<Bucket<E>> {
+        final List<Entry<E>> list = new ArrayList<>();
+
+        void add(Entry<E> entry) {
+            list.add(entry);
+        }
+
+        int getSize() {
+            return list.size();
+        }
+
+        List<Entry<E>> getList() {
+            return list;
+        }
+
+        Entry<E> getFirst() {
+            assert !list.isEmpty() : "bucket should never be empty";
+            return list.get(0);
+        }
+
+        @Override
+        public int hashCode() {
+            return getFirst().hashCode();
+        }
+
+        @Override
+        @SuppressWarnings("EqualsWhichDoesntCheckParameterClass")
+        public boolean equals(Object obj) {
+            return this == obj;
+        }
+
+        @Override
+        public int compareTo(Bucket<E> o) {
+            return o.getSize() - getSize();
+        }
+    }
+
+    public PerfectHashBuilder(Class<?> entryComponent, Class<?> bucketComponent) {
+        this.entryComponent = entryComponent;
+        this.bucketComponent = bucketComponent;
+    }
+
+    public int getCount() {
+        return map.size();
+    }
+
+    public int[] getRedirect() {
+        return redirect;
+    }
+
+    public Entry<E>[] getOrder() {
+        return order;
+    }
+
+    public Entry<E> put(String key, E value) {
+        return put(new UTF8String(key), value);
+    }
+
+    public Entry<E> put(UTF8String key, E value) {
+        return put(new Entry<>(key, value));
+    }
+
+    public Entry<E> put(Entry<E> entry) {
+        Entry<E> old = map.put(entry.key, entry);
+
+        if (old == null) {
+            count++;
+        }
+
+        return old;
+    }
+
+    @SuppressWarnings("unchecked")
+    public void generate() {
+        boolean redo = count != 0;
+        while (redo) {
+            redo = false;
+            redirect = new int[count];
+            order = (Entry<E>[])Array.newInstance(entryComponent, count);
+
+            Bucket<E>[] sorted = createBuckets();
+            int free = 0;
+
+            for (Bucket<E> bucket : sorted) {
+                if (bucket.getSize() != 1) {
+                    if (!collidedEntries(bucket, count)) {
+                        redo = true;
+                        break;
+                    }
+                } else {
+                    for ( ; free < count && order[free] != null; free++) {}
+
+                    if (free >= count) {
+                        redo = true;
+                        break;
+                    }
+
+                    order[free] = bucket.getFirst();
+                    redirect[bucket.hashCode() % count] = -1 - free;
+                    free++;
+                }
+            }
+
+            if (redo) {
+                count = (count + 1) | 1;
+            }
+        }
+    }
+
+    @SuppressWarnings("unchecked")
+    private Bucket<E>[] createBuckets() {
+        Bucket<E>[] buckets = (Bucket<E>[])Array.newInstance(bucketComponent, count);
+
+        map.values().stream().forEach((entry) -> {
+            int index = entry.hashCode() % count;
+            Bucket<E> bucket = buckets[index];
+
+            if (bucket == null) {
+                buckets[index] = bucket = new Bucket<>();
+            }
+
+            bucket.add(entry);
+        });
+
+        Bucket<E>[] sorted = Arrays.asList(buckets).stream()
+                .filter((bucket) -> (bucket != null))
+                .sorted()
+                .toArray((length) -> {
+                    return (Bucket<E>[])Array.newInstance(bucketComponent, length);
+                });
+
+        return sorted;
+    }
+
+    private boolean collidedEntries(Bucket<E> bucket, int count) {
+        List<Integer> undo = new ArrayList<>();
+        int seed = UTF8String.HASH_MULTIPLIER + 1;
+        int retry = 0;
+
+        redo:
+        while (true) {
+            for (Entry<E> entry : bucket.getList()) {
+                int index = entry.hashCode(seed) % count;
+                if (order[index] != null) {
+                    if (++retry > RETRY_LIMIT) {
+                        return false;
+                    }
+
+                    undo.stream().forEach((i) -> {
+                        order[i] = null;
+                    });
+
+                    undo.clear();
+                    seed++;
+
+                    if (seed == 0) {
+                        seed = 1;
+                    }
+
+                    continue redo;
+                }
+
+                order[index] = entry;
+                undo.add(index);
+            }
+
+            redirect[bucket.hashCode() % count] = seed;
+
+            break;
+        }
+
+        return true;
+    }
+ }
--- a/jdk/src/java.base/share/classes/jdk/internal/jimage/Resource.java	Thu Jul 16 19:31:01 2015 -0700
+++ /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.  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.internal.jimage;
-
-/**
- * Resource is a class or resource file.
- */
-public class Resource {
-    private final String name;
-    private final long size;
-    private final long csize;
-
-    public Resource(String name, long size, long csize) {
-        this.name = name;
-        this.size = size;
-        this.csize = csize;
-    }
-
-    /**
-     * Returns the name of this entry.
-     */
-    public String name() {
-        return name;
-    }
-
-    /**
-     * Returns the number of uncompressed bytes for this entry.
-     */
-    public long size() {
-        return size;
-    }
-
-    /**
-     * Returns the number of compressed bytes for this entry; 0 if
-     * uncompressed.
-     */
-    public long csize() {
-        return csize;
-    }
-
-    @Override
-    public String toString() {
-        return String.format("%s uncompressed size %d compressed size %d", name, size, csize);
-    }
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ResourcePool.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,256 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.internal.jimage;
+
+import jdk.internal.jimage.decompressor.CompressedResourceHeader;
+import java.nio.ByteBuffer;
+import java.nio.ByteOrder;
+import java.util.Collection;
+import java.util.Map;
+import java.util.Objects;
+import java.util.Set;
+
+/**
+ * Pool of resources. This class contain the content of a jimage file in the
+ * matter of Resource.
+ */
+public interface ResourcePool {
+
+    /**
+     * Resources visitor
+     */
+    public interface Visitor {
+
+        /**
+         * Called for each visited Resource.
+         *
+         * @param resource The resource to deal with.
+         * @param order Byte order
+         * @param strings
+         * @return A resource or null if the passed resource is to be removed
+         * from the jimage.
+         * @throws Exception
+         */
+        public Resource visit(Resource resource, ByteOrder order,
+                StringTable strings) throws Exception;
+    }
+
+    /**
+     * A JImage Resource. Fully identified by its path.
+     */
+    public static class Resource {
+
+        private final String path;
+        private final ByteBuffer content;
+
+        private final String module;
+
+        public Resource(String path, ByteBuffer content) {
+            Objects.requireNonNull(path);
+            Objects.requireNonNull(content);
+            this.path = path;
+            this.content = content.asReadOnlyBuffer();
+            String[] split = ImageFileCreator.splitPath(path);
+            module = split[0];
+        }
+
+        public String getPath() {
+            return path;
+        }
+
+        public String getModule() {
+            return module;
+        }
+
+        /**
+         * The resource content.
+         *
+         * @return A read only buffer.
+         */
+        public ByteBuffer getContent() {
+            return content;
+        }
+
+        public int getLength() {
+            return content.limit();
+        }
+
+        public byte[] getByteArray() {
+            content.rewind();
+            byte[] array = new byte[content.remaining()];
+            content.get(array);
+            return array;
+        }
+
+        @Override
+        public String toString() {
+            return getPath();
+        }
+
+        @Override
+        public boolean equals(Object obj) {
+            if (!(obj instanceof Resource)) {
+                return false;
+            }
+            Resource res = (Resource) obj;
+            return res.path.equals(path);
+        }
+
+        @Override
+        public int hashCode() {
+            int hash = 7;
+            hash = 53 * hash + Objects.hashCode(this.path);
+            return hash;
+        }
+    }
+
+    /**
+     * A resource that has been compressed.
+     */
+    public static final class CompressedResource extends Resource {
+
+        private final long uncompressed_size;
+
+        private CompressedResource(String path, ByteBuffer content,
+                long uncompressed_size) {
+            super(path, content);
+            this.uncompressed_size = uncompressed_size;
+        }
+
+        public long getUncompressedSize() {
+            return uncompressed_size;
+        }
+
+        public static CompressedResource newCompressedResource(Resource original,
+                ByteBuffer compressed,
+                String plugin, String pluginConfig, StringTable strings,
+                ByteOrder order) throws Exception {
+            Objects.requireNonNull(original);
+            Objects.requireNonNull(compressed);
+            Objects.requireNonNull(plugin);
+
+            boolean isTerminal = !(original instanceof CompressedResource);
+            long uncompressed_size = original.getLength();
+            if (original instanceof CompressedResource) {
+                CompressedResource comp = (CompressedResource) original;
+                uncompressed_size = comp.getUncompressedSize();
+            }
+            int nameOffset = strings.addString(plugin);
+            int configOffset = -1;
+            if (pluginConfig != null) {
+                configOffset = strings.addString(plugin);
+            }
+            CompressedResourceHeader rh =
+                    new CompressedResourceHeader(compressed.limit(), original.getLength(),
+                    nameOffset, configOffset, isTerminal);
+            // Merge header with content;
+            byte[] h = rh.getBytes(order);
+            ByteBuffer bb = ByteBuffer.allocate(compressed.limit() + h.length);
+            bb.order(order);
+            bb.put(h);
+            bb.put(compressed);
+            ByteBuffer contentWithHeader = ByteBuffer.wrap(bb.array());
+
+            CompressedResource compressedResource =
+                    new CompressedResource(original.getPath(),
+                    contentWithHeader, uncompressed_size);
+            return compressedResource;
+        }
+    }
+
+    /**
+     * Read only state.
+     *
+     * @return true if readonly false otherwise.
+     */
+    public boolean isReadOnly();
+
+    /**
+     * The byte order
+     *
+     * @return
+     */
+    public ByteOrder getByteOrder();
+
+    /**
+     * Add a resource.
+     *
+     * @param resource The Resource to add.
+     * @throws java.lang.Exception If the pool is read only.
+     */
+    public void addResource(Resource resource) throws Exception;
+
+    /**
+     * Check if a resource is contained in the pool.
+     *
+     * @param res The resource to check.
+     * @return true if res is contained, false otherwise.
+     */
+    public boolean contains(Resource res);
+
+    /**
+     * Get all resources contained in this pool instance.
+     *
+     * @return The collection of resources;
+     */
+    public Collection<Resource> getResources();
+
+    /**
+     * Get the resource for the passed path.
+     *
+     * @param path A resource path
+     * @return A Resource instance or null if the resource is not found
+     */
+    public Resource getResource(String path);
+
+    /**
+     * The Image modules. It is computed based on the resources contained by
+     * this ResourcePool instance.
+     *
+     * @return The Image Modules.
+     */
+    public Map<String, Set<String>> getModulePackages();
+
+    /**
+     * Check if this pool contains some resources.
+     *
+     * @return True if contains some resources.
+     */
+    public boolean isEmpty();
+
+    /**
+     * Visit the resources contained in this ResourcePool.
+     *
+     * @param visitor The visitor
+     * @param output The pool to store resources.
+     * @param strings
+     * @throws Exception
+     */
+    public void visit(Visitor visitor, ResourcePool output, StringTable strings)
+            throws Exception;
+
+    public void addTransformedResource(Resource original, ByteBuffer transformed)
+            throws Exception;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/ResourcePoolImpl.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,211 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.internal.jimage;
+
+import java.nio.ByteBuffer;
+import java.nio.ByteOrder;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.HashSet;
+import java.util.LinkedHashMap;
+import java.util.Map;
+import java.util.Objects;
+import java.util.Set;
+
+/**
+ * Pool of resources. This class contain the content of a jimage file in the
+ * matter of Resource.
+ */
+public class ResourcePoolImpl implements ResourcePool {
+
+    private final Map<String, Resource> resources = new LinkedHashMap<>();
+
+    private final ByteOrder order;
+    private boolean isReadOnly;
+
+    public ResourcePoolImpl(ByteOrder order) {
+        Objects.requireNonNull(order);
+        this.order = order;
+    }
+
+    /**
+     * Make this Resources instance read-only. No resource can be added.
+     */
+    public void setReadOnly() {
+        isReadOnly = true;
+    }
+
+    /**
+     * Read only state.
+     *
+     * @return true if readonly false otherwise.
+     */
+    @Override
+    public boolean isReadOnly() {
+        return isReadOnly;
+    }
+
+    /**
+     * The byte order
+     *
+     * @return
+     */
+    @Override
+    public ByteOrder getByteOrder() {
+        return order;
+    }
+
+    /**
+     * Add a resource.
+     *
+     * @param resource The Resource to add.
+     * @throws java.lang.Exception If the pool is read only.
+     */
+    @Override
+    public void addResource(Resource resource) throws Exception {
+        if (isReadOnly()) {
+            throw new Exception("pool is readonly");
+        }
+        Objects.requireNonNull(resource);
+        if (resources.get(resource.getPath()) != null) {
+            throw new Exception("Resource" + resource.getPath() +
+                    " already present");
+        }
+        resources.put(resource.getPath(), resource);
+    }
+
+    /**
+     * Check if a resource is contained in the pool.
+     *
+     * @param res The resource to check.
+     * @return true if res is contained, false otherwise.
+     */
+    @Override
+    public boolean contains(Resource res) {
+        Objects.requireNonNull(res);
+        try {
+            getResource(res.getPath());
+            return true;
+        } catch (Exception ex) {
+            return false;
+        }
+    }
+
+    /**
+     * Get all resources contained in this pool instance.
+     *
+     * @return The collection of resources;
+     */
+    @Override
+    public Collection<Resource> getResources() {
+        return Collections.unmodifiableCollection(resources.values());
+    }
+
+/**
+     * Get the resource for the passed path.
+     *
+     * @param path A resource path
+     * @return A Resource instance or null if the resource is not found
+     */
+    @Override
+    public Resource getResource(String path) {
+        Objects.requireNonNull(path);
+        return resources.get(path);
+    }
+
+    /**
+     * The Image modules. It is computed based on the resources contained by
+     * this ResourcePool instance.
+     *
+     * @return The Image Modules.
+     */
+    @Override
+    public Map<String, Set<String>> getModulePackages() {
+        Map<String, Set<String>> moduleToPackage = new LinkedHashMap<>();
+        retrieveModulesPackages(moduleToPackage);
+        return moduleToPackage;
+    }
+
+    /**
+     * Check if this pool contains some resources.
+     *
+     * @return True if contains some resources.
+     */
+    @Override
+    public boolean isEmpty() {
+        return resources.isEmpty();
+    }
+
+    /**
+     * Visit the resources contained in this ResourcePool.
+     *
+     * @param visitor The visitor
+     * @param strings
+     * @throws Exception
+     */
+    @Override
+    public void visit(Visitor visitor, ResourcePool output, StringTable strings)
+            throws Exception {
+        for (Resource resource : getResources()) {
+            Resource res = visitor.visit(resource, order, strings);
+            if (res != null) {
+                output.addResource(res);
+            }
+        }
+    }
+
+    @Override
+    public void addTransformedResource(Resource original, ByteBuffer transformed)
+            throws Exception {
+        if (isReadOnly()) {
+            throw new Exception("Pool is readonly");
+        }
+        Objects.requireNonNull(original);
+        Objects.requireNonNull(transformed);
+        if (resources.get(original.getPath()) != null) {
+            throw new Exception("Resource already present");
+        }
+        Resource res = new Resource(original.getPath(), transformed);
+        addResource(res);
+    }
+
+    private void retrieveModulesPackages(Map<String, Set<String>> moduleToPackage) {
+        for (Resource res : resources.values()) {
+            Set<String> pkgs = moduleToPackage.get(res.getModule());
+            if (pkgs == null) {
+                pkgs = new HashSet<>();
+                moduleToPackage.put(res.getModule(), pkgs);
+            }
+            // Module metadata only contains packages with resource files
+            if (ImageFileCreator.isResourcePackage(res.getPath())) {
+                String[] split = ImageFileCreator.splitPath(res.getPath());
+                String pkg = split[1];
+                if (pkg != null && !pkg.isEmpty()) {
+                    pkgs.add(pkg);
+                }
+            }
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/StringTable.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,44 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.internal.jimage;
+
+/**
+* Added strings are stored in the jimage strings table.
+*/
+public interface StringTable {
+    /**
+     * Add a string to the jimage strings table.
+     * @param str The string to add.
+     * @return a String identifier.
+     */
+    public int addString(String str);
+
+    /**
+     * Retrieve a string from the passed id.
+     * @param id The string id.
+     * @return The string referenced by the passed id.
+     */
+    public String getString(int id);
+}
--- a/jdk/src/java.base/share/classes/jdk/internal/jimage/UTF8String.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/UTF8String.java	Wed Jul 05 20:42:36 2017 +0200
@@ -29,14 +29,18 @@
 import java.util.Arrays;
 
 public final class UTF8String implements CharSequence {
-
     // Same as StandardCharsets.UTF_8 without loading all of the standard charsets
     static final Charset UTF_8 = Charset.forName("UTF-8");
 
     static final int NOT_FOUND = -1;
     static final int HASH_MULTIPLIER = 0x01000193;
-    static final UTF8String EMPTY_STRING  = new UTF8String("");
-    static final UTF8String CLASS_STRING  = new UTF8String(".class");
+    static final UTF8String EMPTY_STRING = new UTF8String("");
+    static final UTF8String SLASH_STRING = new UTF8String("/");
+    static final UTF8String DOT_STRING = new UTF8String(".");
+
+    // TODO This strings are implementation specific and should be defined elsewhere.
+    static final UTF8String MODULES_STRING = new UTF8String("/modules");
+    static final UTF8String PACKAGES_STRING = new UTF8String("/packages");
 
     final byte[] bytes;
     final int offset;
@@ -160,8 +164,8 @@
         return seed & 0x7FFFFFFF;
     }
 
-    int hashCode(int base) {
-        return hashCode(base, bytes, offset, count);
+    int hashCode(int seed) {
+        return hashCode(seed, bytes, offset, count);
     }
 
     @Override
@@ -186,7 +190,7 @@
         return equals(this, (UTF8String)obj);
     }
 
-    private static boolean equals(UTF8String a, UTF8String b) {
+    public static boolean equals(UTF8String a, UTF8String b) {
         if (a == b) {
             return true;
         }
@@ -211,6 +215,10 @@
         return true;
     }
 
+    public byte[] getBytesCopy() {
+        return Arrays.copyOfRange(bytes, offset, offset + count);
+    }
+
     byte[] getBytes() {
         if (offset != 0 || bytes.length != count) {
             return Arrays.copyOfRange(bytes, offset, offset + count);
@@ -232,33 +240,11 @@
     public char charAt(int index) {
         int ch = byteAt(index);
 
-        return (ch & 0x80) != 0 ? (char)ch : '\0';
+        return (ch & 0x80) == 0 ? (char)ch : '\0';
     }
 
     @Override
     public CharSequence subSequence(int start, int end) {
         return (CharSequence)substring(start, end - start);
     }
-
-    static UTF8String match(UTF8String a, UTF8String b) {
-        int aCount = a.count;
-        int bCount = b.count;
-
-        if (aCount < bCount) {
-            return null;
-        }
-
-        byte[] aBytes = a.bytes;
-        byte[] bBytes = b.bytes;
-        int aOffset = a.offset;
-        int bOffset = b.offset;
-
-        for (int i = 0; i < bCount; i++) {
-            if (aBytes[aOffset + i] != bBytes[bOffset + i]) {
-                return null;
-            }
-        }
-
-        return new UTF8String(aBytes, aOffset + bCount, aCount - bCount);
-    }
 }
--- a/jdk/src/java.base/share/classes/jdk/internal/jimage/concurrent/ConcurrentPReader.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,149 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.  Oracle designates this
- * particular file as subject to the "Classpath" exception as provided
- * by Oracle in the LICENSE file that accompanied this code.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package jdk.internal.jimage.concurrent;
-
-import java.io.FileDescriptor;
-import java.io.FileInputStream;
-import java.io.IOException;
-
-import jdk.internal.jimage.PReader;
-
-import sun.misc.Unsafe;
-
-/**
- * A PReader implementation that supports concurrent pread operations.
- */
-public class ConcurrentPReader extends PReader {
-
-    private static final Unsafe UNSAFE = Unsafe.getUnsafe();
-    private static final long BA_OFFSET = (long) UNSAFE.arrayBaseOffset(byte[].class);
-
-    /**
-     * A temporary buffer that is cached on a per-thread basis.
-     */
-    private static class TemporaryBuffer {
-        static final ThreadLocal<TemporaryBuffer> CACHED_BUFFER =
-             new ThreadLocal<TemporaryBuffer>() {
-                @Override
-                protected TemporaryBuffer initialValue() { return null; }
-             };
-
-        static final TemporaryBuffer NOT_AVAILABLE = new TemporaryBuffer(0L, 0);
-
-        final long address;
-        final int size;
-
-        TemporaryBuffer(long address, int size) {
-            this.address = address;
-            this.size = size;
-        }
-
-        long address() { return address; }
-        int size() { return size; }
-
-        /**
-         * Returns the {@code TemporaryBuffer} for the current thread. The buffer
-         * is guaranteed to be of at least the given size. Returns {@code null}
-         * if a buffer cannot be cached for this thread.
-         */
-        static TemporaryBuffer get(int len) {
-            TemporaryBuffer buffer = CACHED_BUFFER.get();
-
-            // cached buffer large enough?
-            if (buffer != null && buffer.size() >= len) {
-                return buffer;
-            }
-
-            // if this is an InnocuousThread then don't return anything
-            if (buffer == NOT_AVAILABLE)
-                return null;
-
-            if (buffer != null) {
-                // replace buffer in cache with a larger buffer
-                long originalAddress = buffer.address();
-                long address = UNSAFE.allocateMemory(len);
-                buffer = new TemporaryBuffer(address, len);
-                CACHED_BUFFER.set(buffer);
-                UNSAFE.freeMemory(originalAddress);
-            } else {
-                // first usage.
-                if (Thread.currentThread() instanceof sun.misc.InnocuousThread) {
-                    buffer = NOT_AVAILABLE;
-                } else {
-                    long address = UNSAFE.allocateMemory(len);
-                    buffer = new TemporaryBuffer(address, len);
-                }
-                CACHED_BUFFER.set(buffer);
-            }
-            return buffer;
-        }
-    }
-
-    private final FileDescriptor fd;
-
-    private ConcurrentPReader(FileInputStream fis) throws IOException {
-        super(fis.getChannel());
-        this.fd = fis.getFD();
-    }
-
-    public ConcurrentPReader(String file) throws IOException {
-        this(new FileInputStream(file));
-    }
-
-    @Override
-    public byte[] read(int len, long position) throws IOException {
-        // need a temporary area of memory to read into
-        TemporaryBuffer buffer = TemporaryBuffer.get(len);
-        long address;
-        if (buffer == null) {
-            address = UNSAFE.allocateMemory(len);
-        } else {
-            address = buffer.address();
-        }
-        try {
-            int n = pread(fd, address, len, position);
-            if (n != len)
-                throw new InternalError("short read, not handled yet");
-            byte[] result = new byte[n];
-            UNSAFE.copyMemory(null, address, result, BA_OFFSET, len);
-            return result;
-        } finally {
-            if (buffer == null) {
-                UNSAFE.freeMemory(address);
-            }
-        }
-    }
-
-    private static native int pread(FileDescriptor fd, long address, int len, long pos)
-        throws IOException;
-
-    private static native void initIDs();
-
-    static {
-        System.loadLibrary("java");
-        initIDs();
-    }
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/decompressor/CompressedResourceHeader.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,124 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.internal.jimage.decompressor;
+
+import java.nio.ByteBuffer;
+import java.nio.ByteOrder;
+import java.util.Objects;
+import jdk.internal.jimage.decompressor.ResourceDecompressor.StringsProvider;
+
+/**
+ *
+ * A resource header for compressed resource. This class is handled internally,
+ * you don't have to add header to the resource, headers are added automatically
+ * for compressed resources.
+ */
+public final class CompressedResourceHeader {
+
+    private static final int SIZE = 21;
+    public static final int MAGIC = 0xCAFEFAFA;
+    private final int uncompressedSize;
+    private final int compressedSize;
+    private final int decompressorNameOffset;
+    private final int contentOffset;
+    private final boolean isTerminal;
+
+    public CompressedResourceHeader(int compressedSize,
+            int uncompressedSize, int decompressorNameOffset, int contentOffset,
+            boolean isTerminal) {
+        this.compressedSize = compressedSize;
+        this.uncompressedSize = uncompressedSize;
+        this.decompressorNameOffset = decompressorNameOffset;
+        this.contentOffset = contentOffset;
+        this.isTerminal = isTerminal;
+    }
+
+    public boolean isTerminal() {
+        return isTerminal;
+    }
+
+    public int getDecompressorNameOffset() {
+        return decompressorNameOffset;
+    }
+
+    public int getContentOffset() {
+        return contentOffset;
+    }
+
+    public String getStoredContent(StringsProvider provider) {
+        Objects.nonNull(provider);
+        if(contentOffset == -1) {
+            return null;
+        }
+        return provider.getString(contentOffset);
+    }
+
+    public int getUncompressedSize() {
+        return uncompressedSize;
+    }
+
+    public int getResourceSize() {
+        return compressedSize;
+    }
+
+    public byte[] getBytes(ByteOrder order) {
+        Objects.requireNonNull(order);
+        ByteBuffer buffer = ByteBuffer.allocate(SIZE);
+        buffer.order(order);
+        buffer.putInt(MAGIC);
+        buffer.putInt(compressedSize);
+        buffer.putInt(uncompressedSize);
+        buffer.putInt(decompressorNameOffset);
+        buffer.putInt(contentOffset);
+        buffer.put(isTerminal ? (byte)1 : (byte)0);
+        return buffer.array();
+    }
+
+    public static int getSize() {
+        return SIZE;
+    }
+
+    public static CompressedResourceHeader readFromResource(ByteOrder order,
+            byte[] resource) {
+        Objects.requireNonNull(order);
+        Objects.requireNonNull(resource);
+        if (resource.length < getSize()) {
+            return null;
+        }
+        ByteBuffer buffer = ByteBuffer.wrap(resource, 0, SIZE);
+        buffer.order(order);
+        int magic = buffer.getInt();
+        if(magic != MAGIC) {
+            return null;
+        }
+        int size = buffer.getInt();
+        int uncompressedSize = buffer.getInt();
+        int decompressorNameOffset = buffer.getInt();
+        int contentIndex = buffer.getInt();
+        byte isTerminal = buffer.get();
+        return new CompressedResourceHeader(size, uncompressedSize,
+                decompressorNameOffset, contentIndex, isTerminal == 1);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/decompressor/Decompressor.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,97 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.internal.jimage.decompressor;
+
+import java.io.ByteArrayInputStream;
+import java.io.IOException;
+import java.nio.ByteOrder;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.Objects;
+import java.util.Properties;
+import jdk.internal.jimage.decompressor.ResourceDecompressor.StringsProvider;
+
+/**
+ * Entry point to decompress resources.
+ */
+public final class Decompressor {
+
+    private final Map<Integer, ResourceDecompressor> pluginsCache = new HashMap<>();
+
+    public Decompressor() {
+    }
+
+    /**
+     * Decompress a resource.
+     * @param order Byte order.
+     * @param provider Strings provider
+     * @param content The resource content to uncompress.
+     * @return A fully uncompressed resource.
+     * @throws IOException
+     */
+    public byte[] decompressResource(ByteOrder order, StringsProvider provider,
+            byte[] content) throws IOException {
+        Objects.requireNonNull(order);
+        Objects.requireNonNull(provider);
+        Objects.requireNonNull(content);
+        CompressedResourceHeader header;
+        do {
+            header = CompressedResourceHeader.readFromResource(order, content);
+            if (header != null) {
+                ResourceDecompressor decompressor =
+                        pluginsCache.get(header.getDecompressorNameOffset());
+                if (decompressor == null) {
+                    String pluginName =
+                            provider.getString(header.getDecompressorNameOffset());
+                    if (pluginName == null) {
+                        throw new IOException("Plugin name not found");
+                    }
+                    String storedContent = header.getStoredContent(provider);
+                    Properties props = new Properties();
+                    if (storedContent != null) {
+                        try (ByteArrayInputStream stream =
+                                new ByteArrayInputStream(storedContent.getBytes());) {
+                            props.loadFromXML(stream);
+                        }
+                    }
+                    decompressor = ResourceDecompressorRepository.
+                            newResourceDecompressor(props, pluginName);
+                    if (decompressor == null) {
+                        throw new IOException("Plugin not found: " + pluginName);
+                    }
+
+                    pluginsCache.put(header.getDecompressorNameOffset(), decompressor);
+                }
+                try {
+                    content = decompressor.decompress(provider, content,
+                            CompressedResourceHeader.getSize(), header.getUncompressedSize());
+                } catch (Exception ex) {
+                    throw new IOException(ex);
+                }
+            }
+        } while (header != null);
+        return content;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/decompressor/ResourceDecompressor.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,53 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.internal.jimage.decompressor;
+
+/**
+ *
+ * JImage Decompressor.
+ */
+public interface ResourceDecompressor {
+
+    public interface StringsProvider {
+        public String getString(int offset);
+    }
+    /**
+     * Decompressor unique name.
+     * @return The decompressor name.
+     */
+    public String getName();
+
+    /**
+     * Decompress a resource.
+     * @param strings The String provider
+     * @param content The resource content
+     * @param offset Resource content offset
+     * @param originalSize Uncompressed size
+     * @return Uncompressed resource
+     * @throws Exception
+     */
+    public byte[] decompress(StringsProvider strings, byte[] content, int offset,
+            int originalSize) throws Exception;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/decompressor/ResourceDecompressorFactory.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,80 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.internal.jimage.decompressor;
+
+import java.io.IOException;
+import java.util.Properties;
+
+/**
+ *
+ * JImage Resource Decompressor factory
+ */
+public abstract class ResourceDecompressorFactory {
+    private final String name;
+    private final String description;
+    private final String arguments;
+
+    protected ResourceDecompressorFactory(String name, String description,
+            String arguments) {
+        this.name = name;
+        this.description = description;
+        this.arguments = arguments;
+    }
+
+    /**
+     * The Factory name.
+     * @return The name.
+     */
+    public String getName() {
+        return name;
+    }
+
+    /**
+     * The Factory description.
+     * @return The description.
+     */
+    public String getDescription() {
+        return description;
+    }
+
+    /**
+     * The Factory arguments description.
+     * @return The arguments description.
+     */
+    public String getArgumentsDescription() {
+        return arguments;
+    }
+
+    /**
+     * To build a new decompressor.
+     * @param properties Contains configuration.
+     * @return A new decompressor.
+     * @throws IOException
+     */
+    public abstract ResourceDecompressor newDecompressor(Properties properties)
+            throws IOException;
+
+}
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/decompressor/ResourceDecompressorRepository.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,70 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.internal.jimage.decompressor;
+
+import java.io.IOException;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.Properties;
+
+/**
+ *
+ * JImage Decompressors. All decompressors must be registered in the static
+ * initializer of this class.
+ */
+public final class ResourceDecompressorRepository {
+
+    private ResourceDecompressorRepository() {
+    }
+
+    private static final Map<String, ResourceDecompressorFactory> factories = new HashMap<>();
+
+    static {
+        registerReaderProvider(new ZipDecompressorFactory());
+    }
+
+    /**
+     * Build a new decompressor for the passed name.
+     * @param properties Contains plugin configuration.
+     * @param name The plugin name to build.
+     * @return A decompressor or null if not found
+     * @throws IOException
+     */
+    public static ResourceDecompressor newResourceDecompressor(Properties properties,
+            String name) throws IOException {
+
+        ResourceDecompressorFactory fact = factories.get(name);
+        if (fact != null) {
+            return fact.newDecompressor(properties);
+        }
+        return null;
+    }
+
+    private static void registerReaderProvider(ResourceDecompressorFactory factory) {
+        factories.put(factory.getName(), factory);
+    }
+
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/decompressor/ZipDecompressor.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,79 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.internal.jimage.decompressor;
+
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+import java.util.zip.DataFormatException;
+import java.util.zip.Inflater;
+
+/**
+ *
+ * ZIP Decompressor
+ */
+final class ZipDecompressor implements ResourceDecompressor {
+
+    @Override
+    public String getName() {
+        return ZipDecompressorFactory.NAME;
+    }
+
+    static byte[] decompress(byte[] bytesIn, int offset) {
+        Inflater inflater = new Inflater();
+        inflater.setInput(bytesIn, offset, bytesIn.length - offset);
+        ByteArrayOutputStream stream = new ByteArrayOutputStream(bytesIn.length - offset);
+        byte[] buffer = new byte[1024];
+
+        while (!inflater.finished()) {
+            int count;
+
+            try {
+                count = inflater.inflate(buffer);
+            } catch (DataFormatException ex) {
+                return null;
+            }
+
+            stream.write(buffer, 0, count);
+        }
+
+        try {
+            stream.close();
+        } catch (IOException ex) {
+            return null;
+        }
+
+        byte[] bytesOut = stream.toByteArray();
+        inflater.end();
+
+        return bytesOut;
+    }
+
+    @Override
+    public byte[] decompress(StringsProvider reader, byte[] content, int offset,
+            int originalSize) throws Exception {
+        byte[] decompressed = decompress(content, offset);
+        return decompressed;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/jdk/internal/jimage/decompressor/ZipDecompressorFactory.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,45 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.internal.jimage.decompressor;
+
+import java.io.IOException;
+import java.util.Properties;
+
+/**
+ *
+ * ZIP decompressor factory
+ */
+public final class ZipDecompressorFactory extends ResourceDecompressorFactory {
+    public static final String NAME = "zip";
+    public ZipDecompressorFactory() {
+        super(NAME, "ZIP Decompression", null);
+    }
+
+    @Override
+    public ResourceDecompressor newDecompressor(Properties properties)
+            throws IOException {
+        return new ZipDecompressor();
+    }
+}
--- a/jdk/src/java.base/share/classes/jdk/internal/jrtfs/JrtDirectoryStream.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/jdk/internal/jrtfs/JrtDirectoryStream.java	Wed Jul 05 20:42:36 2017 +0200
@@ -51,7 +51,7 @@
         this.jrtfs = jrtPath.getFileSystem();
         this.path = jrtPath.getResolvedPath();
         // sanity check
-        if (!jrtfs.isDirectory(path))
+        if (!jrtfs.isDirectory(path, true))
             throw new NotDirectoryException(jrtPath.toString());
 
         // absolute path and does not have funky chars in front like /./java.base
--- a/jdk/src/java.base/share/classes/jdk/internal/jrtfs/JrtFileAttributeView.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/jdk/internal/jrtfs/JrtFileAttributeView.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,6 +25,7 @@
 
 package jdk.internal.jrtfs;
 
+import java.nio.file.LinkOption;
 import java.nio.file.attribute.*;
 import java.io.IOException;
 import java.util.LinkedHashMap;
@@ -48,30 +49,32 @@
 
     private final JrtPath path;
     private final boolean isJrtView;
+    private final LinkOption[] options;
 
-    private JrtFileAttributeView(JrtPath path, boolean isJrtView) {
+    private JrtFileAttributeView(JrtPath path, boolean isJrtView, LinkOption... options) {
         this.path = path;
         this.isJrtView = isJrtView;
+        this.options = options;
     }
 
     @SuppressWarnings("unchecked") // Cast to V
-    static <V extends FileAttributeView> V get(JrtPath path, Class<V> type) {
+    static <V extends FileAttributeView> V get(JrtPath path, Class<V> type, LinkOption... options) {
         if (type == null)
             throw new NullPointerException();
         if (type == BasicFileAttributeView.class)
-            return (V)new JrtFileAttributeView(path, false);
+            return (V)new JrtFileAttributeView(path, false, options);
         if (type == JrtFileAttributeView.class)
-            return (V)new JrtFileAttributeView(path, true);
+            return (V)new JrtFileAttributeView(path, true, options);
         return null;
     }
 
-    static JrtFileAttributeView get(JrtPath path, String type) {
+    static JrtFileAttributeView get(JrtPath path, String type, LinkOption... options) {
         if (type == null)
             throw new NullPointerException();
         if (type.equals("basic"))
-            return new JrtFileAttributeView(path, false);
+            return new JrtFileAttributeView(path, false, options);
         if (type.equals("jjrt"))
-            return new JrtFileAttributeView(path, true);
+            return new JrtFileAttributeView(path, true, options);
         return null;
     }
 
@@ -83,7 +86,7 @@
     @Override
     public JrtFileAttributes readAttributes() throws IOException
     {
-        return path.getAttributes();
+        return path.getAttributes(options);
     }
 
     @Override
--- a/jdk/src/java.base/share/classes/jdk/internal/jrtfs/JrtFileAttributes.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/jdk/internal/jrtfs/JrtFileAttributes.java	Wed Jul 05 20:42:36 2017 +0200
@@ -76,12 +76,12 @@
 
     @Override
     public boolean isSymbolicLink() {
-        return false;
+        return node.isLink();
     }
 
     @Override
     public Object fileKey() {
-        return null;
+        return node.resolveLink(true);
     }
 
     ///////// jrt entry attributes ///////////
--- a/jdk/src/java.base/share/classes/jdk/internal/jrtfs/JrtFileSystem.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/jdk/internal/jrtfs/JrtFileSystem.java	Wed Jul 05 20:42:36 2017 +0200
@@ -31,9 +31,9 @@
 import java.nio.ByteBuffer;
 import java.nio.channels.*;
 import java.nio.charset.Charset;
-import java.nio.file.AccessMode;
 import java.nio.file.ClosedFileSystemException;
 import java.nio.file.CopyOption;
+import java.nio.file.LinkOption;
 import java.nio.file.FileStore;
 import java.nio.file.FileSystem;
 import java.nio.file.FileSystemException;
@@ -45,16 +45,13 @@
 import java.nio.file.Path;
 import java.nio.file.PathMatcher;
 import java.nio.file.ReadOnlyFileSystemException;
-import java.nio.file.StandardCopyOption;
 import java.nio.file.StandardOpenOption;
 import java.nio.file.WatchService;
 import java.nio.file.attribute.FileAttribute;
 import java.nio.file.attribute.FileTime;
 import java.nio.file.attribute.UserPrincipalLookupService;
 import java.nio.file.spi.FileSystemProvider;
-import java.security.AccessController;
-import java.security.PrivilegedActionException;
-import java.security.PrivilegedExceptionAction;
+import java.util.concurrent.ConcurrentHashMap;
 import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.Collections;
@@ -63,8 +60,9 @@
 import java.util.List;
 import java.util.Map;
 import java.util.Set;
+import java.util.function.Function;
 import java.util.regex.Pattern;
-import java.util.stream.Collectors;
+import static java.util.stream.Collectors.toList;
 import jdk.internal.jimage.ImageReader;
 import jdk.internal.jimage.ImageReader.Node;
 import jdk.internal.jimage.UTF8String;
@@ -74,6 +72,7 @@
  */
 class JrtFileSystem extends FileSystem {
     private static final Charset UTF_8 = Charset.forName("UTF-8");
+
     private final JrtFileSystemProvider provider;
     // System image readers
     private ImageReader bootImage;
@@ -109,7 +108,8 @@
         this.extImage = openImage(SystemImages.extImagePath);
         this.appImage = openImage(SystemImages.appImagePath);
 
-        rootPath = new JrtPath(this, new byte[]{'/'});
+        byte[] root = new byte[] { '/' };
+        rootPath = new JrtPath(this, root);
         isOpen = true;
     }
 
@@ -149,12 +149,12 @@
         synchronized(this) {
             isOpen = false;
 
-            // close all image readers and null out
+            // close all image reader and null out
             bootImage.close();
+            bootImage = null;
             extImage.close();
+            extImage = null;
             appImage.close();
-            bootImage = null;
-            extImage = null;
             appImage = null;
         }
     }
@@ -289,21 +289,52 @@
         }
     }
 
-    private NodeAndImage findNode(byte[] path) throws IOException {
-        ImageReader image = bootImage;
+    private NodeAndImage lookup(byte[] path) {
         Node node = bootImage.findNode(path);
+        ImageReader image = bootImage;
         if (node == null) {
+            node = extImage.findNode(path);
             image = extImage;
-            node = extImage.findNode(path);
         }
         if (node == null) {
+            node = appImage.findNode(path);
             image = appImage;
-            node = appImage.findNode(path);
         }
-        if (node == null || node.isHidden()) {
-            throw new NoSuchFileException(getString(path));
+        return node != null? new NodeAndImage(node, image) : null;
+    }
+
+    private NodeAndImage lookupSymbolic(byte[] path) {
+        for (int i = 1; i < path.length; i++) {
+            if (path[i] == (byte)'/') {
+                byte[] prefix = Arrays.copyOfRange(path, 0, i);
+                NodeAndImage ni = lookup(prefix);
+                if (ni == null) {
+                    break;
+                }
+
+                if (ni.node.isLink()) {
+                    Node link = ni.node.resolveLink(true);
+                    // resolved symbolic path concatenated to the rest of the path
+                    UTF8String resPath = link.getName().concat(new UTF8String(path, i));
+                    byte[] resPathBytes = resPath.getBytesCopy();
+                    ni = lookup(resPathBytes);
+                    return ni != null? ni : lookupSymbolic(resPathBytes);
+                }
+            }
         }
-        return new NodeAndImage(node, image);
+
+        return null;
+    }
+
+    private NodeAndImage findNode(byte[] path) throws IOException {
+        NodeAndImage ni = lookup(path);
+        if (ni == null) {
+            ni = lookupSymbolic(path);
+            if (ni == null) {
+                throw new NoSuchFileException(getString(path));
+            }
+        }
+        return ni;
     }
 
     private NodeAndImage checkNode(byte[] path) throws IOException {
@@ -321,10 +352,28 @@
         return ni;
     }
 
+    static boolean followLinks(LinkOption... options) {
+        if (options != null) {
+            for (LinkOption lo : options) {
+                if (lo == LinkOption.NOFOLLOW_LINKS) {
+                    return false;
+                } else if (lo == null) {
+                    throw new NullPointerException();
+                } else {
+                    throw new AssertionError("should not reach here");
+                }
+            }
+        }
+        return true;
+    }
+
     // package private helpers
-    JrtFileAttributes getFileAttributes(byte[] path)
+    JrtFileAttributes getFileAttributes(byte[] path, LinkOption... options)
             throws IOException {
         NodeAndImage ni = checkNode(path);
+        if (ni.node.isLink() && followLinks(options)) {
+            return new JrtFileAttributes(ni.node.resolveLink(true));
+        }
         return new JrtFileAttributes(ni.node);
     }
 
@@ -343,11 +392,13 @@
         return true;
     }
 
-    boolean isDirectory(byte[] path)
+    boolean isDirectory(byte[] path, boolean resolveLinks)
             throws IOException {
         ensureOpen();
         NodeAndImage ni = checkNode(path);
-        return ni.node.isDirectory();
+        return resolveLinks && ni.node.isLink()?
+            ni.node.resolveLink(true).isDirectory() :
+            ni.node.isDirectory();
     }
 
     JrtPath toJrtPath(String path) {
@@ -358,6 +409,28 @@
         return new JrtPath(this, path);
     }
 
+    boolean isSameFile(JrtPath p1, JrtPath p2) throws IOException {
+        NodeAndImage n1 = findNode(p1.getName());
+        NodeAndImage n2 = findNode(p2.getName());
+        return n1.node.equals(n2.node);
+    }
+
+    boolean isLink(JrtPath jrtPath) throws IOException {
+        return findNode(jrtPath.getName()).node.isLink();
+    }
+
+    JrtPath resolveLink(JrtPath jrtPath) throws IOException {
+        NodeAndImage ni = findNode(jrtPath.getName());
+        if (ni.node.isLink()) {
+            Node node = ni.node.resolveLink();
+            return toJrtPath(node.getName().getBytesCopy());
+        }
+
+        return jrtPath;
+    }
+
+    private Map<UTF8String, List<Node>> packagesTreeChildren = new ConcurrentHashMap<>();
+
     /**
      * returns the list of child paths of the given directory "path"
      *
@@ -369,49 +442,73 @@
     Iterator<Path> iteratorOf(byte[] path, String childPrefix)
             throws IOException {
         NodeAndImage ni = checkNode(path);
-        if (!ni.node.isDirectory()) {
+        Node node = ni.node.resolveLink(true);
+
+        if (!node.isDirectory()) {
             throw new NotDirectoryException(getString(path));
         }
 
-        if (ni.node.isRootDir()) {
+        if (node.isRootDir()) {
             return rootDirIterator(path, childPrefix);
+        } else if (node.isModulesDir()) {
+            return modulesDirIterator(path, childPrefix);
+        } else if (node.isPackagesDir()) {
+            return packagesDirIterator(path, childPrefix);
+        } else if (node.getNameString().startsWith("/packages/")) {
+            if (ni.image != appImage) {
+                UTF8String name = node.getName();
+                List<Node> children = packagesTreeChildren.get(name);
+                if (children != null) {
+                    return nodesToIterator(toJrtPath(path), childPrefix, children);
+                }
+
+                children = new ArrayList<>();
+                children.addAll(node.getChildren());
+                Node tmpNode = null;
+                // found in boot
+                if (ni.image == bootImage) {
+                    tmpNode = extImage.findNode(name);
+                    if (tmpNode != null) {
+                        children.addAll(tmpNode.getChildren());
+                    }
+                }
+
+                // found in ext
+                tmpNode = appImage.findNode(name);
+                if (tmpNode != null) {
+                    children.addAll(tmpNode.getChildren());
+                }
+
+                packagesTreeChildren.put(name, children);
+                return nodesToIterator(toJrtPath(path), childPrefix, children);
+            }
         }
 
-        return nodesToIterator(toJrtPath(path), childPrefix, ni.node.getChildren());
+        return nodesToIterator(toJrtPath(path), childPrefix, node.getChildren());
     }
 
     private Iterator<Path> nodesToIterator(Path path, String childPrefix, List<Node> childNodes) {
-        List<Path> childPaths;
-        if (childPrefix == null) {
-            childPaths = childNodes.stream()
-                .filter(Node::isVisible)
-                .map(child -> toJrtPath(child.getNameString()))
-                .collect(Collectors.toCollection(ArrayList::new));
-        } else {
-            childPaths = childNodes.stream()
-                .filter(Node::isVisible)
-                .map(child -> toJrtPath(childPrefix + child.getNameString().substring(1)))
-                .collect(Collectors.toCollection(ArrayList::new));
-        }
-        return childPaths.iterator();
+        Function<Node, Path> f = childPrefix == null
+                ? child -> toJrtPath(child.getNameString())
+                : child -> toJrtPath(childPrefix + child.getNameString().substring(1));
+         return childNodes.stream().map(f).collect(toList()).iterator();
     }
 
-    private List<Node> rootChildren;
-    private static void addRootDirContent(List<Node> dest, List<Node> src) {
-        for (Node n : src) {
-            // only module directories at the top level. Filter other stuff!
-            if (n.isModuleDir()) {
-                dest.add(n);
+    private void addRootDirContent(List<Node> children) {
+        for (Node child : children) {
+            if (!(child.isModulesDir() || child.isPackagesDir())) {
+                rootChildren.add(child);
             }
         }
     }
 
+    private List<Node> rootChildren;
     private synchronized void initRootChildren(byte[] path) {
         if (rootChildren == null) {
             rootChildren = new ArrayList<>();
-            addRootDirContent(rootChildren, bootImage.findNode(path).getChildren());
-            addRootDirContent(rootChildren, extImage.findNode(path).getChildren());
-            addRootDirContent(rootChildren, appImage.findNode(path).getChildren());
+            rootChildren.addAll(bootImage.findNode(path).getChildren());
+            addRootDirContent(extImage.findNode(path).getChildren());
+            addRootDirContent(appImage.findNode(path).getChildren());
         }
     }
 
@@ -420,6 +517,35 @@
         return nodesToIterator(rootPath, childPrefix, rootChildren);
     }
 
+    private List<Node> modulesChildren;
+    private synchronized void initModulesChildren(byte[] path) {
+        if (modulesChildren == null) {
+            modulesChildren = new ArrayList<>();
+            modulesChildren.addAll(bootImage.findNode(path).getChildren());
+            modulesChildren.addAll(appImage.findNode(path).getChildren());
+            modulesChildren.addAll(extImage.findNode(path).getChildren());
+        }
+    }
+
+    private Iterator<Path> modulesDirIterator(byte[] path, String childPrefix) throws IOException {
+        initModulesChildren(path);
+        return nodesToIterator(new JrtPath(this, path), childPrefix, modulesChildren);
+    }
+
+    private List<Node> packagesChildren;
+    private synchronized void initPackagesChildren(byte[] path) {
+        if (packagesChildren == null) {
+            packagesChildren = new ArrayList<>();
+            packagesChildren.addAll(bootImage.findNode(path).getChildren());
+            packagesChildren.addAll(extImage.findNode(path).getChildren());
+            packagesChildren.addAll(appImage.findNode(path).getChildren());
+        }
+    }
+    private Iterator<Path> packagesDirIterator(byte[] path, String childPrefix) throws IOException {
+        initPackagesChildren(path);
+        return nodesToIterator(new JrtPath(this, path), childPrefix, packagesChildren);
+    }
+
     void createDirectory(byte[] dir, FileAttribute<?>... attrs)
             throws IOException {
         throw readOnly();
--- a/jdk/src/java.base/share/classes/jdk/internal/jrtfs/JrtFileSystemProvider.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/jdk/internal/jrtfs/JrtFileSystemProvider.java	Wed Jul 05 20:42:36 2017 +0200
@@ -146,6 +146,11 @@
     }
 
     @Override
+    public Path readSymbolicLink(Path link) throws IOException {
+        return toJrtPath(link).readSymbolicLink();
+    }
+
+    @Override
     public void copy(Path src, Path target, CopyOption... options)
         throws IOException
     {
@@ -169,7 +174,7 @@
     public <V extends FileAttributeView> V
         getFileAttributeView(Path path, Class<V> type, LinkOption... options)
     {
-        return JrtFileAttributeView.get(toJrtPath(path), type);
+        return JrtFileAttributeView.get(toJrtPath(path), type, options);
     }
 
     @Override
@@ -250,7 +255,7 @@
         throws IOException
     {
         if (type == BasicFileAttributes.class || type == JrtFileAttributes.class)
-            return (A)toJrtPath(path).getAttributes();
+            return (A)toJrtPath(path).getAttributes(options);
         return null;
     }
 
--- a/jdk/src/java.base/share/classes/jdk/internal/jrtfs/JrtPath.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/jdk/internal/jrtfs/JrtPath.java	Wed Jul 05 20:42:36 2017 +0200
@@ -55,6 +55,10 @@
             this.path = normalize(path);
     }
 
+    byte[] getName() {
+        return path;
+    }
+
     @Override
     public JrtPath getRoot() {
         if (this.isAbsolute())
@@ -140,10 +144,19 @@
     @Override
     public JrtPath toRealPath(LinkOption... options) throws IOException {
         JrtPath realPath = new JrtPath(jrtfs, getResolvedPath()).toAbsolutePath();
+        realPath = JrtFileSystem.followLinks(options)? jrtfs.resolveLink(this) : realPath;
         realPath.checkAccess();
         return realPath;
     }
 
+    JrtPath readSymbolicLink() throws IOException {
+        if (! jrtfs.isLink(this)) {
+           throw new IOException("not a symbolic link");
+        }
+
+        return jrtfs.resolveLink(this);
+    }
+
     boolean isHidden() {
         return false;
     }
@@ -638,9 +651,9 @@
         jrtfs.deleteFile(getResolvedPath(), false);
     }
 
-    JrtFileAttributes getAttributes() throws IOException
+    JrtFileAttributes getAttributes(LinkOption... options) throws IOException
     {
-        JrtFileAttributes zfas = jrtfs.getFileAttributes(getResolvedPath());
+        JrtFileAttributes zfas = jrtfs.getFileAttributes(getResolvedPath(), options);
         if (zfas == null)
             throw new NoSuchFileException(toString());
         return zfas;
@@ -659,7 +672,7 @@
             type = attribute.substring(0, colonPos++);
             attr = attribute.substring(colonPos);
         }
-        JrtFileAttributeView view = JrtFileAttributeView.get(this, type);
+        JrtFileAttributeView view = JrtFileAttributeView.get(this, type, options);
         if (view == null)
             throw new UnsupportedOperationException("view <" + view + "> is not supported");
         view.setAttribute(attr, value);
@@ -685,7 +698,7 @@
             view = attributes.substring(0, colonPos++);
             attrs = attributes.substring(colonPos);
         }
-        JrtFileAttributeView jrtfv = JrtFileAttributeView.get(this, view);
+        JrtFileAttributeView jrtfv = JrtFileAttributeView.get(this, view, options);
         if (jrtfv == null) {
             throw new UnsupportedOperationException("view not supported");
         }
@@ -706,9 +719,10 @@
             this.getFileSystem() != other.getFileSystem())
             return false;
         this.checkAccess();
-        ((JrtPath)other).checkAccess();
-        return Arrays.equals(this.getResolvedPath(),
-                             ((JrtPath)other).getResolvedPath());
+        JrtPath path = (JrtPath)other;
+        path.checkAccess();
+        return Arrays.equals(this.getResolvedPath(), path.getResolvedPath()) ||
+            jrtfs.isSameFile(this, (JrtPath)other);
     }
 
     SeekableByteChannel newByteChannel(Set<? extends OpenOption> options,
--- a/jdk/src/java.base/share/classes/jdk/internal/jrtfs/SystemImages.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/jdk/internal/jrtfs/SystemImages.java	Wed Jul 05 20:42:36 2017 +0200
@@ -42,6 +42,7 @@
     static final Path bootImagePath;
     static final Path extImagePath;
     static final Path appImagePath;
+
     static {
         PrivilegedAction<String> pa = SystemImages::findHome;
         RUNTIME_HOME = AccessController.doPrivileged(pa);
--- a/jdk/src/java.base/share/classes/sun/misc/JavaNetAccess.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/JavaNetAccess.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2006, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2006, 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
@@ -26,10 +26,17 @@
 package sun.misc;
 
 import java.net.URLClassLoader;
+import java.net.InetAddress;
 
 public interface JavaNetAccess {
     /**
      * return the URLClassPath belonging to the given loader
      */
     URLClassPath getURLClassPath (URLClassLoader u);
+
+    /**
+     * Return the original application specified hostname of
+     * the given InetAddress object.
+     */
+    String getOriginalHostName(InetAddress ia);
 }
--- a/jdk/src/java.base/share/classes/sun/misc/ManagedLocalsThread.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/ManagedLocalsThread.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -48,6 +48,11 @@
         eraseThreadLocals();
     }
 
+    public ManagedLocalsThread(ThreadGroup group, Runnable target) {
+        super(group, target);
+        eraseThreadLocals();
+    }
+
     public ManagedLocalsThread(Runnable target, String name) {
         super(target, name);
         eraseThreadLocals();
--- a/jdk/src/java.base/share/classes/sun/misc/Unsafe.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/Unsafe.java	Wed Jul 05 20:42:36 2017 +0200
@@ -31,6 +31,8 @@
 import sun.reflect.CallerSensitive;
 import sun.reflect.Reflection;
 
+import jdk.internal.HotSpotIntrinsicCandidate;
+
 
 /**
  * A collection of methods for performing low-level, unsafe operations.
@@ -148,6 +150,7 @@
      * @throws RuntimeException No defined exceptions are thrown, not even
      *         {@link NullPointerException}
      */
+    @HotSpotIntrinsicCandidate
     public native int getInt(Object o, long offset);
 
     /**
@@ -170,12 +173,14 @@
      * @throws RuntimeException No defined exceptions are thrown, not even
      *         {@link NullPointerException}
      */
+    @HotSpotIntrinsicCandidate
     public native void putInt(Object o, long offset, int x);
 
     /**
      * Fetches a reference value from a given Java variable.
      * @see #getInt(Object, long)
      */
+    @HotSpotIntrinsicCandidate
     public native Object getObject(Object o, long offset);
 
     /**
@@ -188,35 +193,50 @@
      * are updated.
      * @see #putInt(Object, long, int)
      */
+    @HotSpotIntrinsicCandidate
     public native void putObject(Object o, long offset, Object x);
 
     /** @see #getInt(Object, long) */
+    @HotSpotIntrinsicCandidate
     public native boolean getBoolean(Object o, long offset);
     /** @see #putInt(Object, long, int) */
+    @HotSpotIntrinsicCandidate
     public native void    putBoolean(Object o, long offset, boolean x);
     /** @see #getInt(Object, long) */
+    @HotSpotIntrinsicCandidate
     public native byte    getByte(Object o, long offset);
     /** @see #putInt(Object, long, int) */
+    @HotSpotIntrinsicCandidate
     public native void    putByte(Object o, long offset, byte x);
     /** @see #getInt(Object, long) */
+    @HotSpotIntrinsicCandidate
     public native short   getShort(Object o, long offset);
     /** @see #putInt(Object, long, int) */
+    @HotSpotIntrinsicCandidate
     public native void    putShort(Object o, long offset, short x);
     /** @see #getInt(Object, long) */
+    @HotSpotIntrinsicCandidate
     public native char    getChar(Object o, long offset);
     /** @see #putInt(Object, long, int) */
+    @HotSpotIntrinsicCandidate
     public native void    putChar(Object o, long offset, char x);
     /** @see #getInt(Object, long) */
+    @HotSpotIntrinsicCandidate
     public native long    getLong(Object o, long offset);
     /** @see #putInt(Object, long, int) */
+    @HotSpotIntrinsicCandidate
     public native void    putLong(Object o, long offset, long x);
     /** @see #getInt(Object, long) */
+    @HotSpotIntrinsicCandidate
     public native float   getFloat(Object o, long offset);
     /** @see #putInt(Object, long, int) */
+    @HotSpotIntrinsicCandidate
     public native void    putFloat(Object o, long offset, float x);
     /** @see #getInt(Object, long) */
+    @HotSpotIntrinsicCandidate
     public native double  getDouble(Object o, long offset);
     /** @see #putInt(Object, long, int) */
+    @HotSpotIntrinsicCandidate
     public native void    putDouble(Object o, long offset, double x);
 
     // These read VM internal data.
@@ -257,6 +277,7 @@
      *
      * @see #allocateMemory
      */
+    @HotSpotIntrinsicCandidate
     public native byte    getByte(long address);
 
     /**
@@ -266,31 +287,44 @@
      *
      * @see #getByte(long)
      */
+    @HotSpotIntrinsicCandidate
     public native void    putByte(long address, byte x);
 
     /** @see #getByte(long) */
+    @HotSpotIntrinsicCandidate
     public native short   getShort(long address);
     /** @see #putByte(long, byte) */
+    @HotSpotIntrinsicCandidate
     public native void    putShort(long address, short x);
     /** @see #getByte(long) */
+    @HotSpotIntrinsicCandidate
     public native char    getChar(long address);
     /** @see #putByte(long, byte) */
+    @HotSpotIntrinsicCandidate
     public native void    putChar(long address, char x);
     /** @see #getByte(long) */
+    @HotSpotIntrinsicCandidate
     public native int     getInt(long address);
     /** @see #putByte(long, byte) */
+    @HotSpotIntrinsicCandidate
     public native void    putInt(long address, int x);
     /** @see #getByte(long) */
+    @HotSpotIntrinsicCandidate
     public native long    getLong(long address);
     /** @see #putByte(long, byte) */
+    @HotSpotIntrinsicCandidate
     public native void    putLong(long address, long x);
     /** @see #getByte(long) */
+    @HotSpotIntrinsicCandidate
     public native float   getFloat(long address);
     /** @see #putByte(long, byte) */
+    @HotSpotIntrinsicCandidate
     public native void    putFloat(long address, float x);
     /** @see #getByte(long) */
+    @HotSpotIntrinsicCandidate
     public native double  getDouble(long address);
     /** @see #putByte(long, byte) */
+    @HotSpotIntrinsicCandidate
     public native void    putDouble(long address, double x);
 
     /**
@@ -307,6 +341,7 @@
      *
      * @see #allocateMemory
      */
+    @HotSpotIntrinsicCandidate
     public native long getAddress(long address);
 
     /**
@@ -319,6 +354,7 @@
      *
      * @see #getAddress(long)
      */
+    @HotSpotIntrinsicCandidate
     public native void putAddress(long address, long x);
 
     /// wrappers for malloc, realloc, free:
@@ -406,6 +442,7 @@
      *
      * @since 1.7
      */
+    @HotSpotIntrinsicCandidate
     public native void copyMemory(Object srcBase, long srcOffset,
                                   Object destBase, long destOffset,
                                   long bytes);
@@ -651,6 +688,7 @@
      * Allocates an instance but does not run any constructor.
      * Initializes the class if it has not yet been.
      */
+    @HotSpotIntrinsicCandidate
     public native Object allocateInstance(Class<?> cls)
         throws InstantiationException;
 
@@ -666,6 +704,7 @@
      *
      * @return {@code true} if successful
      */
+    @HotSpotIntrinsicCandidate
     public final native boolean compareAndSwapObject(Object o, long offset,
                                                      Object expected,
                                                      Object x);
@@ -679,6 +718,7 @@
      *
      * @return {@code true} if successful
      */
+    @HotSpotIntrinsicCandidate
     public final native boolean compareAndSwapInt(Object o, long offset,
                                                   int expected,
                                                   int x);
@@ -692,6 +732,7 @@
      *
      * @return {@code true} if successful
      */
+    @HotSpotIntrinsicCandidate
     public final native boolean compareAndSwapLong(Object o, long offset,
                                                    long expected,
                                                    long x);
@@ -700,60 +741,78 @@
      * Fetches a reference value from a given Java variable, with volatile
      * load semantics. Otherwise identical to {@link #getObject(Object, long)}
      */
+    @HotSpotIntrinsicCandidate
     public native Object getObjectVolatile(Object o, long offset);
 
     /**
      * Stores a reference value into a given Java variable, with
      * volatile store semantics. Otherwise identical to {@link #putObject(Object, long, Object)}
      */
+    @HotSpotIntrinsicCandidate
     public native void    putObjectVolatile(Object o, long offset, Object x);
 
     /** Volatile version of {@link #getInt(Object, long)}  */
+    @HotSpotIntrinsicCandidate
     public native int     getIntVolatile(Object o, long offset);
 
     /** Volatile version of {@link #putInt(Object, long, int)}  */
+    @HotSpotIntrinsicCandidate
     public native void    putIntVolatile(Object o, long offset, int x);
 
     /** Volatile version of {@link #getBoolean(Object, long)}  */
+    @HotSpotIntrinsicCandidate
     public native boolean getBooleanVolatile(Object o, long offset);
 
     /** Volatile version of {@link #putBoolean(Object, long, boolean)}  */
+    @HotSpotIntrinsicCandidate
     public native void    putBooleanVolatile(Object o, long offset, boolean x);
 
     /** Volatile version of {@link #getByte(Object, long)}  */
+    @HotSpotIntrinsicCandidate
     public native byte    getByteVolatile(Object o, long offset);
 
     /** Volatile version of {@link #putByte(Object, long, byte)}  */
+    @HotSpotIntrinsicCandidate
     public native void    putByteVolatile(Object o, long offset, byte x);
 
     /** Volatile version of {@link #getShort(Object, long)}  */
+    @HotSpotIntrinsicCandidate
     public native short   getShortVolatile(Object o, long offset);
 
     /** Volatile version of {@link #putShort(Object, long, short)}  */
+    @HotSpotIntrinsicCandidate
     public native void    putShortVolatile(Object o, long offset, short x);
 
     /** Volatile version of {@link #getChar(Object, long)}  */
+    @HotSpotIntrinsicCandidate
     public native char    getCharVolatile(Object o, long offset);
 
     /** Volatile version of {@link #putChar(Object, long, char)}  */
+    @HotSpotIntrinsicCandidate
     public native void    putCharVolatile(Object o, long offset, char x);
 
     /** Volatile version of {@link #getLong(Object, long)}  */
+    @HotSpotIntrinsicCandidate
     public native long    getLongVolatile(Object o, long offset);
 
     /** Volatile version of {@link #putLong(Object, long, long)}  */
+    @HotSpotIntrinsicCandidate
     public native void    putLongVolatile(Object o, long offset, long x);
 
     /** Volatile version of {@link #getFloat(Object, long)}  */
+    @HotSpotIntrinsicCandidate
     public native float   getFloatVolatile(Object o, long offset);
 
     /** Volatile version of {@link #putFloat(Object, long, float)}  */
+    @HotSpotIntrinsicCandidate
     public native void    putFloatVolatile(Object o, long offset, float x);
 
     /** Volatile version of {@link #getDouble(Object, long)}  */
+    @HotSpotIntrinsicCandidate
     public native double  getDoubleVolatile(Object o, long offset);
 
     /** Volatile version of {@link #putDouble(Object, long, double)}  */
+    @HotSpotIntrinsicCandidate
     public native void    putDoubleVolatile(Object o, long offset, double x);
 
     /**
@@ -765,12 +824,15 @@
      *
      * Corresponds to C11 atomic_store_explicit(..., memory_order_release).
      */
+    @HotSpotIntrinsicCandidate
     public native void    putOrderedObject(Object o, long offset, Object x);
 
     /** Ordered/Lazy version of {@link #putIntVolatile(Object, long, int)}  */
+    @HotSpotIntrinsicCandidate
     public native void    putOrderedInt(Object o, long offset, int x);
 
     /** Ordered/Lazy version of {@link #putLongVolatile(Object, long, long)} */
+    @HotSpotIntrinsicCandidate
     public native void    putOrderedLong(Object o, long offset, long x);
 
     /**
@@ -785,6 +847,7 @@
      *
      * @param thread the thread to unpark.
      */
+    @HotSpotIntrinsicCandidate
     public native void unpark(Object thread);
 
     /**
@@ -798,6 +861,7 @@
      * because {@code unpark} is, so it would be strange to place it
      * elsewhere.
      */
+    @HotSpotIntrinsicCandidate
     public native void park(boolean isAbsolute, long time);
 
     /**
@@ -831,6 +895,7 @@
      * @return the previous value
      * @since 1.8
      */
+    @HotSpotIntrinsicCandidate
     public final int getAndAddInt(Object o, long offset, int delta) {
         int v;
         do {
@@ -850,6 +915,7 @@
      * @return the previous value
      * @since 1.8
      */
+    @HotSpotIntrinsicCandidate
     public final long getAndAddLong(Object o, long offset, long delta) {
         long v;
         do {
@@ -869,6 +935,7 @@
      * @return the previous value
      * @since 1.8
      */
+    @HotSpotIntrinsicCandidate
     public final int getAndSetInt(Object o, long offset, int newValue) {
         int v;
         do {
@@ -888,6 +955,7 @@
      * @return the previous value
      * @since 1.8
      */
+    @HotSpotIntrinsicCandidate
     public final long getAndSetLong(Object o, long offset, long newValue) {
         long v;
         do {
@@ -907,6 +975,7 @@
      * @return the previous value
      * @since 1.8
      */
+    @HotSpotIntrinsicCandidate
     public final Object getAndSetObject(Object o, long offset, Object newValue) {
         Object v;
         do {
@@ -928,6 +997,7 @@
      * provide a LoadLoad barrier also provide a LoadStore barrier for free.
      * @since 1.8
      */
+    @HotSpotIntrinsicCandidate
     public native void loadFence();
 
     /**
@@ -942,6 +1012,7 @@
      * provide a StoreStore barrier also provide a LoadStore barrier for free.
      * @since 1.8
      */
+    @HotSpotIntrinsicCandidate
     public native void storeFence();
 
     /**
@@ -953,6 +1024,7 @@
      * Corresponds to C11 atomic_thread_fence(memory_order_seq_cst).
      * @since 1.8
      */
+    @HotSpotIntrinsicCandidate
     public native void fullFence();
 
     /**
@@ -1010,6 +1082,7 @@
      *         {@link NullPointerException}
      * @since 1.9
      */
+    @HotSpotIntrinsicCandidate
     public final long getLongUnaligned(Object o, long offset) {
         if ((offset & 7) == 0) {
             return getLong(o, offset);
@@ -1048,6 +1121,7 @@
     }
 
     /** @see #getLongUnaligned(Object, long) */
+    @HotSpotIntrinsicCandidate
     public final int getIntUnaligned(Object o, long offset) {
         if ((offset & 3) == 0) {
             return getInt(o, offset);
@@ -1067,6 +1141,7 @@
     }
 
     /** @see #getLongUnaligned(Object, long) */
+    @HotSpotIntrinsicCandidate
     public final short getShortUnaligned(Object o, long offset) {
         if ((offset & 1) == 0) {
             return getShort(o, offset);
@@ -1081,9 +1156,11 @@
     }
 
     /** @see #getLongUnaligned(Object, long) */
+    @HotSpotIntrinsicCandidate
     public final char getCharUnaligned(Object o, long offset) {
         return (char)getShortUnaligned(o, offset);
     }
+
     /** @see #getLongUnaligned(Object, long, boolean) */
     public final char getCharUnaligned(Object o, long offset, boolean bigEndian) {
         return convEndian(bigEndian, getCharUnaligned(o, offset));
@@ -1117,6 +1194,7 @@
      *         {@link NullPointerException}
      * @since 1.9
      */
+    @HotSpotIntrinsicCandidate
     public final void putLongUnaligned(Object o, long offset, long x) {
         if ((offset & 7) == 0) {
             putLong(o, offset, x);
@@ -1142,6 +1220,7 @@
                          (byte)(x >>> 56));
         }
     }
+
     /**
      * As {@link #putLongUnaligned(Object, long, long)} but with an additional
      * argument which specifies the endianness of the value as stored in memory.
@@ -1158,6 +1237,7 @@
     }
 
     /** @see #putLongUnaligned(Object, long, long) */
+    @HotSpotIntrinsicCandidate
     public final void putIntUnaligned(Object o, long offset, int x) {
         if ((offset & 3) == 0) {
             putInt(o, offset, x);
@@ -1179,6 +1259,7 @@
     }
 
     /** @see #putLongUnaligned(Object, long, long) */
+    @HotSpotIntrinsicCandidate
     public final void putShortUnaligned(Object o, long offset, short x) {
         if ((offset & 1) == 0) {
             putShort(o, offset, x);
@@ -1194,6 +1275,7 @@
     }
 
     /** @see #putLongUnaligned(Object, long, long) */
+    @HotSpotIntrinsicCandidate
     public final void putCharUnaligned(Object o, long offset, char x) {
         putShortUnaligned(o, offset, (short)x);
     }
--- a/jdk/src/java.base/share/classes/sun/net/idn/StringPrep.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/net/idn/StringPrep.java	Wed Jul 05 20:42:36 2017 +0200
@@ -50,7 +50,6 @@
 import sun.text.Normalizer;
 import sun.text.normalizer.CharTrie;
 import sun.text.normalizer.Trie;
-import sun.text.normalizer.NormalizerImpl;
 import sun.text.normalizer.VersionInfo;
 import sun.text.normalizer.UCharacter;
 import sun.text.normalizer.UCharacterIterator;
@@ -227,7 +226,7 @@
         checkBiDi         = ((indexes[OPTIONS] & CHECK_BIDI_ON) > 0);
         sprepUniVer   = getVersionInfo(reader.getUnicodeVersion());
         normCorrVer   = getVersionInfo(indexes[NORM_CORRECTNS_LAST_UNI_VERSION]);
-        VersionInfo normUniVer = NormalizerImpl.getUnicodeVersion();
+        VersionInfo normUniVer = UCharacter.getUnicodeVersion();
         if(normUniVer.compareTo(sprepUniVer) < 0 && /* the Unicode version of SPREP file must be less than the Unicode Vesion of the normalization data */
            normUniVer.compareTo(normCorrVer) < 0 && /* the Unicode version of the NormalizationCorrections.txt file should be less than the Unicode Vesion of the normalization data */
            ((indexes[OPTIONS] & NORMALIZATION_ON) > 0) /* normalization turned on*/
@@ -354,7 +353,7 @@
             Normalizer.normalize(
                 src.toString(),
                 java.text.Normalizer.Form.NFKC,
-                Normalizer.UNICODE_3_2|NormalizerImpl.BEFORE_PRI_29));
+                Normalizer.UNICODE_3_2));
     }
     /*
     boolean isLabelSeparator(int ch){
--- a/jdk/src/java.base/share/classes/sun/net/util/URLUtil.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/net/util/URLUtil.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,7 +25,10 @@
 
 package sun.net.util;
 
+import java.io.IOException;
 import java.net.URL;
+import java.net.URLPermission;
+import java.security.Permission;
 
 /**
  * URL Utility class.
@@ -76,5 +79,26 @@
 
         return strForm.toString();
     }
+
+    public static Permission getConnectPermission(URL url) throws IOException {
+        String urlStringLowerCase = url.toString().toLowerCase();
+        if (urlStringLowerCase.startsWith("http:") || urlStringLowerCase.startsWith("https:")) {
+            return getURLConnectPermission(url);
+        } else if (urlStringLowerCase.startsWith("jar:http:") || urlStringLowerCase.startsWith("jar:https:")) {
+            String urlString = url.toString();
+            int bangPos = urlString.indexOf("!/");
+            urlString = urlString.substring(4, bangPos > -1 ? bangPos : urlString.length());
+            URL u = new URL(urlString);
+            return getURLConnectPermission(u);
+            // If protocol is HTTP or HTTPS than use URLPermission object
+        } else {
+            return url.openConnection().getPermission();
+        }
+    }
+
+    private static Permission getURLConnectPermission(URL url) {
+        String urlString = url.getProtocol() + "://" + url.getAuthority() + url.getPath();
+        return new URLPermission(urlString);
+    }
 }
 
--- a/jdk/src/java.base/share/classes/sun/nio/cs/ISO_8859_1.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/nio/cs/ISO_8859_1.java	Wed Jul 05 20:42:36 2017 +0200
@@ -32,6 +32,9 @@
 import java.nio.charset.CharsetEncoder;
 import java.nio.charset.CoderResult;
 import java.util.Arrays;
+import java.util.Objects;
+
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 class ISO_8859_1
     extends Charset
@@ -147,9 +150,16 @@
 
         private final Surrogate.Parser sgp = new Surrogate.Parser();
 
-        // JVM may replace this method with intrinsic code.
+        // Method possible replaced with a compiler intrinsic.
         private static int encodeISOArray(char[] sa, int sp,
-                                          byte[] da, int dp, int len)
+                                          byte[] da, int dp, int len) {
+            encodeISOArrayCheck(sa, sp, da, dp, len);
+            return implEncodeISOArray(sa, sp, da, dp, len);
+        }
+
+        @HotSpotIntrinsicCandidate
+        private static int implEncodeISOArray(char[] sa, int sp,
+                                              byte[] da, int dp, int len)
         {
             int i = 0;
             for (; i < len; i++) {
@@ -161,6 +171,34 @@
             return i;
         }
 
+        private static void encodeISOArrayCheck(char[] sa, int sp,
+                                                byte[] da, int dp, int len) {
+            if (len <= 0) {
+                return;  // not an error because encodeISOArrayImpl won't execute if len <= 0
+            }
+
+            Objects.requireNonNull(sa);
+            Objects.requireNonNull(da);
+
+            if (sp < 0 || sp >= sa.length) {
+                throw new ArrayIndexOutOfBoundsException(sp);
+            }
+
+            if (dp < 0 || dp >= da.length) {
+                throw new ArrayIndexOutOfBoundsException(dp);
+            }
+
+            int endIndexSP = sp + len - 1;
+            if (endIndexSP < 0 || endIndexSP >= sa.length) {
+                throw new ArrayIndexOutOfBoundsException(endIndexSP);
+            }
+
+            int endIndexDP = dp + len - 1;
+            if (endIndexDP < 0 || endIndexDP >= da.length) {
+                throw new ArrayIndexOutOfBoundsException(endIndexDP);
+            }
+        }
+
         private CoderResult encodeArrayLoop(CharBuffer src,
                                             ByteBuffer dst)
         {
--- a/jdk/src/java.base/share/classes/sun/reflect/Reflection.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/reflect/Reflection.java	Wed Jul 05 20:42:36 2017 +0200
@@ -28,6 +28,7 @@
 import java.lang.reflect.*;
 import java.util.HashMap;
 import java.util.Map;
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 /** Common utility routines used by both java.lang and
     java.lang.reflect */
@@ -56,6 +57,7 @@
         ignoring frames associated with java.lang.reflect.Method.invoke()
         and its implementation. */
     @CallerSensitive
+    @HotSpotIntrinsicCandidate
     public static native Class<?> getCallerClass();
 
     /**
@@ -74,6 +76,7 @@
         to compatibility reasons; see 4471811. Only the values of the
         low 13 bits (i.e., a mask of 0x1FFF) are guaranteed to be
         valid. */
+    @HotSpotIntrinsicCandidate
     public static native int getClassAccessFlags(Class<?> c);
 
     /** A quick "fast-path" check to try to avoid getCallerClass()
--- a/jdk/src/java.base/share/classes/sun/security/pkcs12/PKCS12KeyStore.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/pkcs12/PKCS12KeyStore.java	Wed Jul 05 20:42:36 2017 +0200
@@ -2059,7 +2059,7 @@
                         "(MAC algorithm: " + m.getAlgorithm() + ")");
                 }
 
-                if (!Arrays.equals(macData.getDigest(), macResult)) {
+                if (!MessageDigest.isEqual(macData.getDigest(), macResult)) {
                    throw new SecurityException("Failed PKCS12" +
                                         " integrity checking");
                 }
--- a/jdk/src/java.base/share/classes/sun/security/provider/DigestBase.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/provider/DigestBase.java	Wed Jul 05 20:42:36 2017 +0200
@@ -28,6 +28,9 @@
 import java.security.MessageDigestSpi;
 import java.security.DigestException;
 import java.security.ProviderException;
+import java.util.Objects;
+
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 /**
  * Common base message digest implementation for the Sun provider.
@@ -136,12 +139,36 @@
 
     // compress complete blocks
     private int implCompressMultiBlock(byte[] b, int ofs, int limit) {
+        implCompressMultiBlockCheck(b, ofs, limit);
+        return implCompressMultiBlock0(b, ofs, limit);
+    }
+
+    @HotSpotIntrinsicCandidate
+    private int implCompressMultiBlock0(byte[] b, int ofs, int limit) {
         for (; ofs <= limit; ofs += blockSize) {
             implCompress(b, ofs);
         }
         return ofs;
     }
 
+    private void implCompressMultiBlockCheck(byte[] b, int ofs, int limit) {
+        if (limit < 0) {
+            return;  // not an error because implCompressMultiBlockImpl won't execute if limit < 0
+                     // and an exception is thrown if ofs < 0.
+        }
+
+        Objects.requireNonNull(b);
+
+        if (ofs < 0 || ofs >= b.length) {
+            throw new ArrayIndexOutOfBoundsException(ofs);
+        }
+
+        int endIndex = (limit / blockSize) * blockSize  + blockSize - 1;
+        if (endIndex >= b.length) {
+            throw new ArrayIndexOutOfBoundsException(endIndex);
+        }
+    }
+
     // reset this object. See JCA doc.
     protected final void engineReset() {
         if (bytesProcessed == 0) {
--- a/jdk/src/java.base/share/classes/sun/security/provider/SHA.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/provider/SHA.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,7 +25,10 @@
 
 package sun.security.provider;
 
+import java.util.Objects;
+
 import static sun.security.provider.ByteArrayAccess.*;
+import jdk.internal.HotSpotIntrinsicCandidate;
 
 /**
  * This class implements the Secure Hash Algorithm (SHA) developed by
@@ -114,8 +117,27 @@
      * "old" NIST Secure Hash Algorithm.
      */
     void implCompress(byte[] buf, int ofs) {
+        implCompressCheck(buf, ofs);
+        implCompress0(buf, ofs);
+    }
+
+    private void implCompressCheck(byte[] buf, int ofs) {
+        Objects.requireNonNull(buf);
+
+        // The checks performed by the method 'b2iBig64'
+        // are sufficient for the case when the method
+        // 'implCompressImpl' is replaced with a compiler
+        // intrinsic.
         b2iBig64(buf, ofs, W);
+    }
 
+    // The method 'implCompressImpl seems not to use its parameters.
+    // The method can, however, be replaced with a compiler intrinsic
+    // that operates directly on the array 'buf' (starting from
+    // offset 'ofs') and not on array 'W', therefore 'buf' and 'ofs'
+    // must be passed as parameter to the method.
+    @HotSpotIntrinsicCandidate
+    private void implCompress0(byte[] buf, int ofs) {
         // The first 16 ints have the byte stream, compute the rest of
         // the buffer
         for (int t = 16; t <= 79; t++) {
--- a/jdk/src/java.base/share/classes/sun/security/provider/SHA2.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/provider/SHA2.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,6 +25,9 @@
 
 package sun.security.provider;
 
+import java.util.Objects;
+
+import jdk.internal.HotSpotIntrinsicCandidate;
 import static sun.security.provider.ByteArrayAccess.*;
 
 /**
@@ -186,8 +189,27 @@
      * Process the current block to update the state variable state.
      */
     void implCompress(byte[] buf, int ofs) {
+        implCompressCheck(buf, ofs);
+        implCompress0(buf, ofs);
+    }
+
+    private void implCompressCheck(byte[] buf, int ofs) {
+        Objects.requireNonNull(buf);
+
+        // The checks performed by the method 'b2iBig64'
+        // are sufficient for the case when the method
+        // 'implCompressImpl' is replaced with a compiler
+        // intrinsic.
         b2iBig64(buf, ofs, W);
+    }
 
+    // The method 'implCompressImpl' seems not to use its parameters.
+    // The method can, however, be replaced with a compiler intrinsic
+    // that operates directly on the array 'buf' (starting from
+    // offset 'ofs') and not on array 'W', therefore 'buf' and 'ofs'
+    // must be passed as parameter to the method.
+    @HotSpotIntrinsicCandidate
+    private void implCompress0(byte[] buf, int ofs) {
         // The first 16 ints are from the byte stream, compute the rest of
         // the W[]'s
         for (int t = 16; t < ITERATION; t++) {
--- a/jdk/src/java.base/share/classes/sun/security/provider/SHA5.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/provider/SHA5.java	Wed Jul 05 20:42:36 2017 +0200
@@ -26,8 +26,10 @@
 package sun.security.provider;
 
 import java.security.*;
+import java.util.Objects;
 import java.math.BigInteger;
 
+import jdk.internal.HotSpotIntrinsicCandidate;
 import static sun.security.provider.ByteArrayAccess.*;
 
 /**
@@ -205,8 +207,27 @@
      * "old" NIST Secure Hash Algorithm.
      */
     final void implCompress(byte[] buf, int ofs) {
+        implCompressCheck(buf, ofs);
+        implCompress0(buf, ofs);
+    }
+
+    private void implCompressCheck(byte[] buf, int ofs) {
+        Objects.requireNonNull(buf);
+
+        // The checks performed by the method 'b2iBig128'
+        // are sufficient for the case when the method
+        // 'implCompressImpl' is replaced with a compiler
+        // intrinsic.
         b2lBig128(buf, ofs, W);
+    }
 
+    // The method 'implCompressImpl' seems not to use its parameters.
+    // The method can, however, be replaced with a compiler intrinsic
+    // that operates directly on the array 'buf' (starting from
+    // offset 'ofs') and not on array 'W', therefore 'buf' and 'ofs'
+    // must be passed as parameter to the method.
+    @HotSpotIntrinsicCandidate
+    private final void implCompress0(byte[] buf, int ofs) {
         // The first 16 longs are from the byte stream, compute the rest of
         // the W[]'s
         for (int t = 16; t < ITERATION; t++) {
--- a/jdk/src/java.base/share/classes/sun/security/provider/certpath/OCSPResponse.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/provider/certpath/OCSPResponse.java	Wed Jul 05 20:42:36 2017 +0200
@@ -151,8 +151,8 @@
     private static final int DEFAULT_MAX_CLOCK_SKEW = 900000;
 
     /**
-     * Integer value indicating the maximum allowable clock skew, in seconds,
-     * to be used for the OCSP check.
+     * Integer value indicating the maximum allowable clock skew,
+     * in milliseconds, to be used for the OCSP check.
      */
     private static final int MAX_CLOCK_SKEW = initializeClockSkew();
 
@@ -585,13 +585,14 @@
                 "Unable to verify OCSP Response's signature");
         }
 
-        // Check freshness of OCSPResponse
         if (nonce != null) {
             if (responseNonce != null && !Arrays.equals(nonce, responseNonce)) {
                 throw new CertPathValidatorException("Nonces don't match");
             }
         }
 
+        // Check freshness of OCSPResponse
+
         long now = (date == null) ? System.currentTimeMillis() : date.getTime();
         Date nowPlusSkew = new Date(now + MAX_CLOCK_SKEW);
         Date nowMinusSkew = new Date(now - MAX_CLOCK_SKEW);
@@ -601,13 +602,18 @@
                 if (sr.nextUpdate != null) {
                     until = " until " + sr.nextUpdate;
                 }
-                debug.println("Response's validity interval is from " +
+                debug.println("OCSP response validity interval is from " +
                               sr.thisUpdate + until);
+                debug.println("Checking validity of OCSP response on: " +
+                    new Date(now));
             }
 
-            // Check that the test date is within the validity interval
-            if ((sr.thisUpdate != null && nowPlusSkew.before(sr.thisUpdate)) ||
-                (sr.nextUpdate != null && nowMinusSkew.after(sr.nextUpdate)))
+            // Check that the test date is within the validity interval:
+            //   [ thisUpdate - MAX_CLOCK_SKEW,
+            //     MAX(thisUpdate, nextUpdate) + MAX_CLOCK_SKEW ]
+            if (nowPlusSkew.before(sr.thisUpdate) ||
+                nowMinusSkew.after(
+                    sr.nextUpdate != null ? sr.nextUpdate : sr.thisUpdate))
             {
                 throw new CertPathValidatorException(
                                       "Response is unreliable: its validity " +
--- a/jdk/src/java.base/share/classes/sun/security/provider/certpath/PKIXCertPathValidator.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/provider/certpath/PKIXCertPathValidator.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 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
@@ -159,12 +159,19 @@
                                                         ValidatorParams params)
         throws CertPathValidatorException
     {
+        // check if anchor is untrusted
+        UntrustedChecker untrustedChecker = new UntrustedChecker();
+        X509Certificate anchorCert = anchor.getTrustedCert();
+        if (anchorCert != null) {
+            untrustedChecker.check(anchorCert);
+        }
+
         int certPathLen = params.certificates().size();
 
         // create PKIXCertPathCheckers
         List<PKIXCertPathChecker> certPathCheckers = new ArrayList<>();
         // add standard checkers that we will be using
-        certPathCheckers.add(new UntrustedChecker());
+        certPathCheckers.add(untrustedChecker);
         certPathCheckers.add(new AlgorithmChecker(anchor));
         certPathCheckers.add(new KeyChecker(certPathLen,
                                             params.targetCertConstraints()));
--- a/jdk/src/java.base/share/classes/sun/security/rsa/RSASignature.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/rsa/RSASignature.java	Wed Jul 05 20:42:36 2017 +0200
@@ -27,7 +27,6 @@
 
 import java.io.IOException;
 import java.nio.ByteBuffer;
-import java.util.Arrays;
 
 import java.security.*;
 import java.security.interfaces.*;
@@ -194,7 +193,7 @@
             byte[] decrypted = RSACore.rsa(sigBytes, publicKey);
             byte[] unpadded = padding.unpad(decrypted);
             byte[] decodedDigest = decodeSignature(digestOID, unpadded);
-            return Arrays.equals(digest, decodedDigest);
+            return MessageDigest.isEqual(digest, decodedDigest);
         } catch (javax.crypto.BadPaddingException e) {
             // occurs if the app has used the wrong RSA public key
             // or if sigBytes is invalid
--- a/jdk/src/java.base/share/classes/sun/security/ssl/CipherSuite.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/ssl/CipherSuite.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1008,7 +1008,7 @@
          * 1. Prefer Suite B compliant cipher suites, see RFC6460 (To be
          *    changed later, see below).
          * 2. Prefer the stronger bulk cipher, in the order of AES_256(GCM),
-         *    AES_128(GCM), AES_256, AES_128, 3DES-EDE, RC-4.
+         *    AES_128(GCM), AES_256, AES_128, 3DES-EDE.
          * 3. Prefer the stronger MAC algorithm, in the order of SHA384,
          *    SHA256, SHA, MD5.
          * 4. Prefer the better performance of key exchange and digital
@@ -1143,20 +1143,6 @@
         add("SSL_DHE_DSS_WITH_3DES_EDE_CBC_SHA",        0x0013, --p,
             K_DHE_DSS,     B_3DES,        M_SHA,    N);
 
-        // RC-4
-        add("TLS_ECDHE_ECDSA_WITH_RC4_128_SHA",         0xC007, --p,
-            K_ECDHE_ECDSA, B_RC4_128,     M_SHA,    N);
-        add("TLS_ECDHE_RSA_WITH_RC4_128_SHA",           0xC011, --p,
-            K_ECDHE_RSA,   B_RC4_128,     M_SHA,    N);
-        add("SSL_RSA_WITH_RC4_128_SHA",                 0x0005, --p,
-            K_RSA,         B_RC4_128,     M_SHA,    N);
-        add("TLS_ECDH_ECDSA_WITH_RC4_128_SHA",          0xC002, --p,
-            K_ECDH_ECDSA,  B_RC4_128,     M_SHA,    N);
-        add("TLS_ECDH_RSA_WITH_RC4_128_SHA",            0xC00C, --p,
-            K_ECDH_RSA,    B_RC4_128,     M_SHA,    N);
-        add("SSL_RSA_WITH_RC4_128_MD5",                 0x0004, --p,
-            K_RSA,         B_RC4_128,     M_MD5,    N);
-
         // Renegotiation protection request Signalling Cipher Suite Value (SCSV)
         add("TLS_EMPTY_RENEGOTIATION_INFO_SCSV",        0x00ff, --p,
             K_SCSV,        B_NULL,        M_NULL,   T);
@@ -1206,6 +1192,20 @@
         add("SSL_DH_anon_WITH_3DES_EDE_CBC_SHA",        0x001b, --p,
             K_DH_ANON,     B_3DES,        M_SHA,    N);
 
+        // RC-4
+        add("TLS_ECDHE_ECDSA_WITH_RC4_128_SHA",         0xC007, --p,
+            K_ECDHE_ECDSA, B_RC4_128,     M_SHA,    N);
+        add("TLS_ECDHE_RSA_WITH_RC4_128_SHA",           0xC011, --p,
+            K_ECDHE_RSA,   B_RC4_128,     M_SHA,    N);
+        add("SSL_RSA_WITH_RC4_128_SHA",                 0x0005, --p,
+            K_RSA,         B_RC4_128,     M_SHA,    N);
+        add("TLS_ECDH_ECDSA_WITH_RC4_128_SHA",          0xC002, --p,
+            K_ECDH_ECDSA,  B_RC4_128,     M_SHA,    N);
+        add("TLS_ECDH_RSA_WITH_RC4_128_SHA",            0xC00C, --p,
+            K_ECDH_RSA,    B_RC4_128,     M_SHA,    N);
+        add("SSL_RSA_WITH_RC4_128_MD5",                 0x0004, --p,
+            K_RSA,         B_RC4_128,     M_MD5,    N);
+
         add("TLS_ECDH_anon_WITH_RC4_128_SHA",           0xC016, --p,
             K_ECDH_ANON,   B_RC4_128,     M_SHA,    N);
         add("SSL_DH_anon_WITH_RC4_128_MD5",             0x0018, --p,
--- a/jdk/src/java.base/share/classes/sun/security/ssl/ClientHandshaker.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/ssl/ClientHandshaker.java	Wed Jul 05 20:42:36 2017 +0200
@@ -542,7 +542,7 @@
                         0, clientVerifyData.length);
                 System.arraycopy(serverVerifyData, 0, verifyData,
                         clientVerifyData.length, serverVerifyData.length);
-                if (!Arrays.equals(verifyData,
+                if (!MessageDigest.isEqual(verifyData,
                                 serverHelloRI.getRenegotiatedConnection())) {
                     fatalSE(Alerts.alert_handshake_failure,
                         "Incorrect verify data in ServerHello " +
@@ -723,6 +723,14 @@
             // NOTREACHED
         }
         ephemeralServerKey = mesg.getPublicKey();
+
+        // check constraints of RSA PublicKey
+        if (!algorithmConstraints.permits(
+            EnumSet.of(CryptoPrimitive.KEY_AGREEMENT), ephemeralServerKey)) {
+
+            throw new SSLHandshakeException("RSA ServerKeyExchange " +
+                    "does not comply to algorithm constraints");
+        }
     }
 
     /*
@@ -739,6 +747,9 @@
         dh = new DHCrypt(mesg.getModulus(), mesg.getBase(),
                                             sslContext.getSecureRandom());
         serverDH = mesg.getServerPublicKey();
+
+        // check algorithm constraints
+        dh.checkConstraints(algorithmConstraints, serverDH);
     }
 
     private void serverKeyExchange(ECDH_ServerKeyExchange mesg)
@@ -749,6 +760,14 @@
         ECPublicKey key = mesg.getPublicKey();
         ecdh = new ECDHCrypt(key.getParams(), sslContext.getSecureRandom());
         ephemeralServerKey = key;
+
+        // check constraints of EC PublicKey
+        if (!algorithmConstraints.permits(
+            EnumSet.of(CryptoPrimitive.KEY_AGREEMENT), ephemeralServerKey)) {
+
+            throw new SSLHandshakeException("ECDH ServerKeyExchange " +
+                    "does not comply to algorithm constraints");
+        }
     }
 
     /*
--- a/jdk/src/java.base/share/classes/sun/security/ssl/DHCrypt.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/ssl/DHCrypt.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1996, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1996, 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
@@ -34,6 +34,7 @@
 import javax.crypto.KeyAgreement;
 import javax.crypto.interfaces.DHPublicKey;
 import javax.crypto.spec.*;
+import java.util.EnumSet;
 
 import sun.security.util.KeyUtil;
 
@@ -216,6 +217,28 @@
         }
     }
 
+    // Check constraints of the specified DH public key.
+    void checkConstraints(AlgorithmConstraints constraints,
+            BigInteger peerPublicValue) throws SSLHandshakeException {
+
+        try {
+            KeyFactory kf = JsseJce.getKeyFactory("DiffieHellman");
+            DHPublicKeySpec spec =
+                        new DHPublicKeySpec(peerPublicValue, modulus, base);
+            DHPublicKey publicKey = (DHPublicKey)kf.generatePublic(spec);
+
+            // check constraints of DHPublicKey
+            if (!constraints.permits(
+                    EnumSet.of(CryptoPrimitive.KEY_AGREEMENT), publicKey)) {
+                throw new SSLHandshakeException(
+                    "DHPublicKey does not comply to algorithm constraints");
+            }
+        } catch (GeneralSecurityException gse) {
+            throw (SSLHandshakeException) new SSLHandshakeException(
+                    "Could not generate DHPublicKey").initCause(gse);
+        }
+    }
+
     // Generate and validate DHPublicKeySpec
     private DHPublicKeySpec generateDHPublicKeySpec(KeyPairGenerator kpg)
             throws GeneralSecurityException {
--- a/jdk/src/java.base/share/classes/sun/security/ssl/ECDHCrypt.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/ssl/ECDHCrypt.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2006, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2006, 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
@@ -29,6 +29,7 @@
 import java.security.interfaces.ECPublicKey;
 import java.security.spec.*;
 
+import java.util.EnumSet;
 import javax.crypto.SecretKey;
 import javax.crypto.KeyAgreement;
 import javax.net.ssl.SSLHandshakeException;
@@ -88,8 +89,11 @@
         return publicKey;
     }
 
-    // called by ClientHandshaker with either the server's static or ephemeral public key
-    SecretKey getAgreedSecret(PublicKey peerPublicKey) throws SSLHandshakeException {
+    // called by ClientHandshaker with either the server's static or
+    // ephemeral public key
+    SecretKey getAgreedSecret(
+            PublicKey peerPublicKey) throws SSLHandshakeException {
+
         try {
             KeyAgreement ka = JsseJce.getKeyAgreement("ECDH");
             ka.init(privateKey);
@@ -102,10 +106,13 @@
     }
 
     // called by ServerHandshaker
-    SecretKey getAgreedSecret(byte[] encodedPoint) throws SSLHandshakeException {
+    SecretKey getAgreedSecret(
+            byte[] encodedPoint) throws SSLHandshakeException {
+
         try {
             ECParameterSpec params = publicKey.getParams();
-            ECPoint point = JsseJce.decodePoint(encodedPoint, params.getCurve());
+            ECPoint point =
+                    JsseJce.decodePoint(encodedPoint, params.getCurve());
             KeyFactory kf = JsseJce.getKeyFactory("EC");
             ECPublicKeySpec spec = new ECPublicKeySpec(point, params);
             PublicKey peerPublicKey = kf.generatePublic(spec);
@@ -116,4 +123,30 @@
         }
     }
 
+    // Check constraints of the specified EC public key.
+    void checkConstraints(AlgorithmConstraints constraints,
+            byte[] encodedPoint) throws SSLHandshakeException {
+
+        try {
+
+            ECParameterSpec params = publicKey.getParams();
+            ECPoint point =
+                    JsseJce.decodePoint(encodedPoint, params.getCurve());
+            ECPublicKeySpec spec = new ECPublicKeySpec(point, params);
+
+            KeyFactory kf = JsseJce.getKeyFactory("EC");
+            ECPublicKey publicKey = (ECPublicKey)kf.generatePublic(spec);
+
+            // check constraints of ECPublicKey
+            if (!constraints.permits(
+                    EnumSet.of(CryptoPrimitive.KEY_AGREEMENT), publicKey)) {
+                throw new SSLHandshakeException(
+                    "ECPublicKey does not comply to algorithm constraints");
+            }
+        } catch (GeneralSecurityException | java.io.IOException e) {
+            throw (SSLHandshakeException) new SSLHandshakeException(
+                    "Could not generate ECPublicKey").initCause(e);
+        }
+    }
+
 }
--- a/jdk/src/java.base/share/classes/sun/security/ssl/HandshakeMessage.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/ssl/HandshakeMessage.java	Wed Jul 05 20:42:36 2017 +0200
@@ -2040,7 +2040,7 @@
      */
     boolean verify(HandshakeHash handshakeHash, int sender, SecretKey master) {
         byte[] myFinished = getFinished(handshakeHash, sender, master);
-        return Arrays.equals(myFinished, verifyData);
+        return MessageDigest.isEqual(myFinished, verifyData);
     }
 
     /*
--- a/jdk/src/java.base/share/classes/sun/security/ssl/Handshaker.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/ssl/Handshaker.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1996, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1996, 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
@@ -87,7 +87,7 @@
     String                      identificationProtocol;
 
     // The cryptographic algorithm constraints
-    private AlgorithmConstraints    algorithmConstraints = null;
+    AlgorithmConstraints        algorithmConstraints = null;
 
     // Local supported signature and algorithms
     Collection<SignatureAndHashAlgorithm> localSupportedSignAlgs;
--- a/jdk/src/java.base/share/classes/sun/security/ssl/SSLAlgorithmConstraints.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/ssl/SSLAlgorithmConstraints.java	Wed Jul 05 20:42:36 2017 +0200
@@ -34,9 +34,9 @@
 import java.security.Key;
 
 import java.util.Set;
-import java.util.HashSet;
 
 import sun.security.util.DisabledAlgorithmConstraints;
+import static sun.security.util.DisabledAlgorithmConstraints.*;
 import sun.security.ssl.CipherSuite.*;
 
 /**
@@ -46,10 +46,15 @@
  * for the syntax of the disabled algorithm string.
  */
 final class SSLAlgorithmConstraints implements AlgorithmConstraints {
+
     private final static AlgorithmConstraints tlsDisabledAlgConstraints =
-            new TLSDisabledAlgConstraints();
+            new DisabledAlgorithmConstraints(PROPERTY_TLS_DISABLED_ALGS,
+                    new SSLAlgorithmDecomposer());
+
     private final static AlgorithmConstraints x509DisabledAlgConstraints =
-            new X509DisabledAlgConstraints();
+            new DisabledAlgorithmConstraints(PROPERTY_CERTPATH_DISABLED_ALGS,
+                    new SSLAlgorithmDecomposer(true));
+
     private AlgorithmConstraints userAlgConstraints = null;
     private AlgorithmConstraints peerAlgConstraints = null;
 
@@ -266,213 +271,4 @@
             return permits(primitives, algorithm, parameters);
         }
     }
-
-    static private class BasicDisabledAlgConstraints
-            extends DisabledAlgorithmConstraints {
-        BasicDisabledAlgConstraints(String propertyName) {
-            super(propertyName);
-        }
-
-        protected Set<String> decomposes(KeyExchange keyExchange,
-                        boolean forCertPathOnly) {
-            Set<String> components = new HashSet<>();
-            switch (keyExchange) {
-                case K_NULL:
-                    if (!forCertPathOnly) {
-                        components.add("NULL");
-                    }
-                    break;
-                case K_RSA:
-                    components.add("RSA");
-                    break;
-                case K_RSA_EXPORT:
-                    components.add("RSA");
-                    components.add("RSA_EXPORT");
-                    break;
-                case K_DH_RSA:
-                    components.add("RSA");
-                    components.add("DH");
-                    components.add("DiffieHellman");
-                    components.add("DH_RSA");
-                    break;
-                case K_DH_DSS:
-                    components.add("DSA");
-                    components.add("DSS");
-                    components.add("DH");
-                    components.add("DiffieHellman");
-                    components.add("DH_DSS");
-                    break;
-                case K_DHE_DSS:
-                    components.add("DSA");
-                    components.add("DSS");
-                    components.add("DH");
-                    components.add("DHE");
-                    components.add("DiffieHellman");
-                    components.add("DHE_DSS");
-                    break;
-                case K_DHE_RSA:
-                    components.add("RSA");
-                    components.add("DH");
-                    components.add("DHE");
-                    components.add("DiffieHellman");
-                    components.add("DHE_RSA");
-                    break;
-                case K_DH_ANON:
-                    if (!forCertPathOnly) {
-                        components.add("ANON");
-                        components.add("DH");
-                        components.add("DiffieHellman");
-                        components.add("DH_ANON");
-                    }
-                    break;
-                case K_ECDH_ECDSA:
-                    components.add("ECDH");
-                    components.add("ECDSA");
-                    components.add("ECDH_ECDSA");
-                    break;
-                case K_ECDH_RSA:
-                    components.add("ECDH");
-                    components.add("RSA");
-                    components.add("ECDH_RSA");
-                    break;
-                case K_ECDHE_ECDSA:
-                    components.add("ECDHE");
-                    components.add("ECDSA");
-                    components.add("ECDHE_ECDSA");
-                    break;
-                case K_ECDHE_RSA:
-                    components.add("ECDHE");
-                    components.add("RSA");
-                    components.add("ECDHE_RSA");
-                    break;
-                case K_ECDH_ANON:
-                    if (!forCertPathOnly) {
-                        components.add("ECDH");
-                        components.add("ANON");
-                        components.add("ECDH_ANON");
-                    }
-                    break;
-                default:
-                    if (ClientKeyExchangeService.find(keyExchange.name) != null) {
-                        if (!forCertPathOnly) {
-                            components.add(keyExchange.name);
-                        }
-                    }
-                    // otherwise ignore
-            }
-
-            return components;
-        }
-
-        protected Set<String> decomposes(BulkCipher bulkCipher) {
-            Set<String> components = new HashSet<>();
-
-            if (bulkCipher.transformation != null) {
-                components.addAll(super.decomposes(bulkCipher.transformation));
-            }
-
-            return components;
-        }
-
-        protected Set<String> decomposes(MacAlg macAlg) {
-            Set<String> components = new HashSet<>();
-
-            if (macAlg == CipherSuite.MacAlg.M_MD5) {
-                components.add("MD5");
-                components.add("HmacMD5");
-            } else if (macAlg == CipherSuite.MacAlg.M_SHA) {
-                components.add("SHA1");
-                components.add("SHA-1");
-                components.add("HmacSHA1");
-            } else if (macAlg == CipherSuite.MacAlg.M_SHA256) {
-                components.add("SHA256");
-                components.add("SHA-256");
-                components.add("HmacSHA256");
-            } else if (macAlg == CipherSuite.MacAlg.M_SHA384) {
-                components.add("SHA384");
-                components.add("SHA-384");
-                components.add("HmacSHA384");
-            }
-
-            return components;
-        }
-    }
-
-    static private class TLSDisabledAlgConstraints
-            extends BasicDisabledAlgConstraints {
-
-        TLSDisabledAlgConstraints() {
-            super(DisabledAlgorithmConstraints.PROPERTY_TLS_DISABLED_ALGS);
-        }
-
-        @Override
-        protected Set<String> decomposes(String algorithm) {
-            if (algorithm.startsWith("SSL_") || algorithm.startsWith("TLS_")) {
-                CipherSuite cipherSuite = null;
-                try {
-                    cipherSuite = CipherSuite.valueOf(algorithm);
-                } catch (IllegalArgumentException iae) {
-                    // ignore: unknown or unsupported ciphersuite
-                }
-
-                if (cipherSuite != null) {
-                    Set<String> components = new HashSet<>();
-
-                    if(cipherSuite.keyExchange != null) {
-                        components.addAll(
-                            decomposes(cipherSuite.keyExchange, false));
-                    }
-
-                    if (cipherSuite.cipher != null) {
-                        components.addAll(decomposes(cipherSuite.cipher));
-                    }
-
-                    if (cipherSuite.macAlg != null) {
-                        components.addAll(decomposes(cipherSuite.macAlg));
-                    }
-
-                    return components;
-                }
-            }
-
-            return super.decomposes(algorithm);
-        }
-    }
-
-    static private class X509DisabledAlgConstraints
-            extends BasicDisabledAlgConstraints {
-
-        X509DisabledAlgConstraints() {
-            super(DisabledAlgorithmConstraints.PROPERTY_CERTPATH_DISABLED_ALGS);
-        }
-
-        @Override
-        protected Set<String> decomposes(String algorithm) {
-            if (algorithm.startsWith("SSL_") || algorithm.startsWith("TLS_")) {
-                CipherSuite cipherSuite = null;
-                try {
-                    cipherSuite = CipherSuite.valueOf(algorithm);
-                } catch (IllegalArgumentException iae) {
-                    // ignore: unknown or unsupported ciphersuite
-                }
-
-                if (cipherSuite != null) {
-                    Set<String> components = new HashSet<>();
-
-                    if(cipherSuite.keyExchange != null) {
-                        components.addAll(
-                            decomposes(cipherSuite.keyExchange, true));
-                    }
-
-                    // Certification path algorithm constraints do not apply
-                    // to cipherSuite.cipher and cipherSuite.macAlg.
-
-                    return components;
-                }
-            }
-
-            return super.decomposes(algorithm);
-        }
-    }
 }
-
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/sun/security/ssl/SSLAlgorithmDecomposer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,258 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package sun.security.ssl;
+
+import java.util.HashSet;
+import java.util.Set;
+import sun.security.util.AlgorithmDecomposer;
+import static sun.security.ssl.CipherSuite.*;
+import static sun.security.ssl.CipherSuite.KeyExchange.*;
+
+/**
+ * The class decomposes standard SSL/TLS cipher suites into sub-elements.
+ */
+class SSLAlgorithmDecomposer extends AlgorithmDecomposer {
+
+    // indicates that only certification path algorithms need to be used
+    private final boolean onlyX509;
+
+    SSLAlgorithmDecomposer(boolean onlyX509) {
+        this.onlyX509 = onlyX509;
+    }
+
+    SSLAlgorithmDecomposer() {
+        this(false);
+    }
+
+    private Set<String> decomposes(CipherSuite.KeyExchange keyExchange) {
+        Set<String> components = new HashSet<>();
+        switch (keyExchange) {
+            case K_NULL:
+                if (!onlyX509) {
+                    components.add("K_NULL");
+                }
+                break;
+            case K_RSA:
+                components.add("RSA");
+                break;
+            case K_RSA_EXPORT:
+                components.add("RSA");
+                components.add("RSA_EXPORT");
+                break;
+            case K_DH_RSA:
+                components.add("RSA");
+                components.add("DH");
+                components.add("DiffieHellman");
+                components.add("DH_RSA");
+                break;
+            case K_DH_DSS:
+                components.add("DSA");
+                components.add("DSS");
+                components.add("DH");
+                components.add("DiffieHellman");
+                components.add("DH_DSS");
+                break;
+            case K_DHE_DSS:
+                components.add("DSA");
+                components.add("DSS");
+                components.add("DH");
+                components.add("DHE");
+                components.add("DiffieHellman");
+                components.add("DHE_DSS");
+                break;
+            case K_DHE_RSA:
+                components.add("RSA");
+                components.add("DH");
+                components.add("DHE");
+                components.add("DiffieHellman");
+                components.add("DHE_RSA");
+                break;
+            case K_DH_ANON:
+                if (!onlyX509) {
+                    components.add("ANON");
+                    components.add("DH");
+                    components.add("DiffieHellman");
+                    components.add("DH_ANON");
+                }
+                break;
+            case K_ECDH_ECDSA:
+                components.add("ECDH");
+                components.add("ECDSA");
+                components.add("ECDH_ECDSA");
+                break;
+            case K_ECDH_RSA:
+                components.add("ECDH");
+                components.add("RSA");
+                components.add("ECDH_RSA");
+                break;
+            case K_ECDHE_ECDSA:
+                components.add("ECDHE");
+                components.add("ECDSA");
+                components.add("ECDHE_ECDSA");
+                break;
+            case K_ECDHE_RSA:
+                components.add("ECDHE");
+                components.add("RSA");
+                components.add("ECDHE_RSA");
+                break;
+            case K_ECDH_ANON:
+                if (!onlyX509) {
+                    components.add("ECDH");
+                    components.add("ANON");
+                    components.add("ECDH_ANON");
+                }
+                break;
+            default:
+                if (ClientKeyExchangeService.find(keyExchange.name) != null) {
+                    if (!onlyX509) {
+                        components.add(keyExchange.name);
+                    }
+                }
+                // otherwise ignore
+            }
+
+        return components;
+    }
+
+    private Set<String> decomposes(CipherSuite.BulkCipher bulkCipher) {
+        Set<String> components = new HashSet<>();
+
+        if (bulkCipher.transformation != null) {
+            components.addAll(super.decompose(bulkCipher.transformation));
+        }
+
+        switch (bulkCipher) {
+            case B_NULL:
+                components.add("C_NULL");
+                break;
+            case B_RC2_40:
+                components.add("RC2_CBC_40");
+                break;
+            case B_RC4_40:
+                components.add("RC4_40");
+                break;
+            case B_RC4_128:
+                components.add("RC4_128");
+                break;
+            case B_DES_40:
+                components.add("DES40_CBC");
+                components.add("DES_CBC_40");
+                break;
+            case B_DES:
+                components.add("DES_CBC");
+                break;
+            case B_3DES:
+                components.add("3DES_EDE_CBC");
+                break;
+            case B_AES_128:
+                components.add("AES_128_CBC");
+                break;
+            case B_AES_256:
+                components.add("AES_256_CBC");
+                break;
+            case B_AES_128_GCM:
+                components.add("AES_128_GCM");
+                break;
+            case B_AES_256_GCM:
+                components.add("AES_256_GCM");
+                break;
+        }
+
+        return components;
+    }
+
+    private Set<String> decomposes(CipherSuite.MacAlg macAlg,
+            BulkCipher cipher) {
+        Set<String> components = new HashSet<>();
+
+        if (macAlg == CipherSuite.MacAlg.M_NULL
+                && cipher.cipherType != CipherType.AEAD_CIPHER) {
+            components.add("M_NULL");
+        } else if (macAlg == CipherSuite.MacAlg.M_MD5) {
+            components.add("MD5");
+            components.add("HmacMD5");
+        } else if (macAlg == CipherSuite.MacAlg.M_SHA) {
+            components.add("SHA1");
+            components.add("SHA-1");
+            components.add("HmacSHA1");
+        } else if (macAlg == CipherSuite.MacAlg.M_SHA256) {
+            components.add("SHA256");
+            components.add("SHA-256");
+            components.add("HmacSHA256");
+        } else if (macAlg == CipherSuite.MacAlg.M_SHA384) {
+            components.add("SHA384");
+            components.add("SHA-384");
+            components.add("HmacSHA384");
+        }
+
+        return components;
+    }
+
+    private Set<String> decompose(KeyExchange keyExchange, BulkCipher cipher,
+            MacAlg macAlg) {
+        Set<String> components = new HashSet<>();
+
+        if (keyExchange != null) {
+            components.addAll(decomposes(keyExchange));
+        }
+
+        if (onlyX509) {
+            // Certification path algorithm constraints do not apply
+            // to cipher and macAlg.
+            return components;
+        }
+
+        if (cipher != null) {
+            components.addAll(decomposes(cipher));
+        }
+
+        if (macAlg != null) {
+            components.addAll(decomposes(macAlg, cipher));
+        }
+
+        return components;
+    }
+
+    @Override
+    public Set<String> decompose(String algorithm) {
+        if (algorithm.startsWith("SSL_") || algorithm.startsWith("TLS_")) {
+            CipherSuite cipherSuite = null;
+            try {
+                cipherSuite = CipherSuite.valueOf(algorithm);
+            } catch (IllegalArgumentException iae) {
+                // ignore: unknown or unsupported ciphersuite
+            }
+
+            if (cipherSuite != null) {
+                return decompose(cipherSuite.keyExchange, cipherSuite.cipher,
+                        cipherSuite.macAlg);
+            }
+        }
+
+        return super.decompose(algorithm);
+    }
+
+}
--- a/jdk/src/java.base/share/classes/sun/security/ssl/SSLSocketImpl.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/ssl/SSLSocketImpl.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1996, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1996, 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
@@ -42,6 +42,9 @@
 import javax.net.ssl.*;
 import sun.misc.ManagedLocalsThread;
 
+import sun.misc.JavaNetAccess;
+import sun.misc.SharedSecrets;
+
 /**
  * Implementation of an SSL socket.  This is a normal connection type
  * socket, implementing SSL over some lower level socket, such as TCP.
@@ -377,6 +380,15 @@
      */
     private int maximumPacketSize = 0;
 
+    /*
+     * Is the local name service trustworthy?
+     *
+     * If the local name service is not trustworthy, reverse host name
+     * resolution should not be performed for endpoint identification.
+     */
+    static final boolean trustNameService =
+            Debug.getBooleanProperty("jdk.tls.trustNameService", false);
+
     //
     // CONSTRUCTORS AND INITIALIZATION CODE
     //
@@ -2063,11 +2075,40 @@
     synchronized String getHost() {
         // Note that the host may be null or empty for localhost.
         if (host == null || host.length() == 0) {
-            host = getInetAddress().getHostName();
+            if (!trustNameService) {
+                // If the local name service is not trustworthy, reverse host
+                // name resolution should not be performed for endpoint
+                // identification.  Use the application original specified
+                // hostname or IP address instead.
+                host = getOriginalHostname(getInetAddress());
+            } else {
+                host = getInetAddress().getHostName();
+            }
         }
+
         return host;
     }
 
+    /*
+     * Get the original application specified hostname.
+     */
+    private static String getOriginalHostname(InetAddress inetAddress) {
+        /*
+         * Get the original hostname via sun.misc.SharedSecrets.
+         */
+        JavaNetAccess jna = SharedSecrets.getJavaNetAccess();
+        String originalHostname = jna.getOriginalHostName(inetAddress);
+
+        /*
+         * If no application specified hostname, use the IP address.
+         */
+        if (originalHostname == null || originalHostname.length() == 0) {
+            originalHostname = inetAddress.getHostAddress();
+        }
+
+        return originalHostname;
+    }
+
     // ONLY used by HttpsClient to setup the URI specified hostname
     //
     // Please NOTE that this method MUST be called before calling to
--- a/jdk/src/java.base/share/classes/sun/security/ssl/ServerHandshaker.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/ssl/ServerHandshaker.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1996, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1996, 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
@@ -32,6 +32,7 @@
 import java.security.cert.*;
 import java.security.interfaces.*;
 import java.security.spec.ECParameterSpec;
+import java.math.BigInteger;
 
 import javax.crypto.SecretKey;
 import javax.crypto.spec.SecretKeySpec;
@@ -39,6 +40,7 @@
 import javax.net.ssl.*;
 
 import sun.security.util.KeyUtil;
+import sun.security.util.LegacyAlgorithmConstraints;
 import sun.security.action.GetPropertyAction;
 import sun.security.ssl.HandshakeMessage.*;
 import sun.security.ssl.CipherSuite.*;
@@ -104,6 +106,12 @@
     // The customized ephemeral DH key size for non-exportable cipher suites.
     private static final int customizedDHKeySize;
 
+    // legacy algorithm constraints
+    private static final AlgorithmConstraints legacyAlgorithmConstraints =
+            new LegacyAlgorithmConstraints(
+                    LegacyAlgorithmConstraints.PROPERTY_TLS_LEGACY_ALGS,
+                    new SSLAlgorithmDecomposer());
+
     static {
         String property = AccessController.doPrivileged(
                     new GetPropertyAction("jdk.tls.ephemeralDHKeySize"));
@@ -400,7 +408,7 @@
                 }
 
                 // verify the client_verify_data value
-                if (!Arrays.equals(clientVerifyData,
+                if (!MessageDigest.isEqual(clientVerifyData,
                                 clientHelloRI.getRenegotiatedConnection())) {
                     fatalSE(Alerts.alert_handshake_failure,
                         "Incorrect verify data in ClientHello " +
@@ -1055,6 +1063,7 @@
             proposed = getActiveCipherSuites();
         }
 
+        List<CipherSuite> legacySuites = new ArrayList<>();
         for (CipherSuite suite : prefered.collection()) {
             if (isNegotiable(proposed, suite) == false) {
                 continue;
@@ -1066,11 +1075,24 @@
                     continue;
                 }
             }
+
+            if (!legacyAlgorithmConstraints.permits(null, suite.name, null)) {
+                legacySuites.add(suite);
+                continue;
+            }
+
             if (trySetCipherSuite(suite) == false) {
                 continue;
             }
             return;
         }
+
+        for (CipherSuite suite : legacySuites) {
+            if (trySetCipherSuite(suite)) {
+                return;
+            }
+        }
+
         fatalSE(Alerts.alert_handshake_failure, "no cipher suites in common");
     }
 
@@ -1550,7 +1572,13 @@
         if (debug != null && Debug.isOn("handshake")) {
             mesg.print(System.out);
         }
-        return dh.getAgreedSecret(mesg.getClientPublicKey(), false);
+
+        BigInteger publicKeyValue = mesg.getClientPublicKey();
+
+        // check algorithm constraints
+        dh.checkConstraints(algorithmConstraints, publicKeyValue);
+
+        return dh.getAgreedSecret(publicKeyValue, false);
     }
 
     private SecretKey clientKeyExchange(ECDHClientKeyExchange mesg)
@@ -1559,7 +1587,13 @@
         if (debug != null && Debug.isOn("handshake")) {
             mesg.print(System.out);
         }
-        return ecdh.getAgreedSecret(mesg.getEncodedPoint());
+
+        byte[] publicPoint = mesg.getEncodedPoint();
+
+        // check algorithm constraints
+        ecdh.checkConstraints(algorithmConstraints, publicPoint);
+
+        return ecdh.getAgreedSecret(publicPoint);
     }
 
     /*
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/sun/security/util/AbstractAlgorithmConstraints.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,119 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package sun.security.util;
+
+import java.security.AccessController;
+import java.security.AlgorithmConstraints;
+import java.security.PrivilegedAction;
+import java.security.Security;
+import java.util.Map;
+import java.util.Set;
+
+/**
+ * The class contains common functionality for algorithm constraints classes.
+ */
+public abstract class AbstractAlgorithmConstraints
+        implements AlgorithmConstraints {
+
+    protected final AlgorithmDecomposer decomposer;
+
+    protected AbstractAlgorithmConstraints(AlgorithmDecomposer decomposer) {
+        this.decomposer = decomposer;
+    }
+
+    // Get algorithm constraints from the specified security property.
+    private static void loadAlgorithmsMap(Map<String, String[]> algorithmsMap,
+            String propertyName) {
+        String property = AccessController.doPrivileged(
+                (PrivilegedAction<String>) () -> Security.getProperty(
+                        propertyName));
+
+        String[] algorithmsInProperty = null;
+        if (property != null && !property.isEmpty()) {
+            // remove double quote marks from beginning/end of the property
+            if (property.charAt(0) == '"'
+                    && property.charAt(property.length() - 1) == '"') {
+                property = property.substring(1, property.length() - 1);
+            }
+            algorithmsInProperty = property.split(",");
+            for (int i = 0; i < algorithmsInProperty.length;
+                    i++) {
+                algorithmsInProperty[i] = algorithmsInProperty[i].trim();
+            }
+        }
+
+        // map the disabled algorithms
+        if (algorithmsInProperty == null) {
+            algorithmsInProperty = new String[0];
+        }
+        algorithmsMap.put(propertyName, algorithmsInProperty);
+    }
+
+    static String[] getAlgorithms(Map<String, String[]> algorithmsMap,
+            String propertyName) {
+        synchronized (algorithmsMap) {
+            if (!algorithmsMap.containsKey(propertyName)) {
+                loadAlgorithmsMap(algorithmsMap, propertyName);
+            }
+
+            return algorithmsMap.get(propertyName);
+        }
+    }
+
+    static boolean checkAlgorithm(String[] algorithms, String algorithm,
+            AlgorithmDecomposer decomposer) {
+        if (algorithm == null || algorithm.length() == 0) {
+            throw new IllegalArgumentException("No algorithm name specified");
+        }
+
+        Set<String> elements = null;
+        for (String item : algorithms) {
+            if (item == null || item.isEmpty()) {
+                continue;
+            }
+
+            // check the full name
+            if (item.equalsIgnoreCase(algorithm)) {
+                return false;
+            }
+
+            // decompose the algorithm into sub-elements
+            if (elements == null) {
+                elements = decomposer.decompose(algorithm);
+            }
+
+            // check the items of the algorithm
+            for (String element : elements) {
+                if (item.equalsIgnoreCase(element)) {
+                    return false;
+                }
+            }
+        }
+
+        return true;
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/sun/security/util/AlgorithmDecomposer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,131 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package sun.security.util;
+
+import java.util.HashSet;
+import java.util.Set;
+import java.util.regex.Pattern;
+
+/**
+ * The class decomposes standard algorithms into sub-elements.
+ */
+public class AlgorithmDecomposer {
+
+    private static final Pattern transPattern = Pattern.compile("/");
+    private static final Pattern pattern =
+                    Pattern.compile("with|and|in", Pattern.CASE_INSENSITIVE);
+
+    /**
+     * Decompose the standard algorithm name into sub-elements.
+     * <p>
+     * For example, we need to decompose "SHA1WithRSA" into "SHA1" and "RSA"
+     * so that we can check the "SHA1" and "RSA" algorithm constraints
+     * separately.
+     * <p>
+     * Please override the method if need to support more name pattern.
+     */
+    public Set<String> decompose(String algorithm) {
+        if (algorithm == null || algorithm.length() == 0) {
+            return new HashSet<>();
+        }
+
+        // algorithm/mode/padding
+        String[] transTockens = transPattern.split(algorithm);
+
+        Set<String> elements = new HashSet<>();
+        for (String transTocken : transTockens) {
+            if (transTocken == null || transTocken.length() == 0) {
+                continue;
+            }
+
+            // PBEWith<digest>And<encryption>
+            // PBEWith<prf>And<encryption>
+            // OAEPWith<digest>And<mgf>Padding
+            // <digest>with<encryption>
+            // <digest>with<encryption>and<mgf>
+            // <digest>with<encryption>in<format>
+            String[] tokens = pattern.split(transTocken);
+
+            for (String token : tokens) {
+                if (token == null || token.length() == 0) {
+                    continue;
+                }
+
+                elements.add(token);
+            }
+        }
+
+        // In Java standard algorithm name specification, for different
+        // purpose, the SHA-1 and SHA-2 algorithm names are different. For
+        // example, for MessageDigest, the standard name is "SHA-256", while
+        // for Signature, the digest algorithm component is "SHA256" for
+        // signature algorithm "SHA256withRSA". So we need to check both
+        // "SHA-256" and "SHA256" to make the right constraint checking.
+
+        // handle special name: SHA-1 and SHA1
+        if (elements.contains("SHA1") && !elements.contains("SHA-1")) {
+            elements.add("SHA-1");
+        }
+        if (elements.contains("SHA-1") && !elements.contains("SHA1")) {
+            elements.add("SHA1");
+        }
+
+        // handle special name: SHA-224 and SHA224
+        if (elements.contains("SHA224") && !elements.contains("SHA-224")) {
+            elements.add("SHA-224");
+        }
+        if (elements.contains("SHA-224") && !elements.contains("SHA224")) {
+            elements.add("SHA224");
+        }
+
+        // handle special name: SHA-256 and SHA256
+        if (elements.contains("SHA256") && !elements.contains("SHA-256")) {
+            elements.add("SHA-256");
+        }
+        if (elements.contains("SHA-256") && !elements.contains("SHA256")) {
+            elements.add("SHA256");
+        }
+
+        // handle special name: SHA-384 and SHA384
+        if (elements.contains("SHA384") && !elements.contains("SHA-384")) {
+            elements.add("SHA-384");
+        }
+        if (elements.contains("SHA-384") && !elements.contains("SHA384")) {
+            elements.add("SHA384");
+        }
+
+        // handle special name: SHA-512 and SHA512
+        if (elements.contains("SHA512") && !elements.contains("SHA-512")) {
+            elements.add("SHA-512");
+        }
+        if (elements.contains("SHA-512") && !elements.contains("SHA512")) {
+            elements.add("SHA512");
+        }
+
+        return elements;
+    }
+
+}
--- a/jdk/src/java.base/share/classes/sun/security/util/DisabledAlgorithmConstraints.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/util/DisabledAlgorithmConstraints.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,15 +25,9 @@
 
 package sun.security.util;
 
-import java.security.AlgorithmConstraints;
 import java.security.CryptoPrimitive;
 import java.security.AlgorithmParameters;
-
 import java.security.Key;
-import java.security.Security;
-import java.security.PrivilegedAction;
-import java.security.AccessController;
-
 import java.util.Locale;
 import java.util.Set;
 import java.util.Collections;
@@ -49,7 +43,7 @@
  * See the "jdk.certpath.disabledAlgorithms" specification in java.security
  * for the syntax of the disabled algorithm string.
  */
-public class DisabledAlgorithmConstraints implements AlgorithmConstraints {
+public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
 
     // the known security property, jdk.certpath.disabledAlgorithms
     public final static String PROPERTY_CERTPATH_DISABLED_ALGS =
@@ -64,8 +58,8 @@
     private final static Map<String, KeySizeConstraints> keySizeConstraintsMap =
                                                             new HashMap<>();
 
-    private String[] disabledAlgorithms;
-    private KeySizeConstraints keySizeConstraints;
+    private final String[] disabledAlgorithms;
+    private final KeySizeConstraints keySizeConstraints;
 
     /**
      * Initialize algorithm constraints with the specified security property.
@@ -74,56 +68,27 @@
      *        algorithm constraints
      */
     public DisabledAlgorithmConstraints(String propertyName) {
-        // Both disabledAlgorithmsMap and keySizeConstraintsMap are
-        // synchronized with the lock of disabledAlgorithmsMap.
-        synchronized (disabledAlgorithmsMap) {
-            if(!disabledAlgorithmsMap.containsKey(propertyName)) {
-                loadDisabledAlgorithmsMap(propertyName);
-            }
+        this(propertyName, new AlgorithmDecomposer());
+    }
 
-            disabledAlgorithms = disabledAlgorithmsMap.get(propertyName);
-            keySizeConstraints = keySizeConstraintsMap.get(propertyName);
-        }
+    public DisabledAlgorithmConstraints(String propertyName,
+            AlgorithmDecomposer decomposer) {
+        super(decomposer);
+        disabledAlgorithms = getAlgorithms(disabledAlgorithmsMap, propertyName);
+        keySizeConstraints = getKeySizeConstraints(disabledAlgorithms,
+                propertyName);
     }
 
     @Override
     final public boolean permits(Set<CryptoPrimitive> primitives,
             String algorithm, AlgorithmParameters parameters) {
 
-        if (algorithm == null || algorithm.length() == 0) {
-            throw new IllegalArgumentException("No algorithm name specified");
-        }
-
         if (primitives == null || primitives.isEmpty()) {
             throw new IllegalArgumentException(
                         "No cryptographic primitive specified");
         }
 
-        Set<String> elements = null;
-        for (String disabled : disabledAlgorithms) {
-            if (disabled == null || disabled.isEmpty()) {
-                continue;
-            }
-
-            // check the full name
-            if (disabled.equalsIgnoreCase(algorithm)) {
-                return false;
-            }
-
-            // decompose the algorithm into sub-elements
-            if (elements == null) {
-                elements = decomposes(algorithm);
-            }
-
-            // check the items of the algorithm
-            for (String element : elements) {
-                if (disabled.equalsIgnoreCase(element)) {
-                    return false;
-                }
-            }
-        }
-
-        return true;
+        return checkAlgorithm(disabledAlgorithms, algorithm, decomposer);
     }
 
     @Override
@@ -142,99 +107,6 @@
         return checkConstraints(primitives, algorithm, key, parameters);
     }
 
-    /**
-     * Decompose the standard algorithm name into sub-elements.
-     * <p>
-     * For example, we need to decompose "SHA1WithRSA" into "SHA1" and "RSA"
-     * so that we can check the "SHA1" and "RSA" algorithm constraints
-     * separately.
-     * <p>
-     * Please override the method if need to support more name pattern.
-     */
-    protected Set<String> decomposes(String algorithm) {
-        if (algorithm == null || algorithm.length() == 0) {
-            return new HashSet<String>();
-        }
-
-        // algorithm/mode/padding
-        Pattern transPattern = Pattern.compile("/");
-        String[] transTockens = transPattern.split(algorithm);
-
-        Set<String> elements = new HashSet<String>();
-        for (String transTocken : transTockens) {
-            if (transTocken == null || transTocken.length() == 0) {
-                continue;
-            }
-
-            // PBEWith<digest>And<encryption>
-            // PBEWith<prf>And<encryption>
-            // OAEPWith<digest>And<mgf>Padding
-            // <digest>with<encryption>
-            // <digest>with<encryption>and<mgf>
-            // <digest>with<encryption>in<format>
-            Pattern pattern =
-                    Pattern.compile("with|and|in", Pattern.CASE_INSENSITIVE);
-            String[] tokens = pattern.split(transTocken);
-
-            for (String token : tokens) {
-                if (token == null || token.length() == 0) {
-                    continue;
-                }
-
-                elements.add(token);
-            }
-        }
-
-        // In Java standard algorithm name specification, for different
-        // purpose, the SHA-1 and SHA-2 algorithm names are different. For
-        // example, for MessageDigest, the standard name is "SHA-256", while
-        // for Signature, the digest algorithm component is "SHA256" for
-        // signature algorithm "SHA256withRSA". So we need to check both
-        // "SHA-256" and "SHA256" to make the right constraint checking.
-
-        // handle special name: SHA-1 and SHA1
-        if (elements.contains("SHA1") && !elements.contains("SHA-1")) {
-            elements.add("SHA-1");
-        }
-        if (elements.contains("SHA-1") && !elements.contains("SHA1")) {
-            elements.add("SHA1");
-        }
-
-        // handle special name: SHA-224 and SHA224
-        if (elements.contains("SHA224") && !elements.contains("SHA-224")) {
-            elements.add("SHA-224");
-        }
-        if (elements.contains("SHA-224") && !elements.contains("SHA224")) {
-            elements.add("SHA224");
-        }
-
-        // handle special name: SHA-256 and SHA256
-        if (elements.contains("SHA256") && !elements.contains("SHA-256")) {
-            elements.add("SHA-256");
-        }
-        if (elements.contains("SHA-256") && !elements.contains("SHA256")) {
-            elements.add("SHA256");
-        }
-
-        // handle special name: SHA-384 and SHA384
-        if (elements.contains("SHA384") && !elements.contains("SHA-384")) {
-            elements.add("SHA-384");
-        }
-        if (elements.contains("SHA-384") && !elements.contains("SHA384")) {
-            elements.add("SHA384");
-        }
-
-        // handle special name: SHA-512 and SHA512
-        if (elements.contains("SHA512") && !elements.contains("SHA-512")) {
-            elements.add("SHA-512");
-        }
-        if (elements.contains("SHA-512") && !elements.contains("SHA512")) {
-            elements.add("SHA512");
-        }
-
-        return elements;
-    }
-
     // Check algorithm constraints
     private boolean checkConstraints(Set<CryptoPrimitive> primitives,
             String algorithm, Key key, AlgorithmParameters parameters) {
@@ -264,43 +136,18 @@
         return true;
     }
 
-    // Get disabled algorithm constraints from the specified security property.
-    private static void loadDisabledAlgorithmsMap(
-            final String propertyName) {
-
-        String property = AccessController.doPrivileged(
-            new PrivilegedAction<String>() {
-                public String run() {
-                    return Security.getProperty(propertyName);
-                }
-            });
-
-        String[] algorithmsInProperty = null;
-
-        if (property != null && !property.isEmpty()) {
-
-            // remove double quote marks from beginning/end of the property
-            if (property.charAt(0) == '"' &&
-                    property.charAt(property.length() - 1) == '"') {
-                property = property.substring(1, property.length() - 1);
+    private static KeySizeConstraints getKeySizeConstraints(
+            String[] disabledAlgorithms, String propertyName) {
+        synchronized (keySizeConstraintsMap) {
+            if(!keySizeConstraintsMap.containsKey(propertyName)) {
+                // map the key constraints
+                KeySizeConstraints keySizeConstraints =
+                        new KeySizeConstraints(disabledAlgorithms);
+                keySizeConstraintsMap.put(propertyName, keySizeConstraints);
             }
 
-            algorithmsInProperty = property.split(",");
-            for (int i = 0; i < algorithmsInProperty.length; i++) {
-                algorithmsInProperty[i] = algorithmsInProperty[i].trim();
-            }
+            return keySizeConstraintsMap.get(propertyName);
         }
-
-        // map the disabled algorithms
-        if (algorithmsInProperty == null) {
-            algorithmsInProperty = new String[0];
-        }
-        disabledAlgorithmsMap.put(propertyName, algorithmsInProperty);
-
-        // map the key constraints
-        KeySizeConstraints keySizeConstraints =
-            new KeySizeConstraints(algorithmsInProperty);
-        keySizeConstraintsMap.put(propertyName, keySizeConstraints);
     }
 
     /**
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/sun/security/util/LegacyAlgorithmConstraints.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,73 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package sun.security.util;
+
+import java.security.AlgorithmParameters;
+import java.security.CryptoPrimitive;
+import java.security.Key;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.Set;
+import static sun.security.util.AbstractAlgorithmConstraints.getAlgorithms;
+
+/**
+ * Algorithm constraints for legacy algorithms.
+ */
+public class LegacyAlgorithmConstraints extends AbstractAlgorithmConstraints {
+
+    // the known security property, jdk.tls.legacyAlgorithms
+    public final static String PROPERTY_TLS_LEGACY_ALGS =
+            "jdk.tls.legacyAlgorithms";
+
+    private final static Map<String, String[]> legacyAlgorithmsMap =
+                                                          new HashMap<>();
+
+    private final String[] legacyAlgorithms;
+
+    public LegacyAlgorithmConstraints(String propertyName,
+            AlgorithmDecomposer decomposer) {
+        super(decomposer);
+        legacyAlgorithms = getAlgorithms(legacyAlgorithmsMap, propertyName);
+    }
+
+    @Override
+    final public boolean permits(Set<CryptoPrimitive> primitives,
+            String algorithm, AlgorithmParameters parameters) {
+        return checkAlgorithm(legacyAlgorithms, algorithm, decomposer);
+    }
+
+    @Override
+    final public boolean permits(Set<CryptoPrimitive> primitives, Key key) {
+        return true;
+    }
+
+    @Override
+    final public boolean permits(Set<CryptoPrimitive> primitives,
+            String algorithm, Key key, AlgorithmParameters parameters) {
+        return checkAlgorithm(legacyAlgorithms, algorithm, decomposer);
+    }
+
+}
--- a/jdk/src/java.base/share/classes/sun/security/validator/SimpleValidator.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/validator/SimpleValidator.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2002, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2002, 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
@@ -141,8 +141,18 @@
         // create distrusted certificates checker
         UntrustedChecker untrustedChecker = new UntrustedChecker();
 
+        // check if anchor is untrusted
+        X509Certificate anchorCert = chain[chain.length - 1];
+        try {
+            untrustedChecker.check(anchorCert);
+        } catch (CertPathValidatorException cpve) {
+            throw new ValidatorException(
+                "Untrusted certificate: "+ anchorCert.getSubjectX500Principal(),
+                ValidatorException.T_UNTRUSTED_CERT, anchorCert, cpve);
+        }
+
         // create default algorithm constraints checker
-        TrustAnchor anchor = new TrustAnchor(chain[chain.length - 1], null);
+        TrustAnchor anchor = new TrustAnchor(anchorCert, null);
         AlgorithmChecker defaultAlgChecker = new AlgorithmChecker(anchor);
 
         // create application level algorithm constraints checker
--- a/jdk/src/java.base/share/classes/sun/text/ComposedCharIter.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/ComposedCharIter.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2001, 2005, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2001, 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
@@ -43,7 +43,7 @@
     private static int decompNum;
 
     static {
-        int maxNum = 2000;     //TBD: Unicode 4.0 only has 1926 canoDecomp...
+        int maxNum = 2100;
         chars = new int[maxNum];
         decomps = new String[maxNum];
         decompNum = NormalizerImpl.getDecompose(chars, decomps);
--- a/jdk/src/java.base/share/classes/sun/text/Normalizer.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/Normalizer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -26,7 +26,7 @@
 package sun.text;
 
 import sun.text.normalizer.NormalizerBase;
-import sun.text.normalizer.NormalizerImpl;
+import sun.text.normalizer.UCharacter;
 
 /**
  * This Normalizer is for Unicode 3.2 support for IDNA only.
@@ -93,6 +93,6 @@
      * @return combining class of the given character
      */
     public static final int getCombiningClass(int ch) {
-        return NormalizerImpl.getCombiningClass(ch);
+        return UCharacter.getCombiningClass(ch);
     }
 }
--- a/jdk/src/java.base/share/classes/sun/text/bidi/BidiBase.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/bidi/BidiBase.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2009, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2009, 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
@@ -22,17 +22,13 @@
  * or visit www.oracle.com if you need additional information or have any
  * questions.
  */
+
 /*
- *******************************************************************************
- * (C) Copyright IBM Corp. and others, 1996-2009 - All Rights Reserved         *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
- *******************************************************************************
- */
+*******************************************************************************
+*   Copyright (C) 2001-2014, International Business Machines
+*   Corporation and others.  All Rights Reserved.
+*******************************************************************************
+*/
 
 /* FOOD FOR THOUGHT: currently the reordering modes are a mixture of
  * algorithm for direct BiDi, algorithm for inverse Bidi and the bizarre
@@ -52,12 +48,10 @@
 
 package sun.text.bidi;
 
-import java.io.IOException;
 import java.lang.reflect.Array;
 import java.text.AttributedCharacterIterator;
 import java.text.Bidi;
 import java.util.Arrays;
-import java.util.MissingResourceException;
 import sun.misc.JavaAWTFontAccess;
 import sun.misc.SharedSecrets;
 import sun.text.normalizer.UBiDiProps;
@@ -68,10 +62,9 @@
  *
  * <h2>Bidi algorithm for ICU</h2>
  *
- * This is an implementation of the Unicode Bidirectional algorithm. The
+ * This is an implementation of the Unicode Bidirectional Algorithm. The
  * algorithm is defined in the <a
- * href="http://www.unicode.org/unicode/reports/tr9/">Unicode Standard Annex #9</a>,
- * version 13, also described in The Unicode Standard, Version 4.0 .
+ * href="http://www.unicode.org/unicode/reports/tr9/">Unicode Standard Annex #9</a>.
  * <p>
  *
  * Note: Libraries that perform a bidirectional algorithm and reorder strings
@@ -106,6 +99,7 @@
  * <li>{@link #LTR}
  * <li>{@link #RTL}
  * <li>{@link #MIXED}
+ * <li>{@link #NEUTRAL}
  * </ul>
  *
  * <h3>Basic concept: levels</h3>
@@ -167,6 +161,7 @@
  *
  * <h3>Basic concept: Reordering Options</h3>
  * Reordering options can be applied during Bidi text transformations.
+ *
  * <p><b>See Also:</b>
  * <ul>
  * <li>{@link #setReorderingOptions}
@@ -456,19 +451,134 @@
  * }</pre>
  */
 
+/*
+ * General implementation notes:
+ *
+ * Throughout the implementation, there are comments like (W2) that refer to
+ * rules of the BiDi algorithm, in this example to the second rule of the
+ * resolution of weak types.
+ *
+ * For handling surrogate pairs, where two UChar's form one "abstract" (or UTF-32)
+ * character according to UTF-16, the second UChar gets the directional property of
+ * the entire character assigned, while the first one gets a BN, a boundary
+ * neutral, type, which is ignored by most of the algorithm according to
+ * rule (X9) and the implementation suggestions of the BiDi algorithm.
+ *
+ * Later, adjustWSLevels() will set the level for each BN to that of the
+ * following character (UChar), which results in surrogate pairs getting the
+ * same level on each of their surrogates.
+ *
+ * In a UTF-8 implementation, the same thing could be done: the last byte of
+ * a multi-byte sequence would get the "real" property, while all previous
+ * bytes of that sequence would get BN.
+ *
+ * It is not possible to assign all those parts of a character the same real
+ * property because this would fail in the resolution of weak types with rules
+ * that look at immediately surrounding types.
+ *
+ * As a related topic, this implementation does not remove Boundary Neutral
+ * types from the input, but ignores them wherever this is relevant.
+ * For example, the loop for the resolution of the weak types reads
+ * types until it finds a non-BN.
+ * Also, explicit embedding codes are neither changed into BN nor removed.
+ * They are only treated the same way real BNs are.
+ * As stated before, adjustWSLevels() takes care of them at the end.
+ * For the purpose of conformance, the levels of all these codes
+ * do not matter.
+ *
+ * Note that this implementation modifies the dirProps
+ * after the initial setup, when applying X5c (replace FSI by LRI or RLI),
+ * X6, N0 (replace paired brackets by L or R).
+ *
+ * In this implementation, the resolution of weak types (W1 to W6),
+ * neutrals (N1 and N2), and the assignment of the resolved level (In)
+ * are all done in one single loop, in resolveImplicitLevels().
+ * Changes of dirProp values are done on the fly, without writing
+ * them back to the dirProps array.
+ *
+ *
+ * This implementation contains code that allows to bypass steps of the
+ * algorithm that are not needed on the specific paragraph
+ * in order to speed up the most common cases considerably,
+ * like text that is entirely LTR, or RTL text without numbers.
+ *
+ * Most of this is done by setting a bit for each directional property
+ * in a flags variable and later checking for whether there are
+ * any LTR characters or any RTL characters, or both, whether
+ * there are any explicit embedding codes, etc.
+ *
+ * If the (Xn) steps are performed, then the flags are re-evaluated,
+ * because they will then not contain the embedding codes any more
+ * and will be adjusted for override codes, so that subsequently
+ * more bypassing may be possible than what the initial flags suggested.
+ *
+ * If the text is not mixed-directional, then the
+ * algorithm steps for the weak type resolution are not performed,
+ * and all levels are set to the paragraph level.
+ *
+ * If there are no explicit embedding codes, then the (Xn) steps
+ * are not performed.
+ *
+ * If embedding levels are supplied as a parameter, then all
+ * explicit embedding codes are ignored, and the (Xn) steps
+ * are not performed.
+ *
+ * White Space types could get the level of the run they belong to,
+ * and are checked with a test of (flags&MASK_EMBEDDING) to
+ * consider if the paragraph direction should be considered in
+ * the flags variable.
+ *
+ * If there are no White Space types in the paragraph, then
+ * (L1) is not necessary in adjustWSLevels().
+ */
+
 public class BidiBase {
 
-    class Point {
+    static class Point {
         int pos;    /* position in text */
         int flag;   /* flag for LRM/RLM, before/after */
     }
 
-    class InsertPoints {
+    static class InsertPoints {
         int size;
         int confirmed;
         Point[] points = new Point[0];
     }
 
+    static class Opening {
+        int   position;                 /* position of opening bracket */
+        int   match;                    /* matching char or -position of closing bracket */
+        int   contextPos;               /* position of last strong char found before opening */
+        short flags;                    /* bits for L or R/AL found within the pair */
+        byte  contextDir;               /* L or R according to last strong char before opening */
+    }
+
+    static class IsoRun {
+        int   contextPos;               /* position of char determining context */
+        short start;                    /* index of first opening entry for this run */
+        short limit;                    /* index after last opening entry for this run */
+        byte  level;                    /* level of this run */
+        byte  lastStrong;               /* bidi class of last strong char found in this run */
+        byte  lastBase;                 /* bidi class of last base char found in this run */
+        byte  contextDir;               /* L or R to use as context for following openings */
+    }
+
+    static class BracketData {
+        Opening[] openings = new Opening[SIMPLE_PARAS_COUNT];
+        int   isoRunLast;               /* index of last used entry */
+        /* array of nested isolated sequence entries; can never excess UBIDI_MAX_EXPLICIT_LEVEL
+           + 1 for index 0, + 1 for before the first isolated sequence */
+        IsoRun[]  isoRuns = new IsoRun[MAX_EXPLICIT_LEVEL+2];
+        boolean   isNumbersSpecial;     /*reordering mode for NUMBERS_SPECIAL */
+    }
+
+    static class Isolate {
+        int   startON;
+        int   start1;
+        short stateImp;
+        short state;
+    }
+
     /** Paragraph level setting<p>
      *
      * Constant indicating that the base direction depends on the first strong
@@ -482,7 +592,7 @@
      * is assumed to be visual LTR, and the text after reordering is required
      * to be the corresponding logical string with appropriate contextual
      * direction. The direction of the result string will be RTL if either
-     * the righmost or leftmost strong character of the source text is RTL
+     * the rightmost or leftmost strong character of the source text is RTL
      * or Arabic Letter, the direction will be LTR otherwise.<p>
      *
      * If reordering option <code>OPTION_INSERT_MARKS</code> is set, an RLM may
@@ -493,7 +603,7 @@
      * @see #REORDER_INVERSE_FOR_NUMBERS_SPECIAL
      * @stable ICU 3.8
      */
-    public static final byte INTERNAL_LEVEL_DEFAULT_LTR = (byte)0x7e;
+    public static final byte LEVEL_DEFAULT_LTR = (byte)0x7e;
 
     /** Paragraph level setting<p>
      *
@@ -508,7 +618,7 @@
      * is assumed to be visual LTR, and the text after reordering is required
      * to be the corresponding logical string with appropriate contextual
      * direction. The direction of the result string will be RTL if either
-     * the righmost or leftmost strong character of the source text is RTL
+     * the rightmost or leftmost strong character of the source text is RTL
      * or Arabic Letter, or if the text contains no strong character;
      * the direction will be LTR otherwise.<p>
      *
@@ -520,21 +630,21 @@
      * @see #REORDER_INVERSE_FOR_NUMBERS_SPECIAL
      * @stable ICU 3.8
      */
-    public static final byte INTERNAL_LEVEL_DEFAULT_RTL = (byte)0x7f;
+    public static final byte LEVEL_DEFAULT_RTL = (byte)0x7f;
 
     /**
      * Maximum explicit embedding level.
      * (The maximum resolved level can be up to <code>MAX_EXPLICIT_LEVEL+1</code>).
      * @stable ICU 3.8
      */
-    public static final byte MAX_EXPLICIT_LEVEL = 61;
+    public static final byte MAX_EXPLICIT_LEVEL = 125;
 
     /**
      * Bit flag for level input.
      * Overrides directional properties.
      * @stable ICU 3.8
      */
-    public static final byte INTERNAL_LEVEL_OVERRIDE = (byte)0x80;
+    public static final byte LEVEL_OVERRIDE = (byte)0x80;
 
     /**
      * Special value which can be returned by the mapping methods when a
@@ -555,13 +665,53 @@
     public static final int MAP_NOWHERE = -1;
 
     /**
+     * Left-to-right text.
+     * <ul>
+     * <li>As return value for <code>getDirection()</code>, it means
+     *     that the source string contains no right-to-left characters, or
+     *     that the source string is empty and the paragraph level is even.
+     * <li>As return value for <code>getBaseDirection()</code>, it
+     *     means that the first strong character of the source string has
+     *     a left-to-right direction.
+     * </ul>
+     * @stable ICU 3.8
+     */
+    public static final byte LTR = 0;
+
+    /**
+     * Right-to-left text.
+     * <ul>
+     * <li>As return value for <code>getDirection()</code>, it means
+     *     that the source string contains no left-to-right characters, or
+     *     that the source string is empty and the paragraph level is odd.
+     * <li>As return value for <code>getBaseDirection()</code>, it
+     *     means that the first strong character of the source string has
+     *     a right-to-left direction.
+     * </ul>
+     * @stable ICU 3.8
+     */
+    public static final byte RTL = 1;
+
+    /**
      * Mixed-directional text.
+     * <p>As return value for <code>getDirection()</code>, it means
+     *    that the source string contains both left-to-right and
+     *    right-to-left characters.
      * @stable ICU 3.8
      */
     public static final byte MIXED = 2;
 
     /**
      * option bit for writeReordered():
+     * keep combining characters after their base characters in RTL runs
+     *
+     * @see #writeReordered
+     * @stable ICU 3.8
+     */
+    public static final short KEEP_BASE_COMBINING = 1;
+
+    /**
+     * option bit for writeReordered():
      * replace characters with the "mirrored" property in RTL runs
      * by their mirror-image mappings
      *
@@ -570,6 +720,50 @@
      */
     public static final short DO_MIRRORING = 2;
 
+    /**
+     * option bit for writeReordered():
+     * surround the run with LRMs if necessary;
+     * this is part of the approximate "inverse Bidi" algorithm
+     *
+     * <p>This option does not imply corresponding adjustment of the index
+     * mappings.</p>
+     *
+     * @see #setInverse
+     * @see #writeReordered
+     * @stable ICU 3.8
+     */
+    public static final short INSERT_LRM_FOR_NUMERIC = 4;
+
+    /**
+     * option bit for writeReordered():
+     * remove Bidi control characters
+     * (this does not affect INSERT_LRM_FOR_NUMERIC)
+     *
+     * <p>This option does not imply corresponding adjustment of the index
+     * mappings.</p>
+     *
+     * @see #writeReordered
+     * @see #INSERT_LRM_FOR_NUMERIC
+     * @stable ICU 3.8
+     */
+    public static final short REMOVE_BIDI_CONTROLS = 8;
+
+    /**
+     * option bit for writeReordered():
+     * write the output in reverse order
+     *
+     * <p>This has the same effect as calling <code>writeReordered()</code>
+     * first without this option, and then calling
+     * <code>writeReverse()</code> without mirroring.
+     * Doing this in the same step is faster and avoids a temporary buffer.
+     * An example for using this option is output to a character terminal that
+     * is designed for RTL scripts and stores text in reverse order.</p>
+     *
+     * @see #writeReordered
+     * @stable ICU 3.8
+     */
+    public static final short OUTPUT_REVERSE = 16;
+
     /** Reordering mode: Regular Logical to Visual Bidi algorithm according to Unicode.
      * @see #setReorderingMode
      * @stable ICU 3.8
@@ -600,7 +794,7 @@
      * @see #setReorderingMode
      * @stable ICU 3.8
      */
-    private static final short REORDER_RUNS_ONLY = 3;
+    static final short REORDER_RUNS_ONLY = 3;
 
     /** Reordering mode: Visual to Logical algorithm which handles numbers
      * like L (same algorithm as selected by <code>setInverse(true)</code>.
@@ -608,21 +802,21 @@
      * @see #setReorderingMode
      * @stable ICU 3.8
      */
-    private static final short REORDER_INVERSE_NUMBERS_AS_L = 4;
+    static final short REORDER_INVERSE_NUMBERS_AS_L = 4;
 
     /** Reordering mode: Visual to Logical algorithm equivalent to the regular
      * Logical to Visual algorithm.
      * @see #setReorderingMode
      * @stable ICU 3.8
      */
-    private static final short REORDER_INVERSE_LIKE_DIRECT = 5;
+    static final short REORDER_INVERSE_LIKE_DIRECT = 5;
 
     /** Reordering mode: Inverse Bidi (Visual to Logical) algorithm for the
      * <code>REORDER_NUMBERS_SPECIAL</code> Bidi algorithm.
      * @see #setReorderingMode
      * @stable ICU 3.8
      */
-    private static final short REORDER_INVERSE_FOR_NUMBERS_SPECIAL = 6;
+    static final short REORDER_INVERSE_FOR_NUMBERS_SPECIAL = 6;
 
     /* Reordering mode values must be ordered so that all the regular logical to
      * visual modes come first, and all inverse Bidi modes come last.
@@ -682,7 +876,7 @@
      * @see #REORDER_INVERSE_FOR_NUMBERS_SPECIAL
      * @stable ICU 3.8
      */
-    private static final int OPTION_INSERT_MARKS = 1;
+    static final int OPTION_INSERT_MARKS = 1;
 
     /**
      * Option bit for <code>setReorderingOptions</code>:
@@ -704,7 +898,7 @@
      * @see #REMOVE_BIDI_CONTROLS
      * @stable ICU 3.8
      */
-    private static final int OPTION_REMOVE_CONTROLS = 2;
+    static final int OPTION_REMOVE_CONTROLS = 2;
 
     /**
      * Option bit for <code>setReorderingOptions</code>:
@@ -741,8 +935,7 @@
      * part of the text.</p>
      *
      * <p>When the <code>OPTION_STREAMING</code> option is used, it is
-     * recommended to call <code>orderParagraphsLTR()</code> with argument
-     * <code>orderParagraphsLTR</code> set to <code>true</code> before calling
+     * recommended to call <code>orderParagraphsLTR(true)</code> before calling
      * <code>setPara()</code> so that later paragraphs may be concatenated to
      * previous paragraphs on the right.
      * </p>
@@ -750,7 +943,6 @@
      * @see #setReorderingMode
      * @see #setReorderingOptions
      * @see #getProcessedLength
-     * @see #orderParagraphsLTR
      * @stable ICU 3.8
      */
     private static final int OPTION_STREAMING = 4;
@@ -760,7 +952,7 @@
      *   is easier with the same names for the Bidi types in the code as there.
      *   See UCharacterDirection
      */
-    private static final byte L   = 0;
+    /* private */ static final byte L   = 0;
     private static final byte R   = 1;
     private static final byte EN  = 2;
     private static final byte ES  = 3;
@@ -779,8 +971,55 @@
     private static final byte PDF = 16;
     private static final byte NSM = 17;
     private static final byte BN  = 18;
-
-    private static final int MASK_R_AL = (1 << R | 1 << AL);
+    private static final byte FSI = 19;
+    private static final byte LRI = 20;
+    private static final byte RLI = 21;
+    private static final byte PDI = 22;
+    private static final byte ENL = PDI + 1;    /* EN after W7 */
+    private static final byte ENR = ENL + 1;    /* EN not subject to W7 */
+
+    // Number of directional types
+    private static final int CHAR_DIRECTION_COUNT       = 23;
+
+    /**
+     * Enumerated property Bidi_Paired_Bracket_Type (new in Unicode 6.3).
+     * Used in UAX #9: Unicode Bidirectional Algorithm
+     * (http://www.unicode.org/reports/tr9/)
+     * Returns UCharacter.BidiPairedBracketType values.
+     * @stable ICU 52
+     */
+    public static final int BIDI_PAIRED_BRACKET_TYPE = 0x1015;
+
+    /**
+     * Bidi Paired Bracket Type constants.
+     *
+     * @see UProperty#BIDI_PAIRED_BRACKET_TYPE
+     * @stable ICU 52
+     */
+    public static interface BidiPairedBracketType {
+        /**
+         * Not a paired bracket.
+         * @stable ICU 52
+         */
+        public static final int NONE = 0;
+        /**
+         * Open paired bracket.
+         * @stable ICU 52
+         */
+        public static final int OPEN = 1;
+        /**
+         * Close paired bracket.
+         * @stable ICU 52
+         */
+        public static final int CLOSE = 2;
+        /**
+         * @stable ICU 52
+         */
+        public static final int COUNT = 3;
+    }
+
+    /* number of paras entries allocated initially */
+    static final int SIMPLE_PARAS_COUNT = 10;
 
     private static final char CR = '\r';
     private static final char LF = '\n';
@@ -790,12 +1029,22 @@
     static final int RLM_BEFORE = 4;
     static final int RLM_AFTER = 8;
 
+    /* flags for Opening.flags */
+    static final byte FOUND_L = (byte)DirPropFlag(L);
+    static final byte FOUND_R = (byte)DirPropFlag(R);
+
+    /*
+     * The following bit is used for the directional isolate status.
+     * Stack entries corresponding to isolate sequences are greater than ISOLATE.
+     */
+    static final int ISOLATE = 0x0100;
+
     /*
      * reference to parent paragraph object (reference to self if this object is
      * a paragraph object); set to null in a newly opened object; set to a
      * real value after a successful execution of setPara or setLine
      */
-    BidiBase                paraBidi;
+    BidiBase            paraBidi;
 
     final UBiDiProps    bdp;
 
@@ -828,6 +1077,15 @@
     byte[]              dirProps;
     byte[]              levels;
 
+    /* are we performing an approximation of the "inverse Bidi" algorithm? */
+    boolean             isInverse;
+
+    /* are we using the basic algorithm or its variation? */
+    int                 reorderingMode;
+
+    /* bitmask for reordering options */
+    int                 reorderingOptions;
+
     /* must block separators receive level 0? */
     boolean             orderParagraphsLTR;
 
@@ -855,14 +1113,10 @@
     /* implicitly at the paraLevel (rule (L1)) - levels may not reflect that */
     int                 trailingWSStart;
 
-    /* fields for paragraph handling */
-    int                 paraCount;       /* set in getDirProps() */
-    int[]               parasMemory = new int[1];
-    int[]               paras;           /* limits of paragraphs, filled in
-                                          ResolveExplicitLevels() or CheckExplicitLevels() */
-
-    /* for single paragraph text, we only need a tiny array of paras (no allocation) */
-    int[]               simpleParas = {0};
+    /* fields for paragraph handling, set in getDirProps() */
+    int                 paraCount;
+    int[]               paras_limit = new int[SIMPLE_PARAS_COUNT];
+    byte[]              paras_level = new byte[SIMPLE_PARAS_COUNT];
 
     /* fields for line reordering */
     int                 runCount;     /* ==-1: runs not set up yet */
@@ -872,9 +1126,18 @@
     /* for non-mixed text, we only need a tiny array of runs (no allocation) */
     BidiRun[]           simpleRuns = {new BidiRun()};
 
+    /* fields for managing isolate sequences */
+    Isolate[]           isolates;
+
+    /* maximum or current nesting depth of isolate sequences */
+    /* Within resolveExplicitLevels() and checkExplicitLevels(), this is the maximal
+       nesting encountered.
+       Within resolveImplicitLevels(), this is the index of the current isolates
+       stack entry. */
+    int                 isolateCount;
+
     /* mapping of runs in logical order to visual order */
     int[]               logicalToVisualRunsMap;
-
     /* flag to indicate that the map has been updated */
     boolean             isGoodLogicalToVisualRunsMap;
 
@@ -894,23 +1157,8 @@
         return (1 << dir);
     }
 
-    /*
-     * The following bit is ORed to the property of characters in paragraphs
-     * with contextual RTL direction when paraLevel is contextual.
-     */
-    static final byte CONTEXT_RTL_SHIFT = 6;
-    static final byte CONTEXT_RTL = (byte)(1<<CONTEXT_RTL_SHIFT);   // 0x40
-    static byte NoContextRTL(byte dir)
-    {
-        return (byte)(dir & ~CONTEXT_RTL);
-    }
-
-    /*
-     * The following is a variant of DirProp.DirPropFlag() which ignores the
-     * CONTEXT_RTL bit.
-     */
-    static int DirPropFlagNC(byte dir) {
-        return (1<<(dir & ~CONTEXT_RTL));
+    boolean testDirPropFlagAt(int flag, int index) {
+        return ((DirPropFlag(dirProps[index]) & flag) != 0);
     }
 
     static final int DirPropFlagMultiRuns = DirPropFlag((byte)31);
@@ -923,40 +1171,38 @@
     static final int DirPropFlagLR(byte level) { return DirPropFlagLR[level & 1]; }
     static final int DirPropFlagE(byte level)  { return DirPropFlagE[level & 1]; }
     static final int DirPropFlagO(byte level)  { return DirPropFlagO[level & 1]; }
-
-    /*
-     *  are there any characters that are LTR?
-     */
+    static final byte DirFromStrong(byte strong) { return strong == L ? L : R; }
+    static final byte NoOverride(byte level) { return (byte)(level & ~LEVEL_OVERRIDE); }
+
+    /*  are there any characters that are LTR or RTL? */
     static final int MASK_LTR =
-        DirPropFlag(L)|DirPropFlag(EN)|DirPropFlag(AN)|DirPropFlag(LRE)|DirPropFlag(LRO);
-
-    /*
-     *  are there any characters that are RTL?
-     */
-    static final int MASK_RTL = DirPropFlag(R)|DirPropFlag(AL)|DirPropFlag(RLE)|DirPropFlag(RLO);
+        DirPropFlag(L)|DirPropFlag(EN)|DirPropFlag(ENL)|DirPropFlag(ENR)|DirPropFlag(AN)|DirPropFlag(LRE)|DirPropFlag(LRO)|DirPropFlag(LRI);
+    static final int MASK_RTL = DirPropFlag(R)|DirPropFlag(AL)|DirPropFlag(RLE)|DirPropFlag(RLO)|DirPropFlag(RLI);
+
+    static final int MASK_R_AL = DirPropFlag(R)|DirPropFlag(AL);
 
     /* explicit embedding codes */
-    private static final int MASK_LRX = DirPropFlag(LRE)|DirPropFlag(LRO);
-    private static final int MASK_RLX = DirPropFlag(RLE)|DirPropFlag(RLO);
-    private static final int MASK_EXPLICIT = MASK_LRX|MASK_RLX|DirPropFlag(PDF);
+    private static final int MASK_EXPLICIT = DirPropFlag(LRE)|DirPropFlag(LRO)|DirPropFlag(RLE)|DirPropFlag(RLO)|DirPropFlag(PDF);
     private static final int MASK_BN_EXPLICIT = DirPropFlag(BN)|MASK_EXPLICIT;
 
+    /* explicit isolate codes */
+    private static final int MASK_ISO = DirPropFlag(LRI)|DirPropFlag(RLI)|DirPropFlag(FSI)|DirPropFlag(PDI);
+
     /* paragraph and segment separators */
     private static final int MASK_B_S = DirPropFlag(B)|DirPropFlag(S);
 
     /* all types that are counted as White Space or Neutral in some steps */
-    static final int MASK_WS = MASK_B_S|DirPropFlag(WS)|MASK_BN_EXPLICIT;
-    private static final int MASK_N = DirPropFlag(ON)|MASK_WS;
+    static final int MASK_WS = MASK_B_S|DirPropFlag(WS)|MASK_BN_EXPLICIT|MASK_ISO;
 
     /* types that are neutrals or could becomes neutrals in (Wn) */
-    private static final int MASK_POSSIBLE_N = DirPropFlag(CS)|DirPropFlag(ES)|DirPropFlag(ET)|MASK_N;
+    private static final int MASK_POSSIBLE_N = DirPropFlag(ON)|DirPropFlag(CS)|DirPropFlag(ES)|DirPropFlag(ET)|MASK_WS;
 
     /*
      * These types may be changed to "e",
      * the embedding type (L or R) of the run,
      * in the Bidi algorithm (N2)
      */
-    static final int MASK_EMBEDDING = DirPropFlag(NSM)|MASK_POSSIBLE_N;
+    private static final int MASK_EMBEDDING = DirPropFlag(NSM)|MASK_POSSIBLE_N;
 
     /*
      *  the dirProp's L and R are defined to 0 and 1 values in UCharacterDirection.java
@@ -968,30 +1214,25 @@
 
     private static boolean IsDefaultLevel(byte level)
     {
-        return ((level & INTERNAL_LEVEL_DEFAULT_LTR) == INTERNAL_LEVEL_DEFAULT_LTR);
-    }
-
-    byte GetParaLevelAt(int index)
-    {
-        return (defaultParaLevel != 0) ?
-                (byte)(dirProps[index]>>CONTEXT_RTL_SHIFT) : paraLevel;
+        return ((level & LEVEL_DEFAULT_LTR) == LEVEL_DEFAULT_LTR);
     }
 
     static boolean IsBidiControlChar(int c)
     {
         /* check for range 0x200c to 0x200f (ZWNJ, ZWJ, LRM, RLM) or
                            0x202a to 0x202e (LRE, RLE, PDF, LRO, RLO) */
-        return (((c & 0xfffffffc) == 0x200c) || ((c >= 0x202a) && (c <= 0x202e)));
+        return (((c & 0xfffffffc) == 0x200c) || ((c >= 0x202a) && (c <= 0x202e))
+                                             || ((c >= 0x2066) && (c <= 0x2069)));
     }
 
-    public void verifyValidPara()
+    void verifyValidPara()
     {
-        if (this != this.paraBidi) {
-            throw new IllegalStateException("");
+        if (!(this == this.paraBidi)) {
+            throw new IllegalStateException();
         }
     }
 
-    public void verifyValidParaOrLine()
+    void verifyValidParaOrLine()
     {
         BidiBase para = this.paraBidi;
         /* verify Para */
@@ -1004,7 +1245,7 @@
         }
     }
 
-    public void verifyRange(int index, int start, int limit)
+    void verifyRange(int index, int start, int limit)
     {
         if (index < start || index >= limit) {
             throw new IllegalArgumentException("Value " + index +
@@ -1012,14 +1253,6 @@
         }
     }
 
-    public void verifyIndex(int index, int start, int limit)
-    {
-        if (index < start || index >= limit) {
-            throw new ArrayIndexOutOfBoundsException("Index " + index +
-                      " is out of range " + start + " to " + limit);
-        }
-    }
-
     /**
      * Allocate a <code>Bidi</code> object with preallocated memory
      * for internal structures.
@@ -1051,7 +1284,7 @@
      * @stable ICU 3.8
      */
     public BidiBase(int maxLength, int maxRunCount)
-     {
+    {
         /* check the argument values */
         if (maxLength < 0 || maxRunCount < 0) {
             throw new IllegalArgumentException();
@@ -1075,12 +1308,7 @@
         direction = 0;
         */
         /* get Bidi properties */
-        try {
-            bdp = UBiDiProps.getSingleton();
-        }
-        catch (IOException e) {
-            throw new MissingResourceException(e.getMessage(), "(BidiProps)", "");
-        }
+        bdp = UBiDiProps.INSTANCE;
 
         /* allocate memory for arrays as requested */
         if (maxLength > 0) {
@@ -1180,18 +1408,68 @@
         getLevelsMemory(true, len);
     }
 
-    private void getInitialParasMemory(int len)
-    {
-        Object array = getMemory("Paras", parasMemory, Integer.TYPE, true, len);
-        parasMemory = (int[]) array;
-    }
-
     private void getInitialRunsMemory(int len)
     {
         getRunsMemory(true, len);
     }
 
-/* perform (P2)..(P3) ------------------------------------------------------- */
+    /**
+     * Is this <code>Bidi</code> object set to perform the inverse Bidi
+     * algorithm?
+     * <p>Note: calling this method after setting the reordering mode with
+     * <code>setReorderingMode</code> will return <code>true</code> if the
+     * reordering mode was set to
+     * <code>REORDER_INVERSE_NUMBERS_AS_L</code>, <code>false</code>
+     * for all other values.</p>
+     *
+     * @return <code>true</code> if the <code>Bidi</code> object is set to
+     * perform the inverse Bidi algorithm by handling numbers as L.
+     *
+     * @see #setInverse
+     * @see #setReorderingMode
+     * @see #REORDER_INVERSE_NUMBERS_AS_L
+     * @stable ICU 3.8
+     */
+    public boolean isInverse() {
+        return isInverse;
+    }
+
+    /* perform (P2)..(P3) ------------------------------------------------------- */
+
+    /*
+     * Check that there are enough entries in the arrays paras_limit and paras_level
+     */
+    private void checkParaCount() {
+        int[] saveLimits;
+        byte[] saveLevels;
+        int count = paraCount;
+        if (count <= paras_level.length)
+            return;
+        int oldLength = paras_level.length;
+        saveLimits = paras_limit;
+        saveLevels = paras_level;
+        try {
+            paras_limit = new int[count * 2];
+            paras_level = new byte[count * 2];
+        } catch (Exception e) {
+            throw new OutOfMemoryError("Failed to allocate memory for paras");
+        }
+        System.arraycopy(saveLimits, 0, paras_limit, 0, oldLength);
+        System.arraycopy(saveLevels, 0, paras_level, 0, oldLength);
+    }
+
+    /*
+     * Get the directional properties for the text, calculate the flags bit-set, and
+     * determine the paragraph level if necessary (in paras_level[i]).
+     * FSI initiators are also resolved and their dirProp replaced with LRI or RLI.
+     * When encountering an FSI, it is initially replaced with an LRI, which is the
+     * default. Only if a strong R or AL is found within its scope will the LRI be
+     * replaced by an RLI.
+     */
+    static final int NOT_SEEKING_STRONG = 0;        /* 0: not contextual paraLevel, not after FSI */
+    static final int SEEKING_STRONG_FOR_PARA = 1;   /* 1: looking for first strong char in para */
+    static final int SEEKING_STRONG_FOR_FSI = 2;    /* 2: looking for first strong after FSI */
+    static final int LOOKING_FOR_PDI = 3;           /* 3: found strong after FSI, looking for PDI */
 
     private void getDirProps()
     {
@@ -1199,32 +1477,44 @@
         flags = 0;          /* collect all directionalities in the text */
         int uchar;
         byte dirProp;
-        byte paraDirDefault = 0;   /* initialize to avoid compiler warnings */
+        byte defaultParaLevel = 0;   /* initialize to avoid compiler warnings */
         boolean isDefaultLevel = IsDefaultLevel(paraLevel);
         /* for inverse Bidi, the default para level is set to RTL if there is a
            strong R or AL character at either end of the text                */
+        boolean isDefaultLevelInverse=isDefaultLevel &&
+                (reorderingMode == REORDER_INVERSE_LIKE_DIRECT ||
+                 reorderingMode == REORDER_INVERSE_FOR_NUMBERS_SPECIAL);
         lastArabicPos = -1;
-        controlCount = 0;
-
-        final int NOT_CONTEXTUAL = 0;         /* 0: not contextual paraLevel */
-        final int LOOKING_FOR_STRONG = 1;     /* 1: looking for first strong char */
-        final int FOUND_STRONG_CHAR = 2;      /* 2: found first strong char       */
-
-        int state;
-        int paraStart = 0;                    /* index of first char in paragraph */
-        byte paraDir;                         /* == CONTEXT_RTL within paragraphs
-                                                 starting with strong R char      */
-        byte lastStrongDir=0;                 /* for default level & inverse Bidi */
-        int lastStrongLTR=0;                  /* for STREAMING option             */
+        int controlCount = 0;
+        boolean removeBidiControls = (reorderingOptions & OPTION_REMOVE_CONTROLS) != 0;
+
+        byte state;
+        byte lastStrong = ON;           /* for default level & inverse Bidi */
+    /* The following stacks are used to manage isolate sequences. Those
+       sequences may be nested, but obviously never more deeply than the
+       maximum explicit embedding level.
+       lastStack is the index of the last used entry in the stack. A value of -1
+       means that there is no open isolate sequence.
+       lastStack is reset to -1 on paragraph boundaries. */
+    /* The following stack contains the position of the initiator of
+       each open isolate sequence */
+        int[] isolateStartStack= new int[MAX_EXPLICIT_LEVEL+1];
+    /* The following stack contains the last known state before
+       encountering the initiator of an isolate sequence */
+        byte[] previousStateStack = new byte[MAX_EXPLICIT_LEVEL+1];
+        int  stackLast=-1;
+
+        if ((reorderingOptions & OPTION_STREAMING) != 0)
+            length = 0;
+        defaultParaLevel = (byte)(paraLevel & 1);
 
         if (isDefaultLevel) {
-            paraDirDefault = ((paraLevel & 1) != 0) ? CONTEXT_RTL : 0;
-            paraDir = paraDirDefault;
-            lastStrongDir = paraDirDefault;
-            state = LOOKING_FOR_STRONG;
+            paras_level[0] = defaultParaLevel;
+            lastStrong = defaultParaLevel;
+            state = SEEKING_STRONG_FOR_PARA;
         } else {
-            state = NOT_CONTEXTUAL;
-            paraDir = 0;
+            paras_level[0] = paraLevel;
+            state = NOT_SEEKING_STRONG;
         }
         /* count paragraphs and determine the paragraph level (P2..P3) */
         /*
@@ -1236,90 +1526,509 @@
         for (i = 0; i < originalLength; /* i is incremented in the loop */) {
             i0 = i;                     /* index of first code unit */
             uchar = UTF16.charAt(text, 0, originalLength, i);
-            i += Character.charCount(uchar);
+            i += UTF16.getCharCount(uchar);
             i1 = i - 1; /* index of last code unit, gets the directional property */
 
-            dirProp = (byte)bdp.getClass(uchar);
-
+            dirProp = (byte)getCustomizedClass(uchar);
             flags |= DirPropFlag(dirProp);
-            dirProps[i1] = (byte)(dirProp | paraDir);
+            dirProps[i1] = dirProp;
             if (i1 > i0) {     /* set previous code units' properties to BN */
                 flags |= DirPropFlag(BN);
                 do {
-                    dirProps[--i1] = (byte)(BN | paraDir);
+                    dirProps[--i1] = BN;
                 } while (i1 > i0);
             }
-            if (state == LOOKING_FOR_STRONG) {
-                if (dirProp == L) {
-                    state = FOUND_STRONG_CHAR;
-                    if (paraDir != 0) {
-                        paraDir = 0;
-                        for (i1 = paraStart; i1 < i; i1++) {
-                            dirProps[i1] &= ~CONTEXT_RTL;
-                        }
-                    }
-                    continue;
-                }
-                if (dirProp == R || dirProp == AL) {
-                    state = FOUND_STRONG_CHAR;
-                    if (paraDir == 0) {
-                        paraDir = CONTEXT_RTL;
-                        for (i1 = paraStart; i1 < i; i1++) {
-                            dirProps[i1] |= CONTEXT_RTL;
-                        }
-                    }
-                    continue;
-                }
+            if (removeBidiControls && IsBidiControlChar(uchar)) {
+                controlCount++;
             }
             if (dirProp == L) {
-                lastStrongDir = 0;
-                lastStrongLTR = i;      /* i is index to next character */
-            }
-            else if (dirProp == R) {
-                lastStrongDir = CONTEXT_RTL;
-            }
-            else if (dirProp == AL) {
-                lastStrongDir = CONTEXT_RTL;
-                lastArabicPos = i-1;
+                if (state == SEEKING_STRONG_FOR_PARA) {
+                    paras_level[paraCount - 1] = 0;
+                    state = NOT_SEEKING_STRONG;
+                }
+                else if (state == SEEKING_STRONG_FOR_FSI) {
+                    if (stackLast <= MAX_EXPLICIT_LEVEL) {
+                        /* no need for next statement, already set by default */
+                        /* dirProps[isolateStartStack[stackLast]] = LRI; */
+                        flags |= DirPropFlag(LRI);
+                    }
+                    state = LOOKING_FOR_PDI;
+                }
+                lastStrong = L;
+                continue;
             }
-            else if (dirProp == B) {
-                if (i < originalLength) {   /* B not last char in text */
-                    if (!((uchar == (int)CR) && (text[i] == (int)LF))) {
-                        paraCount++;
+            if (dirProp == R || dirProp == AL) {
+                if (state == SEEKING_STRONG_FOR_PARA) {
+                    paras_level[paraCount - 1] = 1;
+                    state = NOT_SEEKING_STRONG;
+                }
+                else if (state == SEEKING_STRONG_FOR_FSI) {
+                    if (stackLast <= MAX_EXPLICIT_LEVEL) {
+                        dirProps[isolateStartStack[stackLast]] = RLI;
+                        flags |= DirPropFlag(RLI);
                     }
-                    if (isDefaultLevel) {
-                        state=LOOKING_FOR_STRONG;
-                        paraStart = i;        /* i is index to next character */
-                        paraDir = paraDirDefault;
-                        lastStrongDir = paraDirDefault;
+                    state = LOOKING_FOR_PDI;
+                }
+                lastStrong = R;
+                if (dirProp == AL)
+                    lastArabicPos = i - 1;
+                continue;
+            }
+            if (dirProp >= FSI && dirProp <= RLI) { /* FSI, LRI or RLI */
+                stackLast++;
+                if (stackLast <= MAX_EXPLICIT_LEVEL) {
+                    isolateStartStack[stackLast] = i - 1;
+                    previousStateStack[stackLast] = state;
+                }
+                if (dirProp == FSI) {
+                    dirProps[i-1] = LRI;    /* default if no strong char */
+                    state = SEEKING_STRONG_FOR_FSI;
+                }
+                else
+                    state = LOOKING_FOR_PDI;
+                continue;
+            }
+            if (dirProp == PDI) {
+                if (state == SEEKING_STRONG_FOR_FSI) {
+                    if (stackLast <= MAX_EXPLICIT_LEVEL) {
+                        /* no need for next statement, already set by default */
+                        /* dirProps[isolateStartStack[stackLast]] = LRI; */
+                        flags |= DirPropFlag(LRI);
                     }
                 }
+                if (stackLast >= 0) {
+                    if (stackLast <= MAX_EXPLICIT_LEVEL)
+                        state = previousStateStack[stackLast];
+                    stackLast--;
+                }
+                continue;
             }
+            if (dirProp == B) {
+                if (i < originalLength && uchar == CR && text[i] == LF) /* do nothing on the CR */
+                    continue;
+                paras_limit[paraCount - 1] = i;
+                if (isDefaultLevelInverse && lastStrong == R)
+                    paras_level[paraCount - 1] = 1;
+                if ((reorderingOptions & OPTION_STREAMING) != 0) {
+                /* When streaming, we only process whole paragraphs
+                   thus some updates are only done on paragraph boundaries */
+                   length = i;          /* i is index to next character */
+                   this.controlCount = controlCount;
+                }
+                if (i < originalLength) {       /* B not last char in text */
+                    paraCount++;
+                    checkParaCount();   /* check that there is enough memory for a new para entry */
+                    if (isDefaultLevel) {
+                        paras_level[paraCount - 1] = defaultParaLevel;
+                        state = SEEKING_STRONG_FOR_PARA;
+                        lastStrong = defaultParaLevel;
+                    } else {
+                        paras_level[paraCount - 1] = paraLevel;
+                        state = NOT_SEEKING_STRONG;
+                    }
+                    stackLast = -1;
+                }
+                continue;
+            }
+        }
+        /* +Ignore still open isolate sequences with overflow */
+      if (stackLast > MAX_EXPLICIT_LEVEL) {
+            stackLast = MAX_EXPLICIT_LEVEL;
+            state=SEEKING_STRONG_FOR_FSI;   /* to be on the safe side */
+        }
+        /* Resolve direction of still unresolved open FSI sequences */
+        while (stackLast >= 0) {
+            if (state == SEEKING_STRONG_FOR_FSI) {
+                /* no need for next statement, already set by default */
+                /* dirProps[isolateStartStack[stackLast]] = LRI; */
+                flags |= DirPropFlag(LRI);
+                break;
+            }
+            state = previousStateStack[stackLast];
+            stackLast--;
+        }
+        /* When streaming, ignore text after the last paragraph separator */
+        if ((reorderingOptions & OPTION_STREAMING) != 0) {
+            if (length < originalLength)
+                paraCount--;
+        } else {
+            paras_limit[paraCount - 1] = originalLength;
+            this.controlCount = controlCount;
+        }
+        /* For inverse bidi, default para direction is RTL if there is
+           a strong R or AL at either end of the paragraph */
+        if (isDefaultLevelInverse && lastStrong == R) {
+            paras_level[paraCount - 1] = 1;
         }
         if (isDefaultLevel) {
-            paraLevel = GetParaLevelAt(0);
+            paraLevel = paras_level[0];
         }
-
-        /* The following line does nothing new for contextual paraLevel, but is
-           needed for absolute paraLevel.                               */
-        flags |= DirPropFlagLR(paraLevel);
+        /* The following is needed to resolve the text direction for default level
+           paragraphs containing no strong character */
+        for (i = 0; i < paraCount; i++)
+            flags |= DirPropFlagLR(paras_level[i]);
 
         if (orderParagraphsLTR && (flags & DirPropFlag(B)) != 0) {
             flags |= DirPropFlag(L);
         }
     }
 
+    /* determine the paragraph level at position index */
+    byte GetParaLevelAt(int pindex)
+    {
+        if (defaultParaLevel == 0 || pindex < paras_limit[0])
+            return paraLevel;
+        int i;
+        for (i = 1; i < paraCount; i++)
+            if (pindex < paras_limit[i])
+                break;
+        if (i >= paraCount)
+            i = paraCount - 1;
+        return paras_level[i];
+    }
+
+    /* Functions for handling paired brackets ----------------------------------- */
+
+    /* In the isoRuns array, the first entry is used for text outside of any
+       isolate sequence.  Higher entries are used for each more deeply nested
+       isolate sequence. isoRunLast is the index of the last used entry.  The
+       openings array is used to note the data of opening brackets not yet
+       matched by a closing bracket, or matched but still susceptible to change
+       level.
+       Each isoRun entry contains the index of the first and
+       one-after-last openings entries for pending opening brackets it
+       contains.  The next openings entry to use is the one-after-last of the
+       most deeply nested isoRun entry.
+       isoRun entries also contain their current embedding level and the last
+       encountered strong character, since these will be needed to resolve
+       the level of paired brackets.  */
+
+    private void bracketInit(BracketData bd) {
+        bd.isoRunLast = 0;
+        bd.isoRuns[0] = new IsoRun();
+        bd.isoRuns[0].start = 0;
+        bd.isoRuns[0].limit = 0;
+        bd.isoRuns[0].level = GetParaLevelAt(0);
+        bd.isoRuns[0].lastStrong = bd.isoRuns[0].lastBase = bd.isoRuns[0].contextDir = (byte)(GetParaLevelAt(0) & 1);
+        bd.isoRuns[0].contextPos = 0;
+        bd.openings = new Opening[SIMPLE_PARAS_COUNT];
+        bd.isNumbersSpecial = reorderingMode == REORDER_NUMBERS_SPECIAL ||
+                              reorderingMode == REORDER_INVERSE_FOR_NUMBERS_SPECIAL;
+    }
+
+    /* paragraph boundary */
+    private void bracketProcessB(BracketData bd, byte level) {
+        bd.isoRunLast = 0;
+        bd.isoRuns[0].limit = 0;
+        bd.isoRuns[0].level = level;
+        bd.isoRuns[0].lastStrong = bd.isoRuns[0].lastBase = bd.isoRuns[0].contextDir = (byte)(level & 1);
+        bd.isoRuns[0].contextPos = 0;
+    }
+
+    /* LRE, LRO, RLE, RLO, PDF */
+    private void bracketProcessBoundary(BracketData bd, int lastCcPos,
+                                        byte contextLevel, byte embeddingLevel) {
+        IsoRun pLastIsoRun = bd.isoRuns[bd.isoRunLast];
+        if ((DirPropFlag(dirProps[lastCcPos]) & MASK_ISO) != 0) /* after an isolate */
+            return;
+        if (NoOverride(embeddingLevel) > NoOverride(contextLevel))  /* not a PDF */
+            contextLevel = embeddingLevel;
+        pLastIsoRun.limit = pLastIsoRun.start;
+        pLastIsoRun.level = embeddingLevel;
+        pLastIsoRun.lastStrong = pLastIsoRun.lastBase = pLastIsoRun.contextDir = (byte)(contextLevel & 1);
+        pLastIsoRun.contextPos = lastCcPos;
+    }
+
+    /* LRI or RLI */
+    private void bracketProcessLRI_RLI(BracketData bd, byte level) {
+        IsoRun pLastIsoRun = bd.isoRuns[bd.isoRunLast];
+        short lastLimit;
+        pLastIsoRun.lastBase = ON;
+        lastLimit = pLastIsoRun.limit;
+        bd.isoRunLast++;
+        pLastIsoRun = bd.isoRuns[bd.isoRunLast];
+        if (pLastIsoRun == null)
+            pLastIsoRun = bd.isoRuns[bd.isoRunLast] = new IsoRun();
+        pLastIsoRun.start = pLastIsoRun.limit = lastLimit;
+        pLastIsoRun.level = level;
+        pLastIsoRun.lastStrong = pLastIsoRun.lastBase = pLastIsoRun.contextDir = (byte)(level & 1);
+        pLastIsoRun.contextPos = 0;
+    }
+
+    /* PDI */
+    private void bracketProcessPDI(BracketData bd) {
+        IsoRun pLastIsoRun;
+        bd.isoRunLast--;
+        pLastIsoRun = bd.isoRuns[bd.isoRunLast];
+        pLastIsoRun.lastBase = ON;
+    }
+
+    /* newly found opening bracket: create an openings entry */
+    private void bracketAddOpening(BracketData bd, char match, int position) {
+        IsoRun pLastIsoRun = bd.isoRuns[bd.isoRunLast];
+        Opening pOpening;
+        if (pLastIsoRun.limit >= bd.openings.length) {  /* no available new entry */
+            Opening[] saveOpenings = bd.openings;
+            int count;
+            try {
+                count = bd.openings.length;
+                bd.openings = new Opening[count * 2];
+            } catch (Exception e) {
+                throw new OutOfMemoryError("Failed to allocate memory for openings");
+            }
+            System.arraycopy(saveOpenings, 0, bd.openings, 0, count);
+        }
+        pOpening = bd.openings[pLastIsoRun.limit];
+        if (pOpening == null)
+            pOpening = bd.openings[pLastIsoRun.limit]= new Opening();
+        pOpening.position = position;
+        pOpening.match = match;
+        pOpening.contextDir = pLastIsoRun.contextDir;
+        pOpening.contextPos = pLastIsoRun.contextPos;
+        pOpening.flags = 0;
+        pLastIsoRun.limit++;
+    }
+
+    /* change N0c1 to N0c2 when a preceding bracket is assigned the embedding level */
+    private void fixN0c(BracketData bd, int openingIndex, int newPropPosition, byte newProp) {
+        /* This function calls itself recursively */
+        IsoRun pLastIsoRun = bd.isoRuns[bd.isoRunLast];
+        Opening qOpening;
+        int k, openingPosition, closingPosition;
+        for (k = openingIndex+1; k < pLastIsoRun.limit; k++) {
+            qOpening = bd.openings[k];
+            if (qOpening.match >= 0)    /* not an N0c match */
+                continue;
+            if (newPropPosition < qOpening.contextPos)
+                break;
+            if (newPropPosition >= qOpening.position)
+                continue;
+            if (newProp == qOpening.contextDir)
+                break;
+            openingPosition = qOpening.position;
+            dirProps[openingPosition] = newProp;
+            closingPosition = -(qOpening.match);
+            dirProps[closingPosition] = newProp;
+            qOpening.match = 0;                                 /* prevent further changes */
+            fixN0c(bd, k, openingPosition, newProp);
+            fixN0c(bd, k, closingPosition, newProp);
+        }
+    }
+
+    /* process closing bracket; return L or R if N0b or N0c, ON if N0d */
+    private byte bracketProcessClosing(BracketData bd, int openIdx, int position) {
+        IsoRun pLastIsoRun = bd.isoRuns[bd.isoRunLast];
+        Opening pOpening, qOpening;
+        byte direction;
+        boolean stable;
+        byte newProp;
+        pOpening = bd.openings[openIdx];
+        direction = (byte)(pLastIsoRun.level & 1);
+        stable = true;          /* assume stable until proved otherwise */
+
+        /* The stable flag is set when brackets are paired and their
+           level is resolved and cannot be changed by what will be
+           found later in the source string.
+           An unstable match can occur only when applying N0c, where
+           the resolved level depends on the preceding context, and
+           this context may be affected by text occurring later.
+           Example: RTL paragraph containing:  abc[(latin) HEBREW]
+           When the closing parenthesis is encountered, it appears
+           that N0c1 must be applied since 'abc' sets an opposite
+           direction context and both parentheses receive level 2.
+           However, when the closing square bracket is processed,
+           N0b applies because of 'HEBREW' being included within the
+           brackets, thus the square brackets are treated like R and
+           receive level 1. However, this changes the preceding
+           context of the opening parenthesis, and it now appears
+           that N0c2 must be applied to the parentheses rather than
+           N0c1. */
+
+            if ((direction == 0 && (pOpening.flags & FOUND_L) > 0) ||
+                (direction == 1 && (pOpening.flags & FOUND_R) > 0)) {   /* N0b */
+                newProp = direction;
+            }
+            else if ((pOpening.flags & (FOUND_L | FOUND_R)) != 0) {     /* N0c */
+                    /* it is stable if there is no preceding text or in
+                       conditions too complicated and not worth checking */
+                    stable = (openIdx == pLastIsoRun.start);
+                if (direction != pOpening.contextDir)
+                    newProp = pOpening.contextDir;                      /* N0c1 */
+                else
+                    newProp = direction;                                /* N0c2 */
+            } else {
+            /* forget this and any brackets nested within this pair */
+            pLastIsoRun.limit = (short)openIdx;
+            return ON;                                                  /* N0d */
+        }
+        dirProps[pOpening.position] = newProp;
+        dirProps[position] = newProp;
+        /* Update nested N0c pairs that may be affected */
+        fixN0c(bd, openIdx, pOpening.position, newProp);
+        if (stable) {
+            pLastIsoRun.limit = (short)openIdx; /* forget any brackets nested within this pair */
+            /* remove lower located synonyms if any */
+            while (pLastIsoRun.limit > pLastIsoRun.start &&
+                   bd.openings[pLastIsoRun.limit - 1].position == pOpening.position)
+                pLastIsoRun.limit--;
+        } else {
+            int k;
+            pOpening.match = -position;
+            /* neutralize lower located synonyms if any */
+            k = openIdx - 1;
+            while (k >= pLastIsoRun.start &&
+                   bd.openings[k].position == pOpening.position)
+                bd.openings[k--].match = 0;
+            /* neutralize any unmatched opening between the current pair;
+               this will also neutralize higher located synonyms if any */
+            for (k = openIdx + 1; k < pLastIsoRun.limit; k++) {
+                qOpening =bd.openings[k];
+                if (qOpening.position >= position)
+                    break;
+                if (qOpening.match > 0)
+                    qOpening.match = 0;
+            }
+        }
+        return newProp;
+    }
+
+    /* handle strong characters, digits and candidates for closing brackets */
+    private void bracketProcessChar(BracketData bd, int position) {
+        IsoRun pLastIsoRun = bd.isoRuns[bd.isoRunLast];
+        byte dirProp, newProp;
+        byte level;
+        dirProp = dirProps[position];
+        if (dirProp == ON) {
+            char c, match;
+            int idx;
+            /* First see if it is a matching closing bracket. Hopefully, this is
+               more efficient than checking if it is a closing bracket at all */
+            c = text[position];
+            for (idx = pLastIsoRun.limit - 1; idx >= pLastIsoRun.start; idx--) {
+                if (bd.openings[idx].match != c)
+                    continue;
+                /* We have a match */
+                newProp = bracketProcessClosing(bd, idx, position);
+                if(newProp == ON) {         /* N0d */
+                    c = 0;          /* prevent handling as an opening */
+                    break;
+                }
+                pLastIsoRun.lastBase = ON;
+                pLastIsoRun.contextDir = newProp;
+                pLastIsoRun.contextPos = position;
+                level = levels[position];
+                if ((level & LEVEL_OVERRIDE) != 0) {    /* X4, X5 */
+                    short flag;
+                    int i;
+                    newProp = (byte)(level & 1);
+                    pLastIsoRun.lastStrong = newProp;
+                    flag = (short)DirPropFlag(newProp);
+                    for (i = pLastIsoRun.start; i < idx; i++)
+                        bd.openings[i].flags |= flag;
+                    /* matching brackets are not overridden by LRO/RLO */
+                    levels[position] &= ~LEVEL_OVERRIDE;
+                }
+                /* matching brackets are not overridden by LRO/RLO */
+                levels[bd.openings[idx].position] &= ~LEVEL_OVERRIDE;
+                return;
+            }
+            /* We get here only if the ON character is not a matching closing
+               bracket or it is a case of N0d */
+            /* Now see if it is an opening bracket */
+            if (c != 0) {
+                match = (char)UCharacter.getBidiPairedBracket(c); /* get the matching char */
+            } else {
+                match = 0;
+            }
+            if (match != c &&               /* has a matching char */
+                UCharacter.getIntPropertyValue(c, BIDI_PAIRED_BRACKET_TYPE) ==
+                    /* opening bracket */         BidiPairedBracketType.OPEN) {
+                /* special case: process synonyms
+                   create an opening entry for each synonym */
+                if (match == 0x232A) {      /* RIGHT-POINTING ANGLE BRACKET */
+                    bracketAddOpening(bd, (char)0x3009, position);
+                }
+                else if (match == 0x3009) { /* RIGHT ANGLE BRACKET */
+                    bracketAddOpening(bd, (char)0x232A, position);
+                }
+                bracketAddOpening(bd, match, position);
+            }
+        }
+        level = levels[position];
+        if ((level & LEVEL_OVERRIDE) != 0) {    /* X4, X5 */
+            newProp = (byte)(level & 1);
+            if (dirProp != S && dirProp != WS && dirProp != ON)
+                dirProps[position] = newProp;
+            pLastIsoRun.lastBase = newProp;
+            pLastIsoRun.lastStrong = newProp;
+            pLastIsoRun.contextDir = newProp;
+            pLastIsoRun.contextPos = position;
+        }
+        else if (dirProp <= R || dirProp == AL) {
+            newProp = DirFromStrong(dirProp);
+            pLastIsoRun.lastBase = dirProp;
+            pLastIsoRun.lastStrong = dirProp;
+            pLastIsoRun.contextDir = newProp;
+            pLastIsoRun.contextPos = position;
+        }
+        else if(dirProp == EN) {
+            pLastIsoRun.lastBase = EN;
+            if (pLastIsoRun.lastStrong == L) {
+                newProp = L;                    /* W7 */
+                if (!bd.isNumbersSpecial)
+                    dirProps[position] = ENL;
+                pLastIsoRun.contextDir = L;
+                pLastIsoRun.contextPos = position;
+            }
+            else {
+                newProp = R;                    /* N0 */
+                if (pLastIsoRun.lastStrong == AL)
+                    dirProps[position] = AN;    /* W2 */
+                else
+                    dirProps[position] = ENR;
+                pLastIsoRun.contextDir = R;
+                pLastIsoRun.contextPos = position;
+            }
+        }
+        else if (dirProp == AN) {
+            newProp = R;                        /* N0 */
+            pLastIsoRun.lastBase = AN;
+            pLastIsoRun.contextDir = R;
+            pLastIsoRun.contextPos = position;
+        }
+        else if (dirProp == NSM) {
+            /* if the last real char was ON, change NSM to ON so that it
+               will stay ON even if the last real char is a bracket which
+               may be changed to L or R */
+            newProp = pLastIsoRun.lastBase;
+            if (newProp == ON)
+                dirProps[position] = newProp;
+        }
+        else {
+            newProp = dirProp;
+            pLastIsoRun.lastBase = dirProp;
+        }
+        if (newProp <= R || newProp == AL) {
+            int i;
+            short flag = (short)DirPropFlag(DirFromStrong(newProp));
+            for (i = pLastIsoRun.start; i < pLastIsoRun.limit; i++)
+                if (position > bd.openings[i].position)
+                    bd.openings[i].flags |= flag;
+        }
+    }
+
     /* perform (X1)..(X9) ------------------------------------------------------- */
 
     /* determine if the text is mixed-directional or single-directional */
     private byte directionFromFlags() {
+
         /* if the text contains AN and neutrals, then some neutrals may become RTL */
         if (!((flags & MASK_RTL) != 0 ||
               ((flags & DirPropFlag(AN)) != 0 &&
                (flags & MASK_POSSIBLE_N) != 0))) {
-            return Bidi.DIRECTION_LEFT_TO_RIGHT;
+            return LTR;
         } else if ((flags & MASK_LTR) == 0) {
-            return Bidi.DIRECTION_RIGHT_TO_LEFT;
+            return RTL;
         } else {
             return MIXED;
         }
@@ -1330,16 +2039,16 @@
      * Recalculate the flags to have them reflect the real properties
      * after taking the explicit embeddings into account.
      *
-     * The Bidi algorithm is designed to result in the same behavior whether embedding
+     * The BiDi algorithm is designed to result in the same behavior whether embedding
      * levels are externally specified (from "styled text", supposedly the preferred
-     * method) or set by explicit embedding codes (LRx, RLx, PDF) in the plain text.
-     * That is why (X9) instructs to remove all explicit codes (and BN).
-     * However, in a real implementation, this removal of these codes and their index
+     * method) or set by explicit embedding codes (LRx, RLx, PDF, FSI, PDI) in the plain text.
+     * That is why (X9) instructs to remove all not-isolate explicit codes (and BN).
+     * However, in a real implementation, the removal of these codes and their index
      * positions in the plain text is undesirable since it would result in
      * reallocated, reindexed text.
      * Instead, this implementation leaves the codes in there and just ignores them
      * in the subsequent processing.
-     * In order to get the same reordering behavior, positions with a BN or an
+     * In order to get the same reordering behavior, positions with a BN or a not-isolate
      * explicit embedding code just get the same level assigned as the last "real"
      * character.
      *
@@ -1351,185 +2060,281 @@
      * This limits the scope of the implicit rules in effectively
      * the same way as the run limits.
      *
-     * Instead, this implementation does not modify these codes.
+     * Instead, this implementation does not modify these codes, except for
+     * paired brackets whose properties (ON) may be replaced by L or R.
      * On one hand, the paragraph has to be scanned for same-level-runs, but
      * on the other hand, this saves another loop to reset these codes,
      * or saves making and modifying a copy of dirProps[].
      *
      *
-     * Note that (Pn) and (Xn) changed significantly from version 4 of the Bidi algorithm.
+     * Note that (Pn) and (Xn) changed significantly from version 4 of the BiDi algorithm.
      *
      *
      * Handling the stack of explicit levels (Xn):
      *
-     * With the Bidi stack of explicit levels,
-     * as pushed with each LRE, RLE, LRO, and RLO and popped with each PDF,
-     * the explicit level must never exceed MAX_EXPLICIT_LEVEL==61.
+     * With the BiDi stack of explicit levels, as pushed with each
+     * LRE, RLE, LRO, RLO, LRI, RLI and FSI and popped with each PDF and PDI,
+     * the explicit level must never exceed MAX_EXPLICIT_LEVEL.
      *
      * In order to have a correct push-pop semantics even in the case of overflows,
-     * there are two overflow counters:
-     * - countOver60 is incremented with each LRx at level 60
-     * - from level 60, one RLx increases the level to 61
-     * - countOver61 is incremented with each LRx and RLx at level 61
-     *
-     * Popping levels with PDF must work in the opposite order so that level 61
-     * is correct at the correct point. Underflows (too many PDFs) must be checked.
+     * overflow counters and a valid isolate counter are used as described in UAX#9
+     * section 3.3.2 "Explicit Levels and Directions".
      *
      * This implementation assumes that MAX_EXPLICIT_LEVEL is odd.
+     *
+     * Returns the direction
+     *
      */
     private byte resolveExplicitLevels() {
         int i = 0;
         byte dirProp;
         byte level = GetParaLevelAt(0);
-
         byte dirct;
-        int paraIndex = 0;
+        isolateCount = 0;
 
         /* determine if the text is mixed-directional or single-directional */
         dirct = directionFromFlags();
 
-        /* we may not need to resolve any explicit levels, but for multiple
-           paragraphs we want to loop on all chars to set the para boundaries */
-        if ((dirct != MIXED) && (paraCount == 1)) {
+        /* we may not need to resolve any explicit levels */
+        if (dirct != MIXED) {
             /* not mixed directionality: levels don't matter - trailingWSStart will be 0 */
-        } else if ((paraCount == 1) &&
-                   ((flags & MASK_EXPLICIT) == 0)) {
-            /* mixed, but all characters are at the same embedding level */
-            /* or we are in "inverse Bidi" */
-            /* and we don't have contextual multiple paragraphs with some B char */
+            return dirct;
+        }
+
+        if (reorderingMode > REORDER_LAST_LOGICAL_TO_VISUAL) {
+            /* inverse BiDi: mixed, but all characters are at the same embedding level */
             /* set all levels to the paragraph level */
-            for (i = 0; i < length; ++i) {
-                levels[i] = level;
+            int paraIndex, start, limit;
+            for (paraIndex = 0; paraIndex < paraCount; paraIndex++) {
+                if (paraIndex == 0)
+                    start = 0;
+                else
+                    start = paras_limit[paraIndex - 1];
+                limit = paras_limit[paraIndex];
+                level = paras_level[paraIndex];
+                for (i = start; i < limit; i++)
+                    levels[i] =level;
             }
-        } else {
-            /* continue to perform (Xn) */
-
-            /* (X1) level is set for all codes, embeddingLevel keeps track of the push/pop operations */
-            /* both variables may carry the LEVEL_OVERRIDE flag to indicate the override status */
-            byte embeddingLevel = level;
-            byte newLevel;
-            byte stackTop = 0;
-
-            byte[] stack = new byte[MAX_EXPLICIT_LEVEL];    /* we never push anything >=MAX_EXPLICIT_LEVEL */
-            int countOver60 = 0;
-            int countOver61 = 0;  /* count overflows of explicit levels */
-
-            /* recalculate the flags */
-            flags = 0;
-
-            for (i = 0; i < length; ++i) {
-                dirProp = NoContextRTL(dirProps[i]);
-                switch(dirProp) {
-                case LRE:
-                case LRO:
-                    /* (X3, X5) */
-                    newLevel = (byte)((embeddingLevel+2) & ~(INTERNAL_LEVEL_OVERRIDE | 1)); /* least greater even level */
-                    if (newLevel <= MAX_EXPLICIT_LEVEL) {
-                        stack[stackTop] = embeddingLevel;
-                        ++stackTop;
-                        embeddingLevel = newLevel;
-                        if (dirProp == LRO) {
-                            embeddingLevel |= INTERNAL_LEVEL_OVERRIDE;
+            return dirct;               /* no bracket matching for inverse BiDi */
+        }
+        if ((flags & (MASK_EXPLICIT | MASK_ISO)) == 0) {
+            /* no embeddings, set all levels to the paragraph level */
+            /* we still have to perform bracket matching */
+            int paraIndex, start, limit;
+            BracketData bracketData = new BracketData();
+            bracketInit(bracketData);
+            for (paraIndex = 0; paraIndex < paraCount; paraIndex++) {
+                if (paraIndex == 0)
+                    start = 0;
+                else
+                    start = paras_limit[paraIndex-1];
+                limit = paras_limit[paraIndex];
+                level = paras_level[paraIndex];
+                for (i = start; i < limit; i++) {
+                    levels[i] = level;
+                    dirProp = dirProps[i];
+                    if (dirProp == BN)
+                        continue;
+                    if (dirProp == B) {
+                        if ((i + 1) < length) {
+                            if (text[i] == CR && text[i + 1] == LF)
+                                continue;   /* skip CR when followed by LF */
+                            bracketProcessB(bracketData, level);
                         }
-                        /* we don't need to set LEVEL_OVERRIDE off for LRE
-                           since this has already been done for newLevel which is
-                           the source for embeddingLevel.
-                         */
-                    } else if ((embeddingLevel & ~INTERNAL_LEVEL_OVERRIDE) == MAX_EXPLICIT_LEVEL) {
-                        ++countOver61;
-                    } else /* (embeddingLevel & ~INTERNAL_LEVEL_OVERRIDE) == MAX_EXPLICIT_LEVEL-1 */ {
-                        ++countOver60;
+                        continue;
                     }
-                    flags |= DirPropFlag(BN);
-                    break;
-                case RLE:
-                case RLO:
-                    /* (X2, X4) */
-                    newLevel=(byte)(((embeddingLevel & ~INTERNAL_LEVEL_OVERRIDE) + 1) | 1); /* least greater odd level */
-                    if (newLevel<=MAX_EXPLICIT_LEVEL) {
-                        stack[stackTop] = embeddingLevel;
-                        ++stackTop;
-                        embeddingLevel = newLevel;
-                        if (dirProp == RLO) {
-                            embeddingLevel |= INTERNAL_LEVEL_OVERRIDE;
-                        }
-                        /* we don't need to set LEVEL_OVERRIDE off for RLE
-                           since this has already been done for newLevel which is
-                           the source for embeddingLevel.
-                         */
-                    } else {
-                        ++countOver61;
-                    }
-                    flags |= DirPropFlag(BN);
-                    break;
-                case PDF:
-                    /* (X7) */
-                    /* handle all the overflow cases first */
-                    if (countOver61 > 0) {
-                        --countOver61;
-                    } else if (countOver60 > 0 && (embeddingLevel & ~INTERNAL_LEVEL_OVERRIDE) != MAX_EXPLICIT_LEVEL) {
-                        /* handle LRx overflows from level 60 */
-                        --countOver60;
-                    } else if (stackTop > 0) {
-                        /* this is the pop operation; it also pops level 61 while countOver60>0 */
-                        --stackTop;
-                        embeddingLevel = stack[stackTop];
-                    /* } else { (underflow) */
-                    }
-                    flags |= DirPropFlag(BN);
-                    break;
-                case B:
-                    stackTop = 0;
-                    countOver60 = 0;
-                    countOver61 = 0;
-                    level = GetParaLevelAt(i);
-                    if ((i + 1) < length) {
-                        embeddingLevel = GetParaLevelAt(i+1);
-                        if (!((text[i] == CR) && (text[i + 1] == LF))) {
-                            paras[paraIndex++] = i+1;
-                        }
-                    }
-                    flags |= DirPropFlag(B);
-                    break;
-                case BN:
-                    /* BN, LRE, RLE, and PDF are supposed to be removed (X9) */
-                    /* they will get their levels set correctly in adjustWSLevels() */
-                    flags |= DirPropFlag(BN);
-                    break;
-                default:
-                    /* all other types get the "real" level */
-                    if (level != embeddingLevel) {
-                        level = embeddingLevel;
-                        if ((level & INTERNAL_LEVEL_OVERRIDE) != 0) {
-                            flags |= DirPropFlagO(level) | DirPropFlagMultiRuns;
-                        } else {
-                            flags |= DirPropFlagE(level) | DirPropFlagMultiRuns;
-                        }
-                    }
-                    if ((level & INTERNAL_LEVEL_OVERRIDE) == 0) {
-                        flags |= DirPropFlag(dirProp);
-                    }
+                    bracketProcessChar(bracketData, i);
+                }
+            }
+            return dirct;
+        }
+        /* continue to perform (Xn) */
+
+        /* (X1) level is set for all codes, embeddingLevel keeps track of the push/pop operations */
+        /* both variables may carry the LEVEL_OVERRIDE flag to indicate the override status */
+        byte embeddingLevel = level, newLevel;
+        byte previousLevel = level; /* previous level for regular (not CC) characters */
+        int lastCcPos = 0;          /* index of last effective LRx,RLx, PDx */
+
+        /* The following stack remembers the embedding level and the ISOLATE flag of level runs.
+           stackLast points to its current entry. */
+        short[] stack = new short[MAX_EXPLICIT_LEVEL + 2];  /* we never push anything >= MAX_EXPLICIT_LEVEL
+                                                               but we need one more entry as base */
+        int stackLast = 0;
+        int overflowIsolateCount = 0;
+        int overflowEmbeddingCount = 0;
+        int validIsolateCount = 0;
+        BracketData bracketData = new BracketData();
+        bracketInit(bracketData);
+        stack[0] = level;       /* initialize base entry to para level, no override, no isolate */
+
+        /* recalculate the flags */
+        flags = 0;
+
+        for (i = 0; i < length; i++) {
+            dirProp = dirProps[i];
+            switch (dirProp) {
+            case LRE:
+            case RLE:
+            case LRO:
+            case RLO:
+                /* (X2, X3, X4, X5) */
+                flags |= DirPropFlag(BN);
+                levels[i] = previousLevel;
+                if (dirProp == LRE || dirProp == LRO) {
+                    /* least greater even level */
+                    newLevel = (byte)((embeddingLevel+2) & ~(LEVEL_OVERRIDE | 1));
+                } else {
+                    /* least greater odd level */
+                    newLevel = (byte)((NoOverride(embeddingLevel) + 1) | 1);
+                }
+                if (newLevel <= MAX_EXPLICIT_LEVEL && overflowIsolateCount == 0 &&
+                                                      overflowEmbeddingCount == 0) {
+                    lastCcPos = i;
+                    embeddingLevel = newLevel;
+                    if (dirProp == LRO || dirProp == RLO)
+                        embeddingLevel |= LEVEL_OVERRIDE;
+                    stackLast++;
+                    stack[stackLast] = embeddingLevel;
+                    /* we don't need to set LEVEL_OVERRIDE off for LRE and RLE
+                       since this has already been done for newLevel which is
+                       the source for embeddingLevel.
+                     */
+                } else {
+                    if (overflowIsolateCount == 0)
+                        overflowEmbeddingCount++;
+                }
+                break;
+            case PDF:
+                /* (X7) */
+                flags |= DirPropFlag(BN);
+                levels[i] = previousLevel;
+                /* handle all the overflow cases first */
+                if (overflowIsolateCount > 0) {
                     break;
                 }
-
-                /*
-                 * We need to set reasonable levels even on BN codes and
-                 * explicit codes because we will later look at same-level runs (X10).
-                 */
-                levels[i] = level;
-            }
-            if ((flags & MASK_EMBEDDING) != 0) {
-                flags |= DirPropFlagLR(paraLevel);
+                if (overflowEmbeddingCount > 0) {
+                    overflowEmbeddingCount--;
+                    break;
+                }
+                if (stackLast > 0 && stack[stackLast] < ISOLATE) {   /* not an isolate entry */
+                    lastCcPos = i;
+                    stackLast--;
+                    embeddingLevel = (byte)stack[stackLast];
+                }
+                break;
+            case LRI:
+            case RLI:
+                flags |= DirPropFlag(ON) | DirPropFlagLR(embeddingLevel);
+                levels[i] = NoOverride(embeddingLevel);
+                if (NoOverride(embeddingLevel) != NoOverride(previousLevel)) {
+                    bracketProcessBoundary(bracketData, lastCcPos,
+                                           previousLevel, embeddingLevel);
+                    flags |= DirPropFlagMultiRuns;
+                }
+                previousLevel = embeddingLevel;
+                /* (X5a, X5b) */
+                if (dirProp == LRI)
+                    /* least greater even level */
+                    newLevel=(byte)((embeddingLevel+2)&~(LEVEL_OVERRIDE|1));
+                else
+                    /* least greater odd level */
+                    newLevel=(byte)((NoOverride(embeddingLevel)+1)|1);
+                if (newLevel <= MAX_EXPLICIT_LEVEL && overflowIsolateCount == 0
+                                                   && overflowEmbeddingCount == 0) {
+                    flags |= DirPropFlag(dirProp);
+                    lastCcPos = i;
+                    validIsolateCount++;
+                    if (validIsolateCount > isolateCount)
+                        isolateCount = validIsolateCount;
+                    embeddingLevel = newLevel;
+                    /* we can increment stackLast without checking because newLevel
+                       will exceed UBIDI_MAX_EXPLICIT_LEVEL before stackLast overflows */
+                    stackLast++;
+                    stack[stackLast] = (short)(embeddingLevel + ISOLATE);
+                    bracketProcessLRI_RLI(bracketData, embeddingLevel);
+                } else {
+                    /* make it WS so that it is handled by adjustWSLevels() */
+                    dirProps[i] = WS;
+                    overflowIsolateCount++;
+                }
+                break;
+            case PDI:
+                if (NoOverride(embeddingLevel) != NoOverride(previousLevel)) {
+                    bracketProcessBoundary(bracketData, lastCcPos,
+                                           previousLevel, embeddingLevel);
+                    flags |= DirPropFlagMultiRuns;
+                }
+                /* (X6a) */
+                if (overflowIsolateCount > 0) {
+                    overflowIsolateCount--;
+                    /* make it WS so that it is handled by adjustWSLevels() */
+                    dirProps[i] = WS;
+                }
+                else if (validIsolateCount > 0) {
+                    flags |= DirPropFlag(PDI);
+                    lastCcPos = i;
+                    overflowEmbeddingCount = 0;
+                    while (stack[stackLast] < ISOLATE)  /* pop embedding entries */
+                        stackLast--;                    /* until the last isolate entry */
+                    stackLast--;                        /* pop also the last isolate entry */
+                    validIsolateCount--;
+                    bracketProcessPDI(bracketData);
+                } else
+                    /* make it WS so that it is handled by adjustWSLevels() */
+                    dirProps[i] = WS;
+                embeddingLevel = (byte)(stack[stackLast] & ~ISOLATE);
+                flags |= DirPropFlag(ON) | DirPropFlagLR(embeddingLevel);
+                previousLevel = embeddingLevel;
+                levels[i] = NoOverride(embeddingLevel);
+                break;
+            case B:
+                flags |= DirPropFlag(B);
+                levels[i] = GetParaLevelAt(i);
+                if ((i + 1) < length) {
+                    if (text[i] == CR && text[i + 1] == LF)
+                        break;          /* skip CR when followed by LF */
+                    overflowEmbeddingCount = overflowIsolateCount = 0;
+                    validIsolateCount = 0;
+                    stackLast = 0;
+                    previousLevel = embeddingLevel = GetParaLevelAt(i + 1);
+                    stack[0] = embeddingLevel;   /* initialize base entry to para level, no override, no isolate */
+                    bracketProcessB(bracketData, embeddingLevel);
+                }
+                break;
+            case BN:
+                /* BN, LRE, RLE, and PDF are supposed to be removed (X9) */
+                /* they will get their levels set correctly in adjustWSLevels() */
+                levels[i] = previousLevel;
+                flags |= DirPropFlag(BN);
+                break;
+            default:
+                /* all other types are normal characters and get the "real" level */
+                if (NoOverride(embeddingLevel) != NoOverride(previousLevel)) {
+                    bracketProcessBoundary(bracketData, lastCcPos,
+                                           previousLevel, embeddingLevel);
+                    flags |= DirPropFlagMultiRuns;
+                    if ((embeddingLevel & LEVEL_OVERRIDE) != 0)
+                        flags |= DirPropFlagO(embeddingLevel);
+                    else
+                        flags |= DirPropFlagE(embeddingLevel);
+                }
+                previousLevel = embeddingLevel;
+                levels[i] = embeddingLevel;
+                bracketProcessChar(bracketData, i);
+                /* the dirProp may have been changed in bracketProcessChar() */
+                flags |= DirPropFlag(dirProps[i]);
+                break;
             }
-            if (orderParagraphsLTR && (flags & DirPropFlag(B)) != 0) {
-                flags |= DirPropFlag(L);
-            }
-
-            /* subsequently, ignore the explicit codes and BN (X9) */
-
-            /* again, determine if the text is mixed-directional or single-directional */
-            dirct = directionFromFlags();
+        }
+        if ((flags & MASK_EMBEDDING) != 0) {
+            flags |= DirPropFlagLR(paraLevel);
         }
+        if (orderParagraphsLTR && (flags & DirPropFlag(B)) != 0) {
+            flags |= DirPropFlag(L);
+        }
+        /* again, determine if the text is mixed-directional or single-directional */
+        dirct = directionFromFlags();
 
         return dirct;
     }
@@ -1547,49 +2352,57 @@
     private byte checkExplicitLevels() {
         byte dirProp;
         int i;
+        int isolateCount = 0;
+
         this.flags = 0;     /* collect all directionalities in the text */
         byte level;
-        int paraIndex = 0;
+        this.isolateCount = 0;
 
         for (i = 0; i < length; ++i) {
             if (levels[i] == 0) {
-                levels[i] = paraLevel;
+               levels[i] = paraLevel;
             }
+
+            // for backward compatibility
             if (MAX_EXPLICIT_LEVEL < (levels[i]&0x7f)) {
-                if ((levels[i] & INTERNAL_LEVEL_OVERRIDE) != 0) {
-                    levels[i] =  (byte)(paraLevel|INTERNAL_LEVEL_OVERRIDE);
+                if ((levels[i] & LEVEL_OVERRIDE) != 0) {
+                    levels[i] =  (byte)(paraLevel|LEVEL_OVERRIDE);
                 } else {
                     levels[i] = paraLevel;
                 }
             }
+
             level = levels[i];
-            dirProp = NoContextRTL(dirProps[i]);
-            if ((level & INTERNAL_LEVEL_OVERRIDE) != 0) {
+            dirProp = dirProps[i];
+            if (dirProp == LRI || dirProp == RLI) {
+                isolateCount++;
+                if (isolateCount > this.isolateCount)
+                    this.isolateCount = isolateCount;
+            }
+            else if (dirProp == PDI) {
+                isolateCount--;
+            } else if (dirProp == B) {
+                isolateCount = 0;
+            }
+            if ((level & LEVEL_OVERRIDE) != 0) {
                 /* keep the override flag in levels[i] but adjust the flags */
-                level &= ~INTERNAL_LEVEL_OVERRIDE;     /* make the range check below simpler */
+                level &= ~LEVEL_OVERRIDE;     /* make the range check below simpler */
                 flags |= DirPropFlagO(level);
             } else {
                 /* set the flags */
                 flags |= DirPropFlagE(level) | DirPropFlag(dirProp);
             }
-
             if ((level < GetParaLevelAt(i) &&
                     !((0 == level) && (dirProp == B))) ||
-                    (MAX_EXPLICIT_LEVEL <level)) {
+                    (MAX_EXPLICIT_LEVEL < level)) {
                 /* level out of bounds */
                 throw new IllegalArgumentException("level " + level +
-                                                   " out of bounds at index " + i);
-            }
-            if ((dirProp == B) && ((i + 1) < length)) {
-                if (!((text[i] == CR) && (text[i + 1] == LF))) {
-                    paras[paraIndex++] = i + 1;
-                }
+                                                   " out of bounds at " + i);
             }
         }
-        if ((flags&MASK_EMBEDDING) != 0) {
+        if ((flags & MASK_EMBEDDING) != 0) {
             flags |= DirPropFlagLR(paraLevel);
         }
-
         /* determine if the text is mixed-directional or single-directional */
         return directionFromFlags();
     }
@@ -1610,7 +2423,7 @@
     /*********************************************************************/
     /* Definitions and type for properties state tables                  */
     /*********************************************************************/
-    private static final int IMPTABPROPS_COLUMNS = 14;
+    private static final int IMPTABPROPS_COLUMNS = 16;
     private static final int IMPTABPROPS_RES = IMPTABPROPS_COLUMNS - 1;
     private static short GetStateProps(short cell) {
         return (short)(cell & 0x1f);
@@ -1621,8 +2434,8 @@
 
     private static final short groupProp[] =          /* dirProp regrouped */
     {
-        /*  L   R   EN  ES  ET  AN  CS  B   S   WS  ON  LRE LRO AL  RLE RLO PDF NSM BN  */
-        0,  1,  2,  7,  8,  3,  9,  6,  5,  4,  4,  10, 10, 12, 10, 10, 10, 11, 10
+        /*  L   R   EN  ES  ET  AN  CS  B   S   WS  ON  LRE LRO AL  RLE RLO PDF NSM BN  FSI LRI RLI PDI ENL ENR */
+            0,  1,  2,  7,  8,  3,  9,  6,  5,  4,  4,  10, 10, 12, 10, 10, 10, 11, 10, 4,  4,  4,  4,  13, 14
     };
     private static final short _L  = 0;
     private static final short _R  = 1;
@@ -1637,7 +2450,7 @@
     /*      PROPERTIES  STATE  TABLE                                     */
     /*                                                                   */
     /* In table impTabProps,                                             */
-    /*      - the ON column regroups ON and WS                           */
+    /*      - the ON column regroups ON and WS, FSI, RLI, LRI and PDI    */
     /*      - the BN column regroups BN, LRE, RLE, LRO, RLO, PDF         */
     /*      - the Res column is the reduced property assigned to a run   */
     /*                                                                   */
@@ -1668,25 +2481,31 @@
     /*                                                                   */
     private static final short impTabProps[][] =
     {
-/*                        L,     R,    EN,    AN,    ON,     S,     B,    ES,    ET,    CS,    BN,   NSM,    AL,  Res */
-/* 0 Init        */ {     1,     2,     4,     5,     7,    15,    17,     7,     9,     7,     0,     7,     3,  _ON },
-/* 1 L           */ {     1,  32+2,  32+4,  32+5,  32+7, 32+15, 32+17,  32+7,  32+9,  32+7,     1,     1,  32+3,   _L },
-/* 2 R           */ {  32+1,     2,  32+4,  32+5,  32+7, 32+15, 32+17,  32+7,  32+9,  32+7,     2,     2,  32+3,   _R },
-/* 3 AL          */ {  32+1,  32+2,  32+6,  32+6,  32+8, 32+16, 32+17,  32+8,  32+8,  32+8,     3,     3,     3,   _R },
-/* 4 EN          */ {  32+1,  32+2,     4,  32+5,  32+7, 32+15, 32+17, 64+10,    11, 64+10,     4,     4,  32+3,  _EN },
-/* 5 AN          */ {  32+1,  32+2,  32+4,     5,  32+7, 32+15, 32+17,  32+7,  32+9, 64+12,     5,     5,  32+3,  _AN },
-/* 6 AL:EN/AN    */ {  32+1,  32+2,     6,     6,  32+8, 32+16, 32+17,  32+8,  32+8, 64+13,     6,     6,  32+3,  _AN },
-/* 7 ON          */ {  32+1,  32+2,  32+4,  32+5,     7, 32+15, 32+17,     7, 64+14,     7,     7,     7,  32+3,  _ON },
-/* 8 AL:ON       */ {  32+1,  32+2,  32+6,  32+6,     8, 32+16, 32+17,     8,     8,     8,     8,     8,  32+3,  _ON },
-/* 9 ET          */ {  32+1,  32+2,     4,  32+5,     7, 32+15, 32+17,     7,     9,     7,     9,     9,  32+3,  _ON },
-/*10 EN+ES/CS    */ {  96+1,  96+2,     4,  96+5, 128+7, 96+15, 96+17, 128+7,128+14, 128+7,    10, 128+7,  96+3,  _EN },
-/*11 EN+ET       */ {  32+1,  32+2,     4,  32+5,  32+7, 32+15, 32+17,  32+7,    11,  32+7,    11,    11,  32+3,  _EN },
-/*12 AN+CS       */ {  96+1,  96+2,  96+4,     5, 128+7, 96+15, 96+17, 128+7,128+14, 128+7,    12, 128+7,  96+3,  _AN },
-/*13 AL:EN/AN+CS */ {  96+1,  96+2,     6,     6, 128+8, 96+16, 96+17, 128+8, 128+8, 128+8,    13, 128+8,  96+3,  _AN },
-/*14 ON+ET       */ {  32+1,  32+2, 128+4,  32+5,     7, 32+15, 32+17,     7,    14,     7,    14,    14,  32+3,  _ON },
-/*15 S           */ {  32+1,  32+2,  32+4,  32+5,  32+7,    15, 32+17,  32+7,  32+9,  32+7,    15,  32+7,  32+3,   _S },
-/*16 AL:S        */ {  32+1,  32+2,  32+6,  32+6,  32+8,    16, 32+17,  32+8,  32+8,  32+8,    16,  32+8,  32+3,   _S },
-/*17 B           */ {  32+1,  32+2,  32+4,  32+5,  32+7, 32+15,    17,  32+7,  32+9,  32+7,    17,  32+7,  32+3,   _B }
+/*                        L,     R,    EN,    AN,    ON,     S,     B,    ES,    ET,    CS,    BN,   NSM,    AL,   ENL,   ENR,   Res */
+/* 0 Init        */ {     1,     2,     4,     5,     7,    15,    17,     7,     9,     7,     0,     7,     3,    18,    21,   _ON },
+/* 1 L           */ {     1,  32+2,  32+4,  32+5,  32+7, 32+15, 32+17,  32+7,  32+9,  32+7,     1,     1,  32+3, 32+18, 32+21,    _L },
+/* 2 R           */ {  32+1,     2,  32+4,  32+5,  32+7, 32+15, 32+17,  32+7,  32+9,  32+7,     2,     2,  32+3, 32+18, 32+21,    _R },
+/* 3 AL          */ {  32+1,  32+2,  32+6,  32+6,  32+8, 32+16, 32+17,  32+8,  32+8,  32+8,     3,     3,     3, 32+18, 32+21,    _R },
+/* 4 EN          */ {  32+1,  32+2,     4,  32+5,  32+7, 32+15, 32+17, 64+10,    11, 64+10,     4,     4,  32+3,    18,    21,   _EN },
+/* 5 AN          */ {  32+1,  32+2,  32+4,     5,  32+7, 32+15, 32+17,  32+7,  32+9, 64+12,     5,     5,  32+3, 32+18, 32+21,   _AN },
+/* 6 AL:EN/AN    */ {  32+1,  32+2,     6,     6,  32+8, 32+16, 32+17,  32+8,  32+8, 64+13,     6,     6,  32+3,    18,    21,   _AN },
+/* 7 ON          */ {  32+1,  32+2,  32+4,  32+5,     7, 32+15, 32+17,     7, 64+14,     7,     7,     7,  32+3, 32+18, 32+21,   _ON },
+/* 8 AL:ON       */ {  32+1,  32+2,  32+6,  32+6,     8, 32+16, 32+17,     8,     8,     8,     8,     8,  32+3, 32+18, 32+21,   _ON },
+/* 9 ET          */ {  32+1,  32+2,     4,  32+5,     7, 32+15, 32+17,     7,     9,     7,     9,     9,  32+3,    18,    21,   _ON },
+/*10 EN+ES/CS    */ {  96+1,  96+2,     4,  96+5, 128+7, 96+15, 96+17, 128+7,128+14, 128+7,    10, 128+7,  96+3,    18,    21,   _EN },
+/*11 EN+ET       */ {  32+1,  32+2,     4,  32+5,  32+7, 32+15, 32+17,  32+7,    11,  32+7,    11,    11,  32+3,    18,    21,   _EN },
+/*12 AN+CS       */ {  96+1,  96+2,  96+4,     5, 128+7, 96+15, 96+17, 128+7,128+14, 128+7,    12, 128+7,  96+3, 96+18, 96+21,   _AN },
+/*13 AL:EN/AN+CS */ {  96+1,  96+2,     6,     6, 128+8, 96+16, 96+17, 128+8, 128+8, 128+8,    13, 128+8,  96+3,    18,    21,   _AN },
+/*14 ON+ET       */ {  32+1,  32+2, 128+4,  32+5,     7, 32+15, 32+17,     7,    14,     7,    14,    14,  32+3,128+18,128+21,   _ON },
+/*15 S           */ {  32+1,  32+2,  32+4,  32+5,  32+7,    15, 32+17,  32+7,  32+9,  32+7,    15,  32+7,  32+3, 32+18, 32+21,    _S },
+/*16 AL:S        */ {  32+1,  32+2,  32+6,  32+6,  32+8,    16, 32+17,  32+8,  32+8,  32+8,    16,  32+8,  32+3, 32+18, 32+21,    _S },
+/*17 B           */ {  32+1,  32+2,  32+4,  32+5,  32+7, 32+15,    17,  32+7,  32+9,  32+7,    17,  32+7,  32+3, 32+18, 32+21,    _B },
+/*18 ENL         */ {  32+1,  32+2,    18,  32+5,  32+7, 32+15, 32+17, 64+19,    20, 64+19,    18,    18,  32+3,    18,    21,    _L },
+/*19 ENL+ES/CS   */ {  96+1,  96+2,    18,  96+5, 128+7, 96+15, 96+17, 128+7,128+14, 128+7,    19, 128+7,  96+3,    18,    21,    _L },
+/*20 ENL+ET      */ {  32+1,  32+2,    18,  32+5,  32+7, 32+15, 32+17,  32+7,    20,  32+7,    20,    20,  32+3,    18,    21,    _L },
+/*21 ENR         */ {  32+1,  32+2,    21,  32+5,  32+7, 32+15, 32+17, 64+22,    23, 64+22,    21,    21,  32+3,    18,    21,   _AN },
+/*22 ENR+ES/CS   */ {  96+1,  96+2,    21,  96+5, 128+7, 96+15, 96+17, 128+7,128+14, 128+7,    22, 128+7,  96+3,    18,    21,   _AN },
+/*23 ENR+ET      */ {  32+1,  32+2,    21,  32+5,  32+7, 32+15, 32+17,  32+7,    23,  32+7,    23,    23,  32+3,    18,    21,   _AN }
     };
 
     /*********************************************************************/
@@ -1760,7 +2579,7 @@
     /*                                                                   */
 
     private static final byte impTabL_DEFAULT[][] = /* Even paragraph level */
-        /*  In this table, conditional sequences receive the higher possible level
+        /*  In this table, conditional sequences receive the lower possible level
             until proven otherwise.
         */
     {
@@ -1769,8 +2588,8 @@
         /* 1 : R          */ {     0,     1,     3,     3,  0x14,  0x14,     0,  1 },
         /* 2 : AN         */ {     0,     1,     0,     2,  0x15,  0x15,     0,  2 },
         /* 3 : R+EN/AN    */ {     0,     1,     3,     3,  0x14,  0x14,     0,  2 },
-        /* 4 : R+ON       */ {  0x20,     1,     3,     3,     4,     4,  0x20,  1 },
-        /* 5 : AN+ON      */ {  0x20,     1,  0x20,     2,     5,     5,  0x20,  1 }
+        /* 4 : R+ON       */ {     0,  0x21,  0x33,  0x33,     4,     4,     0,  0 },
+        /* 5 : AN+ON      */ {     0,  0x21,     0,  0x32,     5,     5,     0,  0 }
     };
 
     private static final byte impTabR_DEFAULT[][] = /* Odd  paragraph level */
@@ -1787,20 +2606,20 @@
         /* 5 : L+AN+ON    */ {     1,     0,     1,     3,     5,     5,     0,  0 }
     };
 
-    private static final short[] impAct0 = {0,1,2,3,4,5,6};
+    private static final short[] impAct0 = {0,1,2,3,4};
 
     private static final ImpTabPair impTab_DEFAULT = new ImpTabPair(
             impTabL_DEFAULT, impTabR_DEFAULT, impAct0, impAct0);
 
     private static final byte impTabL_NUMBERS_SPECIAL[][] = { /* Even paragraph level */
-        /* In this table, conditional sequences receive the higher possible
+        /* In this table, conditional sequences receive the lower possible
            level until proven otherwise.
         */
         /*                         L,     R,    EN,    AN,    ON,     S,     B, Res */
-        /* 0 : init       */ {     0,     2,     1,     1,     0,     0,     0,  0 },
-        /* 1 : L+EN/AN    */ {     0,     2,     1,     1,     0,     0,     0,  2 },
-        /* 2 : R          */ {     0,     2,     4,     4,  0x13,     0,     0,  1 },
-        /* 3 : R+ON       */ {  0x20,     2,     4,     4,     3,     3,  0x20,  1 },
+        /* 0 : init       */ {     0,     2,  0x11,  0x11,     0,     0,     0,  0 },
+        /* 1 : L+EN/AN    */ {     0,  0x42,     1,     1,     0,     0,     0,  0 },
+        /* 2 : R          */ {     0,     2,     4,     4,  0x13,  0x13,     0,  1 },
+        /* 3 : R+ON       */ {     0,  0x22,  0x34,  0x34,     3,     3,     0,  0 },
         /* 4 : R+EN/AN    */ {     0,     2,     4,     4,  0x13,  0x13,     0,  2 }
     };
     private static final ImpTabPair impTab_NUMBERS_SPECIAL = new ImpTabPair(
@@ -1874,7 +2693,7 @@
         /* 5 : L+AN+ON    */ {  0x21,  0x30,     6,     4,     5,     5,  0x30,  2 },
         /* 6 : L+ON+EN    */ {  0x21,  0x30,     6,     4,     3,     3,  0x30,  1 }
     };
-    private static final short[] impAct1 = {0,1,11,12};
+    private static final short[] impAct1 = {0,1,13,14};
     private static final ImpTabPair impTab_INVERSE_LIKE_DIRECT = new ImpTabPair(
             impTabL_DEFAULT, impTabR_INVERSE_LIKE_DIRECT, impAct0, impAct1);
 
@@ -1898,15 +2717,16 @@
         /* 0 : init       */ {  0x13,     0,     1,     1,     0,     0,     0,  0 },
         /* 1 : R+EN/AN    */ {  0x23,     0,     1,     1,     2,  0x40,     0,  1 },
         /* 2 : R+EN/AN+ON */ {  0x23,     0,     1,     1,     2,  0x40,     0,  0 },
-        /* 3 : L          */ {    3 ,     0,     3,  0x36,  0x14,  0x40,     0,  1 },
+        /* 3 : L          */ {     3,     0,     3,  0x36,  0x14,  0x40,     0,  1 },
         /* 4 : L+ON       */ {  0x53,  0x40,     5,  0x36,     4,  0x40,  0x40,  0 },
         /* 5 : L+ON+EN    */ {  0x53,  0x40,     5,  0x36,     4,  0x40,  0x40,  1 },
         /* 6 : L+AN       */ {  0x53,  0x40,     6,     6,     4,  0x40,  0x40,  3 }
     };
-    private static final short impAct2[] = {0,1,7,8,9,10};
+    private static final short[] impAct2 = {0,1,2,5,6,7,8};
+    private static final short[] impAct3 = {0,1,9,10,11,12};
     private static final ImpTabPair impTab_INVERSE_LIKE_DIRECT_WITH_MARKS =
             new ImpTabPair(impTabL_INVERSE_LIKE_DIRECT_WITH_MARKS,
-                           impTabR_INVERSE_LIKE_DIRECT_WITH_MARKS, impAct0, impAct2);
+                           impTabR_INVERSE_LIKE_DIRECT_WITH_MARKS, impAct2, impAct3);
 
     private static final ImpTabPair impTab_INVERSE_FOR_NUMBERS_SPECIAL = new ImpTabPair(
             impTabL_NUMBERS_SPECIAL, impTabR_INVERSE_LIKE_DIRECT, impAct0, impAct1);
@@ -1923,14 +2743,15 @@
     };
     private static final ImpTabPair impTab_INVERSE_FOR_NUMBERS_SPECIAL_WITH_MARKS = new
             ImpTabPair(impTabL_INVERSE_FOR_NUMBERS_SPECIAL_WITH_MARKS,
-                       impTabR_INVERSE_LIKE_DIRECT_WITH_MARKS, impAct0, impAct2);
-
-    private class LevState {
+                       impTabR_INVERSE_LIKE_DIRECT_WITH_MARKS, impAct2, impAct3);
+
+    private static class LevState {
         byte[][] impTab;                /* level table pointer          */
         short[] impAct;                 /* action map array             */
         int startON;                    /* start of ON sequence         */
         int startL2EN;                  /* start of level 2 sequence    */
         int lastStrongRTL;              /* index of last found R or AL  */
+        int runStart;                   /* start position of the run    */
         short state;                    /* current state                */
         byte runLevel;                  /* run level before implicit solving */
     }
@@ -1962,6 +2783,22 @@
         insertPoints.size++;
     }
 
+    private void setLevelsOutsideIsolates(int start, int limit, byte level)
+    {
+        byte dirProp;
+        int  isolateCount = 0, k;
+        for (k = start; k < limit; k++) {
+            dirProp = dirProps[k];
+            if (dirProp == PDI)
+                isolateCount--;
+            if (isolateCount == 0) {
+                levels[k] = level;
+            }
+            if (dirProp == LRI || dirProp == RLI)
+                isolateCount++;
+        }
+    }
+
     /* perform rules (Wn), (Nn), and (In) on a run of the text ------------------ */
 
     /*
@@ -2003,7 +2840,17 @@
                 start = levState.startON;
                 break;
 
-            case 3:                     /* L or S after possible relevant EN/AN */
+            case 3:                     /* EN/AN after R+ON */
+                level = (byte)(levState.runLevel + 1);
+                setLevelsOutsideIsolates(levState.startON, start0, level);
+                break;
+
+            case 4:                     /* EN/AN before R for NUMBERS_SPECIAL */
+                level = (byte)(levState.runLevel + 2);
+                setLevelsOutsideIsolates(levState.startON, start0, level);
+                break;
+
+            case 5:                     /* L or S after possible relevant EN/AN */
                 /* check if we had EN after R/AL */
                 if (levState.startL2EN >= 0) {
                     addPoint(levState.startL2EN, LRM_BEFORE);
@@ -2039,7 +2886,7 @@
                 }
                 break;
 
-            case 4:                     /* R/AL after possible relevant EN/AN */
+            case 6:                     /* R/AL after possible relevant EN/AN */
                 /* just clean up */
                 if (insertPoints.points.length > 0)
                     /* remove all non confirmed insert points */
@@ -2049,12 +2896,15 @@
                 levState.lastStrongRTL = limit - 1;
                 break;
 
-            case 5:                     /* EN/AN after R/AL + possible cont */
+            case 7:                     /* EN/AN after R/AL + possible cont */
                 /* check for real AN */
-                if ((_prop == _AN) && (NoContextRTL(dirProps[start0]) == AN)) {
+
+                if ((_prop == _AN) && (dirProps[start0] == AN) &&
+                (reorderingMode != REORDER_INVERSE_FOR_NUMBERS_SPECIAL))
+                {
                     /* real AN */
                     if (levState.startL2EN == -1) { /* if no relevant EN already found */
-                        /* just note the righmost digit as a strong RTL */
+                        /* just note the rightmost digit as a strong RTL */
                         levState.lastStrongRTL = limit - 1;
                         break;
                     }
@@ -2072,12 +2922,12 @@
                 }
                 break;
 
-            case 6:                     /* note location of latest R/AL */
+            case 8:                     /* note location of latest R/AL */
                 levState.lastStrongRTL = limit - 1;
                 levState.startON = -1;
                 break;
 
-            case 7:                     /* L after R+ON/EN/AN */
+            case 9:                     /* L after R+ON/EN/AN */
                 /* include possible adjacent number on the left */
                 for (k = start0-1; k >= 0 && ((levels[k] & 1) == 0); k--) {
                 }
@@ -2088,14 +2938,14 @@
                 levState.startON = start0;
                 break;
 
-            case 8:                     /* AN after L */
+            case 10:                    /* AN after L */
                 /* AN numbers between L text on both sides may be trouble. */
                 /* tentatively bracket with LRMs; will be confirmed if followed by L */
                 addPoint(start0, LRM_BEFORE);   /* add LRM before */
                 addPoint(start0, LRM_AFTER);    /* add LRM after  */
                 break;
 
-            case 9:                     /* R after L+ON/EN/AN */
+            case 11:                    /* R after L+ON/EN/AN */
                 /* false alert, infirm LRMs around previous AN */
                 insertPoints.size=insertPoints.confirmed;
                 if (_prop == _S) {          /* add RLM before S */
@@ -2104,7 +2954,7 @@
                 }
                 break;
 
-            case 10:                    /* L after L+ON/AN */
+            case 12:                    /* L after L+ON/AN */
                 level = (byte)(levState.runLevel + addLevel);
                 for (k=levState.startON; k < start0; k++) {
                     if (levels[k] < level) {
@@ -2115,7 +2965,7 @@
                 levState.startON = start0;
                 break;
 
-            case 11:                    /* L after L+ON+EN/AN/ON */
+            case 13:                    /* L after L+ON+EN/AN/ON */
                 level = levState.runLevel;
                 for (k = start0-1; k >= levState.startON; k--) {
                     if (levels[k] == level+3) {
@@ -2134,7 +2984,7 @@
                 }
                 break;
 
-            case 12:                    /* R after L+ON+EN/AN/ON */
+            case 14:                    /* R after L+ON+EN/AN/ON */
                 level = (byte)(levState.runLevel+1);
                 for (k = start0-1; k >= levState.startON; k--) {
                     if (levels[k] > level) {
@@ -2149,22 +2999,27 @@
         }
         if ((addLevel) != 0 || (start < start0)) {
             level = (byte)(levState.runLevel + addLevel);
-            for (k = start; k < limit; k++) {
-                levels[k] = level;
+            if (start >= levState.runStart) {
+                for (k = start; k < limit; k++) {
+                    levels[k] = level;
+                }
+            } else {
+                setLevelsOutsideIsolates(start, limit, level);
             }
         }
     }
 
     private void resolveImplicitLevels(int start, int limit, short sor, short eor)
     {
+        byte dirProp;
         LevState levState = new LevState();
         int i, start1, start2;
         short oldStateImp, stateImp, actionImp;
         short gprop, resProp, cell;
+        boolean inverseRTL;
         short nextStrongProp = R;
         int nextStrongPos = -1;
 
-
         /* check for RTL inverse Bidi mode */
         /* FOOD FOR THOUGHT: in case of RTL inverse Bidi, it would make sense to
          * loop on the text characters from end to start.
@@ -2172,29 +3027,78 @@
          * actions) and different levels state tables (maybe very similar to the
          * LTR corresponding ones.
          */
-        /* initialize for levels state table */
+        inverseRTL=((start<lastArabicPos) && ((GetParaLevelAt(start) & 1)>0) &&
+                    (reorderingMode == REORDER_INVERSE_LIKE_DIRECT  ||
+                     reorderingMode == REORDER_INVERSE_FOR_NUMBERS_SPECIAL));
+        /* initialize for property and levels state table */
         levState.startL2EN = -1;        /* used for INVERSE_LIKE_DIRECT_WITH_MARKS */
         levState.lastStrongRTL = -1;    /* used for INVERSE_LIKE_DIRECT_WITH_MARKS */
-        levState.state = 0;
+        levState.runStart = start;
         levState.runLevel = levels[start];
         levState.impTab = impTabPair.imptab[levState.runLevel & 1];
         levState.impAct = impTabPair.impact[levState.runLevel & 1];
-        processPropertySeq(levState, sor, start, start);
-        /* initialize for property state table */
-        if (dirProps[start] == NSM) {
-            stateImp = (short)(1 + sor);
+
+        /* The isolates[] entries contain enough information to
+           resume the bidi algorithm in the same state as it was
+           when it was interrupted by an isolate sequence. */
+        if (dirProps[start] == PDI) {
+            levState.startON = isolates[isolateCount].startON;
+            start1 = isolates[isolateCount].start1;
+            stateImp = isolates[isolateCount].stateImp;
+            levState.state = isolates[isolateCount].state;
+            isolateCount--;
         } else {
-            stateImp = 0;
+            levState.startON = -1;
+            start1 = start;
+            if (dirProps[start] == NSM)
+              stateImp = (short)(1 + sor);
+            else
+                stateImp = 0;
+            levState.state = 0;
+            processPropertySeq(levState, sor, start, start);
         }
-        start1 = start;
-        start2 = 0;
+        start2 = start;                 /* to make the Java compiler happy */
 
         for (i = start; i <= limit; i++) {
             if (i >= limit) {
+                int k;
+                for (k = limit - 1;
+                     k > start &&
+                         (DirPropFlag(dirProps[k]) & MASK_BN_EXPLICIT) != 0;
+                     k--);
+                dirProp = dirProps[k];
+                if (dirProp == LRI || dirProp == RLI)
+                    break;  /* no forced closing for sequence ending with LRI/RLI */
                 gprop = eor;
             } else {
-                short prop, prop1;
-                prop = NoContextRTL(dirProps[i]);
+                byte prop, prop1;
+                prop = dirProps[i];
+                if (prop == B)
+                    isolateCount = -1;  /* current isolates stack entry == none */
+                if (inverseRTL) {
+                    if (prop == AL) {
+                        /* AL before EN does not make it AN */
+                        prop = R;
+                    } else if (prop == EN) {
+                        if (nextStrongPos <= i) {
+                            /* look for next strong char (L/R/AL) */
+                            int j;
+                            nextStrongProp = R;     /* set default */
+                            nextStrongPos = limit;
+                            for (j = i+1; j < limit; j++) {
+                                prop1 = dirProps[j];
+                                if (prop1 == L || prop1 == R || prop1 == AL) {
+                                    nextStrongProp = prop1;
+                                    nextStrongPos = j;
+                                    break;
+                                }
+                            }
+                        }
+                        if (nextStrongProp == AL) {
+                            prop = AN;
+                        }
+                    }
+                }
                 gprop = groupProp[prop];
             }
             oldStateImp = stateImp;
@@ -2230,8 +3134,24 @@
                 }
             }
         }
-        /* flush possible pending sequence, e.g. ON */
-        processPropertySeq(levState, eor, limit, limit);
+
+        /* look for the last char not a BN or LRE/RLE/LRO/RLO/PDF */
+        for (i = limit - 1;
+             i > start &&
+                 (DirPropFlag(dirProps[i]) & MASK_BN_EXPLICIT) != 0;
+             i--);
+        dirProp = dirProps[i];
+        if ((dirProp == LRI || dirProp == RLI) && limit < length) {
+            isolateCount++;
+            if (isolates[isolateCount] == null)
+                isolates[isolateCount] = new Isolate();
+            isolates[isolateCount].stateImp = stateImp;
+            isolates[isolateCount].state = levState.state;
+            isolates[isolateCount].start1 = start1;
+            isolates[isolateCount].startON = levState.startON;
+        }
+        else
+            processPropertySeq(levState, eor, limit, limit);
     }
 
     /* perform (L1) and (X9) ---------------------------------------------------- */
@@ -2250,7 +3170,7 @@
             i = trailingWSStart;
             while (i > 0) {
                 /* reset a sequence of WS/BN before eop and B/S to the paragraph paraLevel */
-                while (i > 0 && ((flag = DirPropFlagNC(dirProps[--i])) & MASK_WS) != 0) {
+                while (i > 0 && ((flag = DirPropFlag(dirProps[--i])) & MASK_WS) != 0) {
                     if (orderParagraphsLTR && (flag & DirPropFlag(B)) != 0) {
                         levels[i] = 0;
                     } else {
@@ -2261,7 +3181,7 @@
                 /* reset BN to the next character's paraLevel until B/S, which restarts above loop */
                 /* here, i+1 is guaranteed to be <length */
                 while (i > 0) {
-                    flag = DirPropFlagNC(dirProps[--i]);
+                    flag = DirPropFlag(dirProps[--i]);
                     if ((flag & MASK_BN_EXPLICIT) != 0) {
                         levels[i] = levels[i + 1];
                     } else if (orderParagraphsLTR && (flag & DirPropFlag(B)) != 0) {
@@ -2276,6 +3196,10 @@
         }
     }
 
+    private void setParaSuccess() {
+        paraBidi = this;                /* mark successful setPara */
+    }
+
     private int Bidi_Min(int x, int y) {
         return x < y ? x : y;
     }
@@ -2284,6 +3208,159 @@
         return x >= 0 ? x : -x;
     }
 
+    void setParaRunsOnly(char[] parmText, byte parmParaLevel) {
+        int[] visualMap;
+        String visualText;
+        int saveLength, saveTrailingWSStart;
+        byte[] saveLevels;
+        byte saveDirection;
+        int i, j, visualStart, logicalStart,
+            oldRunCount, runLength, addedRuns, insertRemove,
+            start, limit, step, indexOddBit, logicalPos,
+            index, index1;
+        int saveOptions;
+
+        reorderingMode = REORDER_DEFAULT;
+        int parmLength = parmText.length;
+        if (parmLength == 0) {
+            setPara(parmText, parmParaLevel, null);
+            reorderingMode = REORDER_RUNS_ONLY;
+            return;
+        }
+        /* obtain memory for mapping table and visual text */
+        saveOptions = reorderingOptions;
+        if ((saveOptions & OPTION_INSERT_MARKS) > 0) {
+            reorderingOptions &= ~OPTION_INSERT_MARKS;
+            reorderingOptions |= OPTION_REMOVE_CONTROLS;
+        }
+        parmParaLevel &= 1;             /* accept only 0 or 1 */
+        setPara(parmText, parmParaLevel, null);
+        /* we cannot access directly levels since it is not yet set if
+         * direction is not MIXED
+         */
+        saveLevels = new byte[this.length];
+        System.arraycopy(getLevels(), 0, saveLevels, 0, this.length);
+        saveTrailingWSStart = trailingWSStart;
+
+        /* FOOD FOR THOUGHT: instead of writing the visual text, we could use
+         * the visual map and the dirProps array to drive the second call
+         * to setPara (but must make provision for possible removal of
+         * Bidi controls.  Alternatively, only use the dirProps array via
+         * customized classifier callback.
+         */
+        visualText = writeReordered(DO_MIRRORING);
+        visualMap = getVisualMap();
+        this.reorderingOptions = saveOptions;
+        saveLength = this.length;
+        saveDirection=this.direction;
+
+        this.reorderingMode = REORDER_INVERSE_LIKE_DIRECT;
+        parmParaLevel ^= 1;
+        setPara(visualText, parmParaLevel, null);
+        BidiLine.getRuns(this);
+        /* check if some runs must be split, count how many splits */
+        addedRuns = 0;
+        oldRunCount = this.runCount;
+        visualStart = 0;
+        for (i = 0; i < oldRunCount; i++, visualStart += runLength) {
+            runLength = runs[i].limit - visualStart;
+            if (runLength < 2) {
+                continue;
+            }
+            logicalStart = runs[i].start;
+            for (j = logicalStart+1; j < logicalStart+runLength; j++) {
+                index = visualMap[j];
+                index1 = visualMap[j-1];
+                if ((Bidi_Abs(index-index1)!=1) || (saveLevels[index]!=saveLevels[index1])) {
+                    addedRuns++;
+                }
+            }
+        }
+        if (addedRuns > 0) {
+            getRunsMemory(oldRunCount + addedRuns);
+            if (runCount == 1) {
+                /* because we switch from UBiDi.simpleRuns to UBiDi.runs */
+                runsMemory[0] = runs[0];
+            } else {
+                System.arraycopy(runs, 0, runsMemory, 0, runCount);
+            }
+            runs = runsMemory;
+            runCount += addedRuns;
+            for (i = oldRunCount; i < runCount; i++) {
+                if (runs[i] == null) {
+                    runs[i] = new BidiRun(0, 0, (byte)0);
+                }
+            }
+        }
+        /* split runs which are not consecutive in source text */
+        int newI;
+        for (i = oldRunCount-1; i >= 0; i--) {
+            newI = i + addedRuns;
+            runLength = i==0 ? runs[0].limit :
+                               runs[i].limit - runs[i-1].limit;
+            logicalStart = runs[i].start;
+            indexOddBit = runs[i].level & 1;
+            if (runLength < 2) {
+                if (addedRuns > 0) {
+                    runs[newI].copyFrom(runs[i]);
+                }
+                logicalPos = visualMap[logicalStart];
+                runs[newI].start = logicalPos;
+                runs[newI].level = (byte)(saveLevels[logicalPos] ^ indexOddBit);
+                continue;
+            }
+            if (indexOddBit > 0) {
+                start = logicalStart;
+                limit = logicalStart + runLength - 1;
+                step = 1;
+            } else {
+                start = logicalStart + runLength - 1;
+                limit = logicalStart;
+                step = -1;
+            }
+            for (j = start; j != limit; j += step) {
+                index = visualMap[j];
+                index1 = visualMap[j+step];
+                if ((Bidi_Abs(index-index1)!=1) || (saveLevels[index]!=saveLevels[index1])) {
+                    logicalPos = Bidi_Min(visualMap[start], index);
+                    runs[newI].start = logicalPos;
+                    runs[newI].level = (byte)(saveLevels[logicalPos] ^ indexOddBit);
+                    runs[newI].limit = runs[i].limit;
+                    runs[i].limit -= Bidi_Abs(j - start) + 1;
+                    insertRemove = runs[i].insertRemove & (LRM_AFTER|RLM_AFTER);
+                    runs[newI].insertRemove = insertRemove;
+                    runs[i].insertRemove &= ~insertRemove;
+                    start = j + step;
+                    addedRuns--;
+                    newI--;
+                }
+            }
+            if (addedRuns > 0) {
+                runs[newI].copyFrom(runs[i]);
+            }
+            logicalPos = Bidi_Min(visualMap[start], visualMap[limit]);
+            runs[newI].start = logicalPos;
+            runs[newI].level = (byte)(saveLevels[logicalPos] ^ indexOddBit);
+        }
+
+    cleanup1:
+        /* restore initial paraLevel */
+        this.paraLevel ^= 1;
+    cleanup2:
+        /* restore real text */
+        this.text = parmText;
+        this.length = saveLength;
+        this.originalLength = parmLength;
+        this.direction=saveDirection;
+        this.levels = saveLevels;
+        this.trailingWSStart = saveTrailingWSStart;
+        if (runCount > 1) {
+            this.direction = MIXED;
+        }
+    cleanup3:
+        this.reorderingMode = REORDER_RUNS_ONLY;
+    }
+
     /**
      * Perform the Unicode Bidi algorithm. It is defined in the
      * <a href="http://www.unicode.org/unicode/reports/tr9/">Unicode Standard Annex #9</a>,
@@ -2386,7 +3463,7 @@
      * For example, in pure LTR text with numbers the numbers would get
      * a resolved level of 2 higher than the surrounding text according to
      * the algorithm. This implementation may set all resolved levels to
-     * the same value in such a case.<p>
+     * the same value in such a case.
      *
      * The text can be composed of multiple paragraphs. Occurrence of a block
      * separator in the text terminates a paragraph, and whatever comes next starts
@@ -2421,9 +3498,9 @@
      *        (same index) character if the level has the
      *        <code>LEVEL_OVERRIDE</code> bit set.<br><br>
      *        Except for that bit, it must be
-     *        {@code paraLevel<=embeddingLevels[]<=MAX_EXPLICIT_LEVEL},
+     *        <code>paraLevel<=embeddingLevels[]<=MAX_EXPLICIT_LEVEL</code>,
      *        with one exception: a level of zero may be specified for a
-     *        paragraph separator even if {@code paraLevel > 0} when multiple
+     *        paragraph separator even if <code>paraLevel&gt;0</code> when multiple
      *        paragraphs are submitted in the same call to <code>setPara()</code>.<br><br>
      *        <strong>Caution: </strong>A reference to this array, not a copy
      *        of the levels, will be stored in the <code>Bidi</code> object;
@@ -2444,22 +3521,28 @@
      * @see #MAX_EXPLICIT_LEVEL
      * @stable ICU 3.8
      */
-    public void setPara(char[] chars, byte paraLevel, byte[] embeddingLevels)
+    void setPara(char[] chars, byte paraLevel, byte[] embeddingLevels)
     {
         /* check the argument values */
-        if (paraLevel < INTERNAL_LEVEL_DEFAULT_LTR) {
+        if (paraLevel < LEVEL_DEFAULT_LTR) {
             verifyRange(paraLevel, 0, MAX_EXPLICIT_LEVEL + 1);
         }
         if (chars == null) {
             chars = new char[0];
         }
 
+        /* special treatment for RUNS_ONLY mode */
+        if (reorderingMode == REORDER_RUNS_ONLY) {
+            setParaRunsOnly(chars, paraLevel);
+            return;
+        }
+
         /* initialize the Bidi object */
         this.paraBidi = null;          /* mark unfinished setPara */
         this.text = chars;
         this.length = this.originalLength = this.resultLength = text.length;
         this.paraLevel = paraLevel;
-        this.direction = Bidi.DIRECTION_LEFT_TO_RIGHT;
+        this.direction = (byte)(paraLevel & 1);
         this.paraCount = 1;
 
         /* Allocate zero-length arrays instead of setting to null here; then
@@ -2475,11 +3558,7 @@
         /*
          * Save the original paraLevel if contextual; otherwise, set to 0.
          */
-        if (IsDefaultLevel(paraLevel)) {
-            defaultParaLevel = paraLevel;
-        } else {
-            defaultParaLevel = 0;
-        }
+        defaultParaLevel = IsDefaultLevel(paraLevel) ? paraLevel : 0;
 
         if (length == 0) {
             /*
@@ -2491,17 +3570,10 @@
                 this.paraLevel &= 1;
                 defaultParaLevel = 0;
             }
-            if ((this.paraLevel & 1) != 0) {
-                flags = DirPropFlag(R);
-                direction = Bidi.DIRECTION_RIGHT_TO_LEFT;
-            } else {
-                flags = DirPropFlag(L);
-                direction = Bidi.DIRECTION_LEFT_TO_RIGHT;
-            }
-
+            flags = DirPropFlagLR(paraLevel);
             runCount = 0;
             paraCount = 0;
-            paraBidi = this;         /* mark successful setPara */
+            setParaSuccess();
             return;
         }
 
@@ -2515,21 +3587,9 @@
         getDirPropsMemory(length);
         dirProps = dirPropsMemory;
         getDirProps();
-
         /* the processed length may have changed if OPTION_STREAMING is set */
         trailingWSStart = length;  /* the levels[] will reflect the WS run */
 
-        /* allocate paras memory */
-        if (paraCount > 1) {
-            getInitialParasMemory(paraCount);
-            paras = parasMemory;
-            paras[paraCount - 1] = length;
-        } else {
-            /* initialize paras for single paragraph */
-            paras = simpleParas;
-            simpleParas[0] = length;
-        }
-
         /* are explicit levels specified? */
         if (embeddingLevels == null) {
             /* no: determine explicit levels according to the (Xn) rules */
@@ -2542,28 +3602,62 @@
             direction = checkExplicitLevels();
         }
 
+        /* allocate isolate memory */
+        if (isolateCount > 0) {
+            if (isolates == null || isolates.length < isolateCount)
+                isolates = new Isolate[isolateCount + 3];   /* keep some reserve */
+        }
+        isolateCount = -1;              /* current isolates stack entry == none */
+
         /*
          * The steps after (X9) in the Bidi algorithm are performed only if
          * the paragraph text has mixed directionality!
          */
         switch (direction) {
-        case Bidi.DIRECTION_LEFT_TO_RIGHT:
-            /* make sure paraLevel is even */
-            paraLevel = (byte)((paraLevel + 1) & ~1);
-
+        case LTR:
             /* all levels are implicitly at paraLevel (important for getLevels()) */
             trailingWSStart = 0;
             break;
-        case Bidi.DIRECTION_RIGHT_TO_LEFT:
-            /* make sure paraLevel is odd */
-            paraLevel |= 1;
-
+        case RTL:
             /* all levels are implicitly at paraLevel (important for getLevels()) */
             trailingWSStart = 0;
             break;
         default:
-            this.impTabPair = impTab_DEFAULT;
-
+            /*
+             *  Choose the right implicit state table
+             */
+            switch(reorderingMode) {
+            case REORDER_DEFAULT:
+                this.impTabPair = impTab_DEFAULT;
+                break;
+            case REORDER_NUMBERS_SPECIAL:
+                this.impTabPair = impTab_NUMBERS_SPECIAL;
+                break;
+            case REORDER_GROUP_NUMBERS_WITH_R:
+                this.impTabPair = impTab_GROUP_NUMBERS_WITH_R;
+                break;
+            case REORDER_RUNS_ONLY:
+                /* we should never get here */
+                throw new InternalError("Internal ICU error in setPara");
+                /* break; */
+            case REORDER_INVERSE_NUMBERS_AS_L:
+                this.impTabPair = impTab_INVERSE_NUMBERS_AS_L;
+                break;
+            case REORDER_INVERSE_LIKE_DIRECT:
+                if ((reorderingOptions & OPTION_INSERT_MARKS) != 0) {
+                    this.impTabPair = impTab_INVERSE_LIKE_DIRECT_WITH_MARKS;
+                } else {
+                    this.impTabPair = impTab_INVERSE_LIKE_DIRECT;
+                }
+                break;
+            case REORDER_INVERSE_FOR_NUMBERS_SPECIAL:
+                if ((reorderingOptions & OPTION_INSERT_MARKS) != 0) {
+                    this.impTabPair = impTab_INVERSE_FOR_NUMBERS_SPECIAL_WITH_MARKS;
+                } else {
+                    this.impTabPair = impTab_INVERSE_FOR_NUMBERS_SPECIAL;
+                }
+                break;
+            }
             /*
              * If there are no external levels specified and there
              * are no significant explicit level codes in the text,
@@ -2601,7 +3695,7 @@
                     /* the values for this run's start are the same as for the previous run's end */
                     start = limit;
                     level = nextLevel;
-                    if ((start > 0) && (NoContextRTL(dirProps[start - 1]) == B)) {
+                    if ((start > 0) && (dirProps[start - 1] == B)) {
                         /* except if this is a new paragraph, then set sor = para level */
                         sor = GetLRFromLevel(GetParaLevelAt(start));
                     } else {
@@ -2609,7 +3703,9 @@
                     }
 
                     /* search for the limit of this run */
-                    while (++limit < length && levels[limit] == level) {}
+                    while ((++limit < length) &&
+                           ((levels[limit] == level) ||
+                            ((DirPropFlag(dirProps[limit]) & MASK_BN_EXPLICIT) != 0))) {}
 
                     /* get the correct level of the next run */
                     if (limit < length) {
@@ -2619,7 +3715,7 @@
                     }
 
                     /* determine eor from max(level, nextLevel); sor is last run's eor */
-                    if ((level & ~INTERNAL_LEVEL_OVERRIDE) < (nextLevel & ~INTERNAL_LEVEL_OVERRIDE)) {
+                    if (NoOverride(level) < NoOverride(nextLevel)) {
                         eor = GetLRFromLevel(nextLevel);
                     } else {
                         eor = GetLRFromLevel(level);
@@ -2627,12 +3723,12 @@
 
                     /* if the run consists of overridden directional types, then there
                        are no implicit types to be resolved */
-                    if ((level & INTERNAL_LEVEL_OVERRIDE) == 0) {
+                    if ((level & LEVEL_OVERRIDE) == 0) {
                         resolveImplicitLevels(start, limit, sor, eor);
                     } else {
                         /* remove the LEVEL_OVERRIDE flags */
                         do {
-                            levels[start++] &= ~INTERNAL_LEVEL_OVERRIDE;
+                            levels[start++] &= ~LEVEL_OVERRIDE;
                         } while (start < limit);
                     }
                 } while (limit  < length);
@@ -2644,8 +3740,46 @@
             break;
         }
 
-        resultLength += insertPoints.size;
-        paraBidi = this;             /* mark successful setPara */
+        /* add RLM for inverse Bidi with contextual orientation resolving
+         * to RTL which would not round-trip otherwise
+         */
+        if ((defaultParaLevel > 0) &&
+            ((reorderingOptions & OPTION_INSERT_MARKS) != 0) &&
+            ((reorderingMode == REORDER_INVERSE_LIKE_DIRECT) ||
+             (reorderingMode == REORDER_INVERSE_FOR_NUMBERS_SPECIAL))) {
+            int start, last;
+            byte level;
+            byte dirProp;
+            for (int i = 0; i < paraCount; i++) {
+                last = paras_limit[i] - 1;
+                level = paras_level[i];
+                if (level == 0)
+                    continue;           /* LTR paragraph */
+                start = i == 0 ? 0 : paras_limit[i - 1];
+                for (int j = last; j >= start; j--) {
+                    dirProp = dirProps[j];
+                    if (dirProp == L) {
+                        if (j < last) {
+                            while (dirProps[last] == B) {
+                                last--;
+                            }
+                        }
+                        addPoint(last, RLM_BEFORE);
+                        break;
+                    }
+                    if ((DirPropFlag(dirProp) & MASK_R_AL) != 0) {
+                        break;
+                    }
+                }
+            }
+        }
+
+        if ((reorderingOptions & OPTION_REMOVE_CONTROLS) != 0) {
+            resultLength -= controlCount;
+        } else {
+            resultLength += insertPoints.size;
+        }
+        setParaSuccess();
     }
 
     /**
@@ -2682,7 +3816,7 @@
      * For example, in pure LTR text with numbers the numbers would get
      * a resolved level of 2 higher than the surrounding text according to
      * the algorithm. This implementation may set all resolved levels to
-     * the same value in such a case.
+     * the same value in such a case.<p>
      *
      * @param paragraph a paragraph of text with optional character and
      *        paragraph attribute information
@@ -2693,13 +3827,14 @@
         byte paraLvl;
         char ch = paragraph.first();
         Boolean runDirection =
-            (Boolean) paragraph.getAttribute(TextAttributeConstants.RUN_DIRECTION);
+          (Boolean) paragraph.getAttribute(TextAttributeConstants.RUN_DIRECTION);
         Object shaper = paragraph.getAttribute(TextAttributeConstants.NUMERIC_SHAPING);
+
         if (runDirection == null) {
-            paraLvl = INTERNAL_LEVEL_DEFAULT_LTR;
+            paraLvl = LEVEL_DEFAULT_LTR;
         } else {
             paraLvl = (runDirection.equals(TextAttributeConstants.RUN_DIRECTION_LTR)) ?
-                        (byte)Bidi.DIRECTION_LEFT_TO_RIGHT : (byte)Bidi.DIRECTION_RIGHT_TO_LEFT;
+                        LTR : RTL;
         }
 
         byte[] lvls = null;
@@ -2717,7 +3852,7 @@
                     /* no-op */
                 } else if (level < 0) {
                     lvls = embeddingLevels;
-                    embeddingLevels[i] = (byte)((0 - level) | INTERNAL_LEVEL_OVERRIDE);
+                    embeddingLevels[i] = (byte)((0 - level) | LEVEL_OVERRIDE);
                 } else {
                     lvls = embeddingLevels;
                     embeddingLevels[i] = level;
@@ -2751,7 +3886,7 @@
      * @see #setPara
      * @stable ICU 3.8
      */
-    private void orderParagraphsLTR(boolean ordarParaLTR) {
+    public void orderParagraphsLTR(boolean ordarParaLTR) {
         orderParagraphsLTR = ordarParaLTR;
     }
 
@@ -2771,7 +3906,7 @@
      * @see #MIXED
      * @stable ICU 3.8
      */
-    private byte getDirection()
+    public byte getDirection()
     {
         verifyValidParaOrLine();
         return direction;
@@ -2819,31 +3954,25 @@
     }
 
     /**
-     * Get the index of a paragraph, given a position within the text.
-     *
-     * @param charIndex is the index of a character within the text, in the
-     *        range <code>[0..getProcessedLength()-1]</code>.
+     * Retrieves the Bidi class for a given code point.
+     * <p>If a <code>BidiClassifier</code> is defined and returns a value
+     * other than <code>CLASS_DEFAULT</code>, that value is used; otherwise
+     * the default class determination mechanism is invoked.</p>
      *
-     * @return The index of the paragraph containing the specified position,
-     *         starting from 0.
+     * @param c The code point to get a Bidi class for.
      *
-     * @throws IllegalStateException if this call is not preceded by a successful
-     *         call to <code>setPara</code> or <code>setLine</code>
-     * @throws IllegalArgumentException if charIndex is not within the legal range
+     * @return The Bidi class for the character <code>c</code> that is in effect
+     *         for this <code>Bidi</code> instance.
      *
-     * @see com.ibm.icu.text.BidiRun
-     * @see #getProcessedLength
      * @stable ICU 3.8
      */
-    public int getParagraphIndex(int charIndex)
-    {
-        verifyValidParaOrLine();
-        BidiBase bidi = paraBidi;             /* get Para object if Line object */
-        verifyRange(charIndex, 0, bidi.length);
-        int paraIndex;
-        for (paraIndex = 0; charIndex >= bidi.paras[paraIndex]; paraIndex++) {
-        }
-        return paraIndex;
+    public int getCustomizedClass(int c) {
+        int dir;
+
+        dir = bdp.getClass(c);
+        if (dir >= CHAR_DIRECTION_COUNT)
+            dir = ON;
+        return dir;
     }
 
     /**
@@ -2891,7 +4020,7 @@
         verifyRange(start, 0, limit);
         verifyRange(limit, 0, length+1);
 
-        return BidiLine.setLine(bidi, this, newBidi, newBidiBase, start, limit);
+        return BidiLine.setLine(this, newBidi, newBidiBase, start, limit);
     }
 
     /**
@@ -2911,9 +4040,11 @@
      */
     public byte getLevelAt(int charIndex)
     {
+        // for backward compatibility
         if (charIndex < 0 || charIndex >= length) {
             return (byte)getBaseLevel();
         }
+
         verifyValidParaOrLine();
         verifyRange(charIndex, 0, length);
         return BidiLine.getLevelAt(this, charIndex);
@@ -2932,7 +4063,7 @@
      *         call to <code>setPara</code> or <code>setLine</code>
      * @stable ICU 3.8
      */
-    private byte[] getLevels()
+    byte[] getLevels()
     {
         verifyValidParaOrLine();
         if (length <= 0) {
@@ -2963,6 +4094,78 @@
     }
 
     /**
+     *
+     * Get a <code>BidiRun</code> object according to its index. BidiRun methods
+     * may be used to retrieve the run's logical start, length and level,
+     * which can be even for an LTR run or odd for an RTL run.
+     * In an RTL run, the character at the logical start is
+     * visually on the right of the displayed run.
+     * The length is the number of characters in the run.<p>
+     * <code>countRuns()</code> is normally called
+     * before the runs are retrieved.
+     *
+     * <p>
+     *  Example:
+     * <pre>
+     *  Bidi bidi = new Bidi();
+     *  String text = "abc 123 DEFG xyz";
+     *  bidi.setPara(text, Bidi.RTL, null);
+     *  int i, count=bidi.countRuns(), logicalStart, visualIndex=0, length;
+     *  BidiRun run;
+     *  for (i = 0; i &lt; count; ++i) {
+     *      run = bidi.getVisualRun(i);
+     *      logicalStart = run.getStart();
+     *      length = run.getLength();
+     *      if (Bidi.LTR == run.getEmbeddingLevel()) {
+     *          do { // LTR
+     *              show_char(text.charAt(logicalStart++), visualIndex++);
+     *          } while (--length &gt; 0);
+     *      } else {
+     *          logicalStart += length;  // logicalLimit
+     *          do { // RTL
+     *              show_char(text.charAt(--logicalStart), visualIndex++);
+     *          } while (--length &gt; 0);
+     *      }
+     *  }
+     * </pre>
+     * <p>
+     * Note that in right-to-left runs, code like this places
+     * second surrogates before first ones (which is generally a bad idea)
+     * and combining characters before base characters.
+     * <p>
+     * Use of <code>{@link #writeReordered}</code>, optionally with the
+     * <code>{@link #KEEP_BASE_COMBINING}</code> option, can be considered in
+     * order to avoid these issues.
+     *
+     * @param runIndex is the number of the run in visual order, in the
+     *        range <code>[0..countRuns()-1]</code>.
+     *
+     * @return a BidiRun object containing the details of the run. The
+     *         directionality of the run is
+     *         <code>LTR==0</code> or <code>RTL==1</code>,
+     *         never <code>MIXED</code>.
+     *
+     * @throws IllegalStateException if this call is not preceded by a successful
+     *         call to <code>setPara</code> or <code>setLine</code>
+     * @throws IllegalArgumentException if <code>runIndex</code> is not in
+     *         the range <code>0&lt;=runIndex&lt;countRuns()</code>
+     *
+     * @see #countRuns()
+     * @see com.ibm.icu.text.BidiRun
+     * @see com.ibm.icu.text.BidiRun#getStart()
+     * @see com.ibm.icu.text.BidiRun#getLength()
+     * @see com.ibm.icu.text.BidiRun#getEmbeddingLevel()
+     * @stable ICU 3.8
+     */
+    BidiRun getVisualRun(int runIndex)
+    {
+        verifyValidParaOrLine();
+        BidiLine.getRuns(this);
+        verifyRange(runIndex, 0, runCount);
+        return BidiLine.getVisualRun(this, runIndex);
+    }
+
+    /**
      * Get a visual-to-logical index map (array) for the characters in the
      * <code>Bidi</code> (paragraph or line) object.
      * <p>
@@ -3031,19 +4234,10 @@
      * Constant indicating that the base direction depends on the first strong
      * directional character in the text according to the Unicode Bidirectional
      * Algorithm. If no strong directional character is present, the base
-     * direction is left-to-right.
-     * @stable ICU 3.8
-     */
-    private static final int INTERNAL_DIRECTION_DEFAULT_LEFT_TO_RIGHT = 0x7e;
-
-    /**
-     * Constant indicating that the base direction depends on the first strong
-     * directional character in the text according to the Unicode Bidirectional
-     * Algorithm. If no strong directional character is present, the base
      * direction is right-to-left.
      * @stable ICU 3.8
      */
-    private static final int INTERMAL_DIRECTION_DEFAULT_RIGHT_TO_LEFT = 0x7f;
+    public static final int DIRECTION_DEFAULT_RIGHT_TO_LEFT = LEVEL_DEFAULT_RTL;
 
     /**
      * Create Bidi from the given text, embedding, and direction information.
@@ -3080,27 +4274,27 @@
      * @stable ICU 3.8
      */
     public BidiBase(char[] text,
-             int textStart,
-             byte[] embeddings,
-             int embStart,
-             int paragraphLength,
-             int flags)
-     {
+            int textStart,
+            byte[] embeddings,
+            int embStart,
+            int paragraphLength,
+            int flags)
+    {
         this(0, 0);
         byte paraLvl;
         switch (flags) {
         case Bidi.DIRECTION_LEFT_TO_RIGHT:
         default:
-            paraLvl = Bidi.DIRECTION_LEFT_TO_RIGHT;
+            paraLvl = LTR;
             break;
         case Bidi.DIRECTION_RIGHT_TO_LEFT:
-            paraLvl = Bidi.DIRECTION_RIGHT_TO_LEFT;
+            paraLvl = RTL;
             break;
         case Bidi.DIRECTION_DEFAULT_LEFT_TO_RIGHT:
-            paraLvl = INTERNAL_LEVEL_DEFAULT_LTR;
+            paraLvl = LEVEL_DEFAULT_LTR;
             break;
         case Bidi.DIRECTION_DEFAULT_RIGHT_TO_LEFT:
-            paraLvl = INTERNAL_LEVEL_DEFAULT_RTL;
+            paraLvl = LEVEL_DEFAULT_RTL;
             break;
         }
         byte[] paraEmbeddings;
@@ -3112,7 +4306,7 @@
             for (int i = 0; i < paragraphLength; i++) {
                 lev = embeddings[i + embStart];
                 if (lev < 0) {
-                    lev = (byte)((- lev) | INTERNAL_LEVEL_OVERRIDE);
+                    lev = (byte)((- lev) | LEVEL_OVERRIDE);
                 } else if (lev == 0) {
                     lev = paraLvl;
                     if (paraLvl > MAX_EXPLICIT_LEVEL) {
@@ -3122,13 +4316,10 @@
                 paraEmbeddings[i] = lev;
             }
         }
-        if (textStart == 0 && embStart == 0 && paragraphLength == text.length) {
-            setPara(text, paraLvl, paraEmbeddings);
-        } else {
-            char[] paraText = new char[paragraphLength];
-            System.arraycopy(text, textStart, paraText, 0, paragraphLength);
-            setPara(paraText, paraLvl, paraEmbeddings);
-        }
+
+        char[] paraText = new char[paragraphLength];
+        System.arraycopy(text, textStart, paraText, 0, paragraphLength);
+        setPara(paraText, paraLvl, paraEmbeddings);
     }
 
     /**
@@ -3148,7 +4339,7 @@
     }
 
     /**
-    * Return true if the line is all left-to-right text and the base direction
+     * Return true if the line is all left-to-right text and the base direction
      * is left-to-right.
      *
      * @return true if the line is all left-to-right text and the base direction
@@ -3160,7 +4351,7 @@
      */
     public boolean isLeftToRight()
     {
-        return (getDirection() == Bidi.DIRECTION_LEFT_TO_RIGHT && (paraLevel & 1) == 0);
+        return (getDirection() == LTR && (paraLevel & 1) == 0);
     }
 
     /**
@@ -3176,7 +4367,7 @@
      */
     public boolean isRightToLeft()
     {
-        return (getDirection() == Bidi.DIRECTION_RIGHT_TO_LEFT && (paraLevel & 1) == 1);
+        return (getDirection() == RTL && (paraLevel & 1) == 1);
     }
 
     /**
@@ -3191,7 +4382,7 @@
      */
     public boolean baseIsLeftToRight()
     {
-        return (getParaLevel() == Bidi.DIRECTION_LEFT_TO_RIGHT);
+        return (getParaLevel() == LTR);
     }
 
     /**
@@ -3212,8 +4403,8 @@
     /**
      * Compute the logical to visual run mapping
      */
-    private void getLogicalToVisualRunsMap()
-    {
+     void getLogicalToVisualRunsMap()
+     {
         if (isGoodLogicalToVisualRunsMap) {
             return;
         }
@@ -3231,9 +4422,8 @@
         for (i = 0; i < count; i++) {
             logicalToVisualRunsMap[i] = (int)(keys[i] & 0x00000000FFFFFFFF);
         }
-        keys = null;
         isGoodLogicalToVisualRunsMap = true;
-    }
+     }
 
     /**
      * Return the level of the nth logical run in this line.
@@ -3252,9 +4442,12 @@
     {
         verifyValidParaOrLine();
         BidiLine.getRuns(this);
+
+        // for backward compatibility
         if (run < 0 || run >= runCount) {
             return getParaLevel();
         }
+
         getLogicalToVisualRunsMap();
         return runs[logicalToVisualRunsMap[run]].level;
     }
@@ -3277,12 +4470,14 @@
     {
         verifyValidParaOrLine();
         BidiLine.getRuns(this);
+
+        // for backward compatibility
         if (runCount == 1) {
             return 0;
         } else if (run == runCount) {
             return length;
         }
-        verifyIndex(run, 0, runCount);
+
         getLogicalToVisualRunsMap();
         return runs[logicalToVisualRunsMap[run]].start;
     }
@@ -3306,10 +4501,12 @@
     {
         verifyValidParaOrLine();
         BidiLine.getRuns(this);
+
+        // for backward compatibility
         if (runCount == 1) {
             return length;
         }
-        verifyIndex(run, 0, runCount);
+
         getLogicalToVisualRunsMap();
         int idx = logicalToVisualRunsMap[run];
         int len = idx == 0 ? runs[idx].limit :
@@ -3336,7 +4533,7 @@
             int start,
             int limit)
     {
-        final int RTLMask = (1 << Bidi.DIRECTION_RIGHT_TO_LEFT |
+        final int RTLMask = (1 << R |
                 1 << AL |
                 1 << RLE |
                 1 << RLO |
@@ -3346,6 +4543,7 @@
             throw new IllegalArgumentException("Value start " + start +
                       " is out of range 0 to " + limit);
         }
+
         for (int i = start; i < limit; ++i) {
             if (Character.isHighSurrogate(text[i]) && i < (limit-1) &&
                 Character.isLowSurrogate(text[i+1])) {
@@ -3356,6 +4554,7 @@
                 return true;
             }
         }
+
         return false;
     }
 
@@ -3382,8 +4581,9 @@
             int objectStart,
             int count)
     {
+        // for backward compatibility
         if (0 > levelStart || levels.length <= levelStart) {
-            throw new IllegalArgumentException("Value levelStart " +
+          throw new IllegalArgumentException("Value levelStart " +
                       levelStart + " is out of range 0 to " +
                       (levels.length-1));
         }
@@ -3397,6 +4597,7 @@
                       levelStart + " is out of range 0 to " +
                       (objects.length - objectStart));
         }
+
         byte[] reorderLevels = new byte[count];
         System.arraycopy(levels, levelStart, reorderLevels, 0, count);
         int[] indexMap = reorderVisual(reorderLevels);
@@ -3408,6 +4609,74 @@
     }
 
     /**
+     * Take a <code>Bidi</code> object containing the reordering
+     * information for a piece of text (one or more paragraphs) set by
+     * <code>setPara()</code> or for a line of text set by <code>setLine()</code>
+     * and return a string containing the reordered text.
+     *
+     * <p>The text may have been aliased (only a reference was stored
+     * without copying the contents), thus it must not have been modified
+     * since the <code>setPara()</code> call.</p>
+     *
+     * This method preserves the integrity of characters with multiple
+     * code units and (optionally) combining characters.
+     * Characters in RTL runs can be replaced by mirror-image characters
+     * in the returned string. Note that "real" mirroring has to be done in a
+     * rendering engine by glyph selection and that for many "mirrored"
+     * characters there are no Unicode characters as mirror-image equivalents.
+     * There are also options to insert or remove Bidi control
+     * characters; see the descriptions of the return value and the
+     * <code>options</code> parameter, and of the option bit flags.
+     *
+     * @param options A bit set of options for the reordering that control
+     *                how the reordered text is written.
+     *                The options include mirroring the characters on a code
+     *                point basis and inserting LRM characters, which is used
+     *                especially for transforming visually stored text
+     *                to logically stored text (although this is still an
+     *                imperfect implementation of an "inverse Bidi" algorithm
+     *                because it uses the "forward Bidi" algorithm at its core).
+     *                The available options are:
+     *                <code>DO_MIRRORING</code>,
+     *                <code>INSERT_LRM_FOR_NUMERIC</code>,
+     *                <code>KEEP_BASE_COMBINING</code>,
+     *                <code>OUTPUT_REVERSE</code>,
+     *                <code>REMOVE_BIDI_CONTROLS</code>,
+     *                <code>STREAMING</code>
+     *
+     * @return The reordered text.
+     *         If the <code>INSERT_LRM_FOR_NUMERIC</code> option is set, then
+     *         the length of the returned string could be as large as
+     *         <code>getLength()+2*countRuns()</code>.<br>
+     *         If the <code>REMOVE_BIDI_CONTROLS</code> option is set, then the
+     *         length of the returned string may be less than
+     *         <code>getLength()</code>.<br>
+     *         If none of these options is set, then the length of the returned
+     *         string will be exactly <code>getProcessedLength()</code>.
+     *
+     * @throws IllegalStateException if this call is not preceded by a successful
+     *         call to <code>setPara</code> or <code>setLine</code>
+     *
+     * @see #DO_MIRRORING
+     * @see #INSERT_LRM_FOR_NUMERIC
+     * @see #KEEP_BASE_COMBINING
+     * @see #OUTPUT_REVERSE
+     * @see #REMOVE_BIDI_CONTROLS
+     * @see #OPTION_STREAMING
+     * @see #getProcessedLength
+     * @stable ICU 3.8
+     */
+    public String writeReordered(int options)
+    {
+        verifyValidParaOrLine();
+        if (length == 0) {
+            /* nothing to do */
+            return "";
+        }
+        return BidiWriter.writeReordered(this, options);
+    }
+
+    /**
      * Display the bidi internal state, used in debugging.
      */
     public String toString() {
@@ -3507,4 +4776,5 @@
             }
         }
     }
+
 }
--- a/jdk/src/java.base/share/classes/sun/text/bidi/BidiLine.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/bidi/BidiLine.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2009, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2009, 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
@@ -22,17 +22,13 @@
  * or visit www.oracle.com if you need additional information or have any
  * questions.
  */
+
 /*
- *******************************************************************************
- * (C) Copyright IBM Corp. and others, 1996-2009 - All Rights Reserved         *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
- *******************************************************************************
- */
+*******************************************************************************
+*   Copyright (C) 2001-2014, International Business Machines
+*   Corporation and others.  All Rights Reserved.
+*******************************************************************************
+*/
 /* Written by Simon Montagu, Matitiahu Allouche
  * (ported from C code written by Markus W. Scherer)
  */
@@ -42,7 +38,7 @@
 import java.text.Bidi;
 import java.util.Arrays;
 
-public final class BidiLine {
+final class BidiLine {
 
     /*
      * General remarks about the functions in this file:
@@ -122,13 +118,13 @@
            level of B chars from 0 to paraLevel in getLevels when
            orderParagraphsLTR==TRUE
         */
-        if (BidiBase.NoContextRTL(dirProps[start - 1]) == BidiBase.B) {
+        if (dirProps[start - 1] == BidiBase.B) {
             bidiBase.trailingWSStart = start;   /* currently == bidiBase.length */
             return;
         }
         /* go backwards across all WS, BN, explicit codes */
         while (start > 0 &&
-                (BidiBase.DirPropFlagNC(dirProps[start - 1]) & BidiBase.MASK_WS) != 0) {
+                (BidiBase.DirPropFlag(dirProps[start - 1]) & BidiBase.MASK_WS) != 0) {
             --start;
         }
 
@@ -140,13 +136,11 @@
         bidiBase.trailingWSStart=start;
     }
 
-    public static Bidi setLine(Bidi bidi, BidiBase paraBidi,
-                               Bidi newBidi, BidiBase newBidiBase,
-                               int start, int limit) {
+    static Bidi setLine(BidiBase paraBidi,
+                              Bidi newBidi, BidiBase lineBidi,
+                              int start, int limit) {
         int length;
 
-        BidiBase lineBidi = newBidiBase;
-
         /* set the values in lineBidi from its paraBidi parent */
         /* class members are already initialized to 0 */
         // lineBidi.paraBidi = null;        /* mark unfinished setLine */
@@ -161,6 +155,8 @@
         lineBidi.paraLevel = paraBidi.GetParaLevelAt(start);
         lineBidi.paraCount = paraBidi.paraCount;
         lineBidi.runs = new BidiRun[0];
+        lineBidi.reorderingMode = paraBidi.reorderingMode;
+        lineBidi.reorderingOptions = paraBidi.reorderingOptions;
         if (paraBidi.controlCount > 0) {
             int j;
             for (j = start; j < limit; j++) {
@@ -206,7 +202,7 @@
             setTrailingWSStart(lineBidi);
             trailingWSStart = lineBidi.trailingWSStart;
 
-            /* recalculate lineBidi.direction */
+            /* recalculate lineBidiBase.direction */
             if (trailingWSStart == 0) {
                 /* all levels are at paraLevel */
                 lineBidi.direction = (byte)(lineBidi.paraLevel & 1);
@@ -260,7 +256,8 @@
             }
         }
 
-        newBidiBase.paraBidi = paraBidi; /* mark successful setLine */
+        lineBidi.paraBidi = paraBidi;     /* mark successful setLine */
+
         return newBidi;
     }
 
@@ -303,30 +300,19 @@
         return bidiBase.levels;
     }
 
-    static BidiRun getLogicalRun(BidiBase bidiBase, int logicalPosition)
-    {
-        /* this is done based on runs rather than on levels since levels have
-           a special interpretation when REORDER_RUNS_ONLY
-         */
-        BidiRun newRun = new BidiRun(), iRun;
-        getRuns(bidiBase);
-        int runCount = bidiBase.runCount;
-        int visualStart = 0, logicalLimit = 0;
-        iRun = bidiBase.runs[0];
+    static BidiRun getVisualRun(BidiBase bidiBase, int runIndex) {
+        int start = bidiBase.runs[runIndex].start;
+        int limit;
+        byte level = bidiBase.runs[runIndex].level;
 
-        for (int i = 0; i < runCount; i++) {
-            iRun = bidiBase.runs[i];
-            logicalLimit = iRun.start + iRun.limit - visualStart;
-            if ((logicalPosition >= iRun.start) &&
-                (logicalPosition < logicalLimit)) {
-                break;
-            }
-            visualStart = iRun.limit;
+        if (runIndex > 0) {
+            limit = start +
+                    bidiBase.runs[runIndex].limit -
+                    bidiBase.runs[runIndex - 1].limit;
+        } else {
+            limit = start + bidiBase.runs[0].limit;
         }
-        newRun.start = iRun.start;
-        newRun.limit = logicalLimit;
-        newRun.level = iRun.level;
-        return newRun;
+        return new BidiRun(start, limit, level);
     }
 
     /* in trivial cases there is only one trivial run; called by getRuns() */
@@ -502,7 +488,7 @@
             int length = bidiBase.length, limit;
             byte[] levels = bidiBase.levels;
             int i, runCount;
-            byte level = BidiBase.INTERNAL_LEVEL_DEFAULT_LTR;   /* initialize with no valid level */
+            byte level = -1;    /* initialize with no valid level */
             /*
              * If there are WS characters at the end of the line
              * and the run preceding them has a level different from
@@ -651,7 +637,7 @@
         maxLevel = 0;
         for (start = levels.length; start>0; ) {
             level = levels[--start];
-            if (level > BidiBase.MAX_EXPLICIT_LEVEL + 1) {
+            if (level < 0 || level > (BidiBase.MAX_EXPLICIT_LEVEL + 1)) {
                 return null;
             }
             if (level < minLevel) {
--- a/jdk/src/java.base/share/classes/sun/text/bidi/BidiRun.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/bidi/BidiRun.java	Wed Jul 05 20:42:36 2017 +0200
@@ -55,7 +55,7 @@
  *
  * @see com.ibm.icu.text.Bidi
  */
-public class BidiRun {
+class BidiRun {
 
     int start;              /* first logical position of the run */
     int limit;              /* last visual position of the run +1 */
@@ -106,7 +106,7 @@
     /**
      * Get level of run
      */
-    public byte getEmbeddingLevel()
+    byte getEmbeddingLevel()
     {
         return level;
     }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/sun/text/bidi/BidiWriter.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,452 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/*
+*******************************************************************************
+*   Copyright (C) 2001-2010, International Business Machines
+*   Corporation and others.  All Rights Reserved.
+*******************************************************************************
+*/
+/* Written by Simon Montagu, Matitiahu Allouche
+ * (ported from C code written by Markus W. Scherer)
+ */
+
+package sun.text.bidi;
+
+import sun.text.normalizer.UCharacter;
+import sun.text.normalizer.UTF16;
+
+final class BidiWriter {
+
+    /** Bidi control code points */
+    static final char LRM_CHAR = 0x200e;
+    static final char RLM_CHAR = 0x200f;
+    static final int MASK_R_AL = (1 << UCharacter.RIGHT_TO_LEFT |
+                                  1 << UCharacter.RIGHT_TO_LEFT_ARABIC);
+
+    private static boolean IsCombining(int type) {
+        return ((1<<type &
+                (1<<UCharacter.NON_SPACING_MARK |
+                 1<<UCharacter.COMBINING_SPACING_MARK |
+                 1<<UCharacter.ENCLOSING_MARK)) != 0);
+    }
+
+    /*
+     * When we have OUTPUT_REVERSE set on writeReordered(), then we
+     * semantically write RTL runs in reverse and later reverse them again.
+     * Instead, we actually write them in forward order to begin with.
+     * However, if the RTL run was to be mirrored, we need to mirror here now
+     * since the implicit second reversal must not do it.
+     * It looks strange to do mirroring in LTR output, but it is only because
+     * we are writing RTL output in reverse.
+     */
+    private static String doWriteForward(String src, int options) {
+        /* optimize for several combinations of options */
+        switch(options&(BidiBase.REMOVE_BIDI_CONTROLS|BidiBase.DO_MIRRORING)) {
+        case 0: {
+            /* simply return the LTR run */
+            return src;
+        }
+        case BidiBase.DO_MIRRORING: {
+            StringBuffer dest = new StringBuffer(src.length());
+
+            /* do mirroring */
+            int i=0;
+            int c;
+
+            do {
+                c = UTF16.charAt(src, i);
+                i += UTF16.getCharCount(c);
+                UTF16.append(dest, UCharacter.getMirror(c));
+            } while(i < src.length());
+            return dest.toString();
+        }
+        case BidiBase.REMOVE_BIDI_CONTROLS: {
+            StringBuilder dest = new StringBuilder(src.length());
+
+            /* copy the LTR run and remove any Bidi control characters */
+            int i = 0;
+            char c;
+            do {
+                c = src.charAt(i++);
+                if(!BidiBase.IsBidiControlChar(c)) {
+                    dest.append(c);
+                }
+            } while(i < src.length());
+            return dest.toString();
+        }
+        default: {
+            StringBuffer dest = new StringBuffer(src.length());
+
+            /* remove Bidi control characters and do mirroring */
+            int i = 0;
+            int c;
+            do {
+                c = UTF16.charAt(src, i);
+                i += UTF16.getCharCount(c);
+                if(!BidiBase.IsBidiControlChar(c)) {
+                    UTF16.append(dest, UCharacter.getMirror(c));
+                }
+            } while(i < src.length());
+                return dest.toString();
+            }
+        } /* end of switch */
+    }
+
+    private static String doWriteForward(char[] text, int start, int limit,
+                                         int options) {
+        return doWriteForward(new String(text, start, limit - start), options);
+    }
+
+    static String writeReverse(String src, int options) {
+        /*
+         * RTL run -
+         *
+         * RTL runs need to be copied to the destination in reverse order
+         * of code points, not code units, to keep Unicode characters intact.
+         *
+         * The general strategy for this is to read the source text
+         * in backward order, collect all code units for a code point
+         * (and optionally following combining characters, see below),
+         * and copy all these code units in ascending order
+         * to the destination for this run.
+         *
+         * Several options request whether combining characters
+         * should be kept after their base characters,
+         * whether Bidi control characters should be removed, and
+         * whether characters should be replaced by their mirror-image
+         * equivalent Unicode characters.
+         */
+        StringBuffer dest = new StringBuffer(src.length());
+
+        /* optimize for several combinations of options */
+        switch (options &
+                (BidiBase.REMOVE_BIDI_CONTROLS |
+                 BidiBase.DO_MIRRORING |
+                 BidiBase.KEEP_BASE_COMBINING)) {
+
+        case 0:
+            /*
+             * With none of the "complicated" options set, the destination
+             * run will have the same length as the source run,
+             * and there is no mirroring and no keeping combining characters
+             * with their base characters.
+             *
+             * XXX: or dest = UTF16.reverse(new StringBuffer(src));
+             */
+
+            int srcLength = src.length();
+
+            /* preserve character integrity */
+            do {
+                /* i is always after the last code unit known to need to be kept
+                 *  in this segment */
+                int i = srcLength;
+
+                /* collect code units for one base character */
+                srcLength -= UTF16.getCharCount(UTF16.charAt(src,
+                                                             srcLength - 1));
+
+                /* copy this base character */
+                dest.append(src.substring(srcLength, i));
+            } while(srcLength > 0);
+            break;
+
+        case BidiBase.KEEP_BASE_COMBINING:
+            /*
+             * Here, too, the destination
+             * run will have the same length as the source run,
+             * and there is no mirroring.
+             * We do need to keep combining characters with their base
+             * characters.
+             */
+            srcLength = src.length();
+
+            /* preserve character integrity */
+            do {
+                /* i is always after the last code unit known to need to be kept
+                 *  in this segment */
+                int c;
+                int i = srcLength;
+
+                /* collect code units and modifier letters for one base
+                 * character */
+                do {
+                    c = UTF16.charAt(src, srcLength - 1);
+                    srcLength -= UTF16.getCharCount(c);
+                } while(srcLength > 0 && IsCombining(UCharacter.getType(c)));
+
+                /* copy this "user character" */
+                dest.append(src.substring(srcLength, i));
+            } while(srcLength > 0);
+            break;
+
+        default:
+            /*
+             * With several "complicated" options set, this is the most
+             * general and the slowest copying of an RTL run.
+             * We will do mirroring, remove Bidi controls, and
+             * keep combining characters with their base characters
+             * as requested.
+             */
+            srcLength = src.length();
+
+            /* preserve character integrity */
+            do {
+                /* i is always after the last code unit known to need to be kept
+                 *  in this segment */
+                int i = srcLength;
+
+                /* collect code units for one base character */
+                int c = UTF16.charAt(src, srcLength - 1);
+                srcLength -= UTF16.getCharCount(c);
+                if ((options & BidiBase.KEEP_BASE_COMBINING) != 0) {
+                    /* collect modifier letters for this base character */
+                    while(srcLength > 0 && IsCombining(UCharacter.getType(c))) {
+                        c = UTF16.charAt(src, srcLength - 1);
+                        srcLength -= UTF16.getCharCount(c);
+                    }
+                }
+
+                if ((options & BidiBase.REMOVE_BIDI_CONTROLS) != 0 &&
+                    BidiBase.IsBidiControlChar(c)) {
+                    /* do not copy this Bidi control character */
+                    continue;
+                }
+
+                /* copy this "user character" */
+                int j = srcLength;
+                if((options & BidiBase.DO_MIRRORING) != 0) {
+                    /* mirror only the base character */
+                    c = UCharacter.getMirror(c);
+                    UTF16.append(dest, c);
+                    j += UTF16.getCharCount(c);
+                }
+                dest.append(src.substring(j, i));
+            } while(srcLength > 0);
+            break;
+        } /* end of switch */
+
+        return dest.toString();
+    }
+
+    static String doWriteReverse(char[] text, int start, int limit, int options) {
+        return writeReverse(new String(text, start, limit - start), options);
+    }
+
+    static String writeReordered(BidiBase bidi, int options) {
+        int run, runCount;
+        StringBuilder dest;
+        char[] text = bidi.text;
+        runCount = bidi.countRuns();
+
+        /*
+         * Option "insert marks" implies BidiBase.INSERT_LRM_FOR_NUMERIC if the
+         * reordering mode (checked below) is appropriate.
+         */
+        if ((bidi.reorderingOptions & BidiBase.OPTION_INSERT_MARKS) != 0) {
+            options |= BidiBase.INSERT_LRM_FOR_NUMERIC;
+            options &= ~BidiBase.REMOVE_BIDI_CONTROLS;
+        }
+        /*
+         * Option "remove controls" implies BidiBase.REMOVE_BIDI_CONTROLS
+         * and cancels BidiBase.INSERT_LRM_FOR_NUMERIC.
+         */
+        if ((bidi.reorderingOptions & BidiBase.OPTION_REMOVE_CONTROLS) != 0) {
+            options |= BidiBase.REMOVE_BIDI_CONTROLS;
+            options &= ~BidiBase.INSERT_LRM_FOR_NUMERIC;
+        }
+        /*
+         * If we do not perform the "inverse Bidi" algorithm, then we
+         * don't need to insert any LRMs, and don't need to test for it.
+         */
+        if ((bidi.reorderingMode != BidiBase.REORDER_INVERSE_NUMBERS_AS_L) &&
+            (bidi.reorderingMode != BidiBase.REORDER_INVERSE_LIKE_DIRECT)  &&
+            (bidi.reorderingMode != BidiBase.REORDER_INVERSE_FOR_NUMBERS_SPECIAL) &&
+            (bidi.reorderingMode != BidiBase.REORDER_RUNS_ONLY)) {
+            options &= ~BidiBase.INSERT_LRM_FOR_NUMERIC;
+        }
+        dest = new StringBuilder((options & BidiBase.INSERT_LRM_FOR_NUMERIC) != 0 ?
+                                 bidi.length * 2 : bidi.length);
+        /*
+         * Iterate through all visual runs and copy the run text segments to
+         * the destination, according to the options.
+         *
+         * The tests for where to insert LRMs ignore the fact that there may be
+         * BN codes or non-BMP code points at the beginning and end of a run;
+         * they may insert LRMs unnecessarily but the tests are faster this way
+         * (this would have to be improved for UTF-8).
+         */
+        if ((options & BidiBase.OUTPUT_REVERSE) == 0) {
+            /* forward output */
+            if ((options & BidiBase.INSERT_LRM_FOR_NUMERIC) == 0) {
+                /* do not insert Bidi controls */
+                for (run = 0; run < runCount; ++run) {
+                    BidiRun bidiRun = bidi.getVisualRun(run);
+                    if (bidiRun.isEvenRun()) {
+                        dest.append(doWriteForward(text, bidiRun.start,
+                                                   bidiRun.limit,
+                                                   options & ~BidiBase.DO_MIRRORING));
+                     } else {
+                        dest.append(doWriteReverse(text, bidiRun.start,
+                                                   bidiRun.limit, options));
+                     }
+                }
+            } else {
+                /* insert Bidi controls for "inverse Bidi" */
+                byte[] dirProps = bidi.dirProps;
+                char uc;
+                int markFlag;
+
+                for (run = 0; run < runCount; ++run) {
+                    BidiRun bidiRun = bidi.getVisualRun(run);
+                    markFlag=0;
+                    /* check if something relevant in insertPoints */
+                    markFlag = bidi.runs[run].insertRemove;
+                    if (markFlag < 0) { /* bidi controls count */
+                        markFlag = 0;
+                    }
+                    if (bidiRun.isEvenRun()) {
+                        if (bidi.isInverse() &&
+                                dirProps[bidiRun.start] != BidiBase.L) {
+                            markFlag |= BidiBase.LRM_BEFORE;
+                        }
+                        if ((markFlag & BidiBase.LRM_BEFORE) != 0) {
+                            uc = LRM_CHAR;
+                        } else if ((markFlag & BidiBase.RLM_BEFORE) != 0) {
+                            uc = RLM_CHAR;
+                        } else {
+                            uc = 0;
+                        }
+                        if (uc != 0) {
+                            dest.append(uc);
+                        }
+                        dest.append(doWriteForward(text,
+                                                   bidiRun.start, bidiRun.limit,
+                                                   options & ~BidiBase.DO_MIRRORING));
+
+                        if (bidi.isInverse() &&
+                             dirProps[bidiRun.limit - 1] != BidiBase.L) {
+                            markFlag |= BidiBase.LRM_AFTER;
+                        }
+                        if ((markFlag & BidiBase.LRM_AFTER) != 0) {
+                            uc = LRM_CHAR;
+                        } else if ((markFlag & BidiBase.RLM_AFTER) != 0) {
+                            uc = RLM_CHAR;
+                        } else {
+                            uc = 0;
+                        }
+                        if (uc != 0) {
+                            dest.append(uc);
+                        }
+                    } else { /* RTL run */
+                        if (bidi.isInverse() &&
+                            !bidi.testDirPropFlagAt(MASK_R_AL,
+                                                    bidiRun.limit - 1)) {
+                            markFlag |= BidiBase.RLM_BEFORE;
+                        }
+                        if ((markFlag & BidiBase.LRM_BEFORE) != 0) {
+                            uc = LRM_CHAR;
+                        } else if ((markFlag & BidiBase.RLM_BEFORE) != 0) {
+                            uc = RLM_CHAR;
+                        } else {
+                            uc = 0;
+                        }
+                        if (uc != 0) {
+                            dest.append(uc);
+                        }
+                        dest.append(doWriteReverse(text, bidiRun.start,
+                                                   bidiRun.limit, options));
+
+                        if(bidi.isInverse() &&
+                                (MASK_R_AL & BidiBase.DirPropFlag(dirProps[bidiRun.start])) == 0) {
+                            markFlag |= BidiBase.RLM_AFTER;
+                        }
+                        if ((markFlag & BidiBase.LRM_AFTER) != 0) {
+                            uc = LRM_CHAR;
+                        } else if ((markFlag & BidiBase.RLM_AFTER) != 0) {
+                            uc = RLM_CHAR;
+                        } else {
+                            uc = 0;
+                        }
+                        if (uc != 0) {
+                            dest.append(uc);
+                        }
+                    }
+                }
+            }
+        } else {
+            /* reverse output */
+            if((options & BidiBase.INSERT_LRM_FOR_NUMERIC) == 0) {
+                /* do not insert Bidi controls */
+                for(run = runCount; --run >= 0; ) {
+                    BidiRun bidiRun = bidi.getVisualRun(run);
+                    if (bidiRun.isEvenRun()) {
+                        dest.append(doWriteReverse(text,
+                                                   bidiRun.start, bidiRun.limit,
+                                                   options & ~BidiBase.DO_MIRRORING));
+                    } else {
+                        dest.append(doWriteForward(text, bidiRun.start,
+                                                   bidiRun.limit, options));
+                    }
+                }
+            } else {
+                /* insert Bidi controls for "inverse Bidi" */
+
+                byte[] dirProps = bidi.dirProps;
+
+                for (run = runCount; --run >= 0; ) {
+                    /* reverse output */
+                    BidiRun bidiRun = bidi.getVisualRun(run);
+                    if (bidiRun.isEvenRun()) {
+                        if (dirProps[bidiRun.limit - 1] != BidiBase.L) {
+                            dest.append(LRM_CHAR);
+                        }
+
+                        dest.append(doWriteReverse(text, bidiRun.start,
+                                bidiRun.limit, options & ~BidiBase.DO_MIRRORING));
+
+                        if (dirProps[bidiRun.start] != BidiBase.L) {
+                            dest.append(LRM_CHAR);
+                        }
+                    } else {
+                        if ((MASK_R_AL & BidiBase.DirPropFlag(dirProps[bidiRun.start])) == 0) {
+                            dest.append(RLM_CHAR);
+                        }
+
+                        dest.append(doWriteForward(text, bidiRun.start,
+                                                   bidiRun.limit, options));
+
+                        if ((MASK_R_AL & BidiBase.DirPropFlag(dirProps[bidiRun.limit - 1])) == 0) {
+                            dest.append(RLM_CHAR);
+                        }
+                    }
+                }
+            }
+        }
+
+        return dest.toString();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/BMPSet.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,526 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/*
+ ******************************************************************************
+ *
+ *   Copyright (C) 2009-2014, International Business Machines
+ *   Corporation and others.  All Rights Reserved.
+ *
+ ******************************************************************************
+ */
+
+package sun.text.normalizer;
+
+import sun.text.normalizer.UnicodeSet.SpanCondition;
+
+/**
+ * Helper class for frozen UnicodeSets, implements contains() and span() optimized for BMP code points.
+ *
+ * Latin-1: Look up bytes.
+ * 2-byte characters: Bits organized vertically.
+ * 3-byte characters: Use zero/one/mixed data per 64-block in U+0000..U+FFFF, with mixed for illegal ranges.
+ * Supplementary characters: Call contains() on the parent set.
+ */
+final class BMPSet {
+
+    /**
+     * One boolean ('true' or 'false') per Latin-1 character.
+     */
+    private boolean[] latin1Contains;
+
+    /**
+     * One bit per code point from U+0000..U+07FF. The bits are organized vertically; consecutive code points
+     * correspond to the same bit positions in consecutive table words. With code point parts lead=c{10..6}
+     * trail=c{5..0} it is set.contains(c)==(table7FF[trail] bit lead)
+     *
+     * Bits for 0..7F (non-shortest forms) are set to the result of contains(FFFD) for faster validity checking at
+     * runtime.
+     */
+    private int[] table7FF;
+
+    /**
+     * One bit per 64 BMP code points. The bits are organized vertically; consecutive 64-code point blocks
+     * correspond to the same bit position in consecutive table words. With code point parts lead=c{15..12}
+     * t1=c{11..6} test bits (lead+16) and lead in bmpBlockBits[t1]. If the upper bit is 0, then the lower bit
+     * indicates if contains(c) for all code points in the 64-block. If the upper bit is 1, then the block is mixed
+     * and set.contains(c) must be called.
+     *
+     * Bits for 0..7FF (non-shortest forms) and D800..DFFF are set to the result of contains(FFFD) for faster
+     * validity checking at runtime.
+     */
+    private int[] bmpBlockBits;
+
+    /**
+     * Inversion list indexes for restricted binary searches in findCodePoint(), from findCodePoint(U+0800, U+1000,
+     * U+2000, .., U+F000, U+10000). U+0800 is the first 3-byte-UTF-8 code point. Code points below U+0800 are
+     * always looked up in the bit tables. The last pair of indexes is for finding supplementary code points.
+     */
+    private int[] list4kStarts;
+
+    /**
+     * The inversion list of the parent set, for the slower contains() implementation for mixed BMP blocks and for
+     * supplementary code points. The list is terminated with list[listLength-1]=0x110000.
+     */
+    private final int[] list;
+    private final int listLength; // length used; list may be longer to minimize reallocs
+
+    public BMPSet(final int[] parentList, int parentListLength) {
+        list = parentList;
+        listLength = parentListLength;
+        latin1Contains = new boolean[0x100];
+        table7FF = new int[64];
+        bmpBlockBits = new int[64];
+        list4kStarts = new int[18];
+
+        /*
+         * Set the list indexes for binary searches for U+0800, U+1000, U+2000, .., U+F000, U+10000. U+0800 is the
+         * first 3-byte-UTF-8 code point. Lower code points are looked up in the bit tables. The last pair of
+         * indexes is for finding supplementary code points.
+         */
+        list4kStarts[0] = findCodePoint(0x800, 0, listLength - 1);
+        int i;
+        for (i = 1; i <= 0x10; ++i) {
+            list4kStarts[i] = findCodePoint(i << 12, list4kStarts[i - 1], listLength - 1);
+        }
+        list4kStarts[0x11] = listLength - 1;
+
+        initBits();
+    }
+
+    public boolean contains(int c) {
+        if (c <= 0xff) {
+            return (latin1Contains[c]);
+        } else if (c <= 0x7ff) {
+            return ((table7FF[c & 0x3f] & (1 << (c >> 6))) != 0);
+        } else if (c < 0xd800 || (c >= 0xe000 && c <= 0xffff)) {
+            int lead = c >> 12;
+            int twoBits = (bmpBlockBits[(c >> 6) & 0x3f] >> lead) & 0x10001;
+            if (twoBits <= 1) {
+                // All 64 code points with the same bits 15..6
+                // are either in the set or not.
+                return (0 != twoBits);
+            } else {
+                // Look up the code point in its 4k block of code points.
+                return containsSlow(c, list4kStarts[lead], list4kStarts[lead + 1]);
+            }
+        } else if (c <= 0x10ffff) {
+            // surrogate or supplementary code point
+            return containsSlow(c, list4kStarts[0xd], list4kStarts[0x11]);
+        } else {
+            // Out-of-range code points get false, consistent with long-standing
+            // behavior of UnicodeSet.contains(c).
+            return false;
+        }
+    }
+
+    /**
+     * Span the initial substring for which each character c has spanCondition==contains(c). It must be
+     * spanCondition==0 or 1.
+     *
+     * @param start The start index
+     * @param outCount If not null: Receives the number of code points in the span.
+     * @return the limit (exclusive end) of the span
+     *
+     * NOTE: to reduce the overhead of function call to contains(c), it is manually inlined here. Check for
+     * sufficient length for trail unit for each surrogate pair. Handle single surrogates as surrogate code points
+     * as usual in ICU.
+     */
+    public final int span(CharSequence s, int start, SpanCondition spanCondition,
+            OutputInt outCount) {
+        char c, c2;
+        int i = start;
+        int limit = s.length();
+        int numSupplementary = 0;
+        if (SpanCondition.NOT_CONTAINED != spanCondition) {
+            // span
+            while (i < limit) {
+                c = s.charAt(i);
+                if (c <= 0xff) {
+                    if (!latin1Contains[c]) {
+                        break;
+                    }
+                } else if (c <= 0x7ff) {
+                    if ((table7FF[c & 0x3f] & (1 << (c >> 6))) == 0) {
+                        break;
+                    }
+                } else if (c < 0xd800 ||
+                           c >= 0xdc00 || (i + 1) == limit || (c2 = s.charAt(i + 1)) < 0xdc00 || c2 >= 0xe000) {
+                    int lead = c >> 12;
+                    int twoBits = (bmpBlockBits[(c >> 6) & 0x3f] >> lead) & 0x10001;
+                    if (twoBits <= 1) {
+                        // All 64 code points with the same bits 15..6
+                        // are either in the set or not.
+                        if (twoBits == 0) {
+                            break;
+                        }
+                    } else {
+                        // Look up the code point in its 4k block of code points.
+                        if (!containsSlow(c, list4kStarts[lead], list4kStarts[lead + 1])) {
+                            break;
+                        }
+                    }
+                } else {
+                    // surrogate pair
+                    int supplementary = UCharacterProperty.getRawSupplementary(c, c2);
+                    if (!containsSlow(supplementary, list4kStarts[0x10], list4kStarts[0x11])) {
+                        break;
+                    }
+                    ++numSupplementary;
+                    ++i;
+                }
+                ++i;
+            }
+        } else {
+            // span not
+            while (i < limit) {
+                c = s.charAt(i);
+                if (c <= 0xff) {
+                    if (latin1Contains[c]) {
+                        break;
+                    }
+                } else if (c <= 0x7ff) {
+                    if ((table7FF[c & 0x3f] & (1 << (c >> 6))) != 0) {
+                        break;
+                    }
+                } else if (c < 0xd800 ||
+                           c >= 0xdc00 || (i + 1) == limit || (c2 = s.charAt(i + 1)) < 0xdc00 || c2 >= 0xe000) {
+                    int lead = c >> 12;
+                    int twoBits = (bmpBlockBits[(c >> 6) & 0x3f] >> lead) & 0x10001;
+                    if (twoBits <= 1) {
+                        // All 64 code points with the same bits 15..6
+                        // are either in the set or not.
+                        if (twoBits != 0) {
+                            break;
+                        }
+                    } else {
+                        // Look up the code point in its 4k block of code points.
+                        if (containsSlow(c, list4kStarts[lead], list4kStarts[lead + 1])) {
+                            break;
+                        }
+                    }
+                } else {
+                    // surrogate pair
+                    int supplementary = UCharacterProperty.getRawSupplementary(c, c2);
+                    if (containsSlow(supplementary, list4kStarts[0x10], list4kStarts[0x11])) {
+                        break;
+                    }
+                    ++numSupplementary;
+                    ++i;
+                }
+                ++i;
+            }
+        }
+        if (outCount != null) {
+            int spanLength = i - start;
+            outCount.value = spanLength - numSupplementary;  // number of code points
+        }
+        return i;
+    }
+
+    /**
+     * Symmetrical with span().
+     * Span the trailing substring for which each character c has spanCondition==contains(c). It must be s.length >=
+     * limit and spanCondition==0 or 1.
+     *
+     * @return The string index which starts the span (i.e. inclusive).
+     */
+    public final int spanBack(CharSequence s, int limit, SpanCondition spanCondition) {
+        char c, c2;
+
+        if (SpanCondition.NOT_CONTAINED != spanCondition) {
+            // span
+            for (;;) {
+                c = s.charAt(--limit);
+                if (c <= 0xff) {
+                    if (!latin1Contains[c]) {
+                        break;
+                    }
+                } else if (c <= 0x7ff) {
+                    if ((table7FF[c & 0x3f] & (1 << (c >> 6))) == 0) {
+                        break;
+                    }
+                } else if (c < 0xd800 ||
+                           c < 0xdc00 || 0 == limit || (c2 = s.charAt(limit - 1)) < 0xd800 || c2 >= 0xdc00) {
+                    int lead = c >> 12;
+                    int twoBits = (bmpBlockBits[(c >> 6) & 0x3f] >> lead) & 0x10001;
+                    if (twoBits <= 1) {
+                        // All 64 code points with the same bits 15..6
+                        // are either in the set or not.
+                        if (twoBits == 0) {
+                            break;
+                        }
+                    } else {
+                        // Look up the code point in its 4k block of code points.
+                        if (!containsSlow(c, list4kStarts[lead], list4kStarts[lead + 1])) {
+                            break;
+                        }
+                    }
+                } else {
+                    // surrogate pair
+                    int supplementary = UCharacterProperty.getRawSupplementary(c2, c);
+                    if (!containsSlow(supplementary, list4kStarts[0x10], list4kStarts[0x11])) {
+                        break;
+                    }
+                    --limit;
+                }
+                if (0 == limit) {
+                    return 0;
+                }
+            }
+        } else {
+            // span not
+            for (;;) {
+                c = s.charAt(--limit);
+                if (c <= 0xff) {
+                    if (latin1Contains[c]) {
+                        break;
+                    }
+                } else if (c <= 0x7ff) {
+                    if ((table7FF[c & 0x3f] & (1 << (c >> 6))) != 0) {
+                        break;
+                    }
+                } else if (c < 0xd800 ||
+                           c < 0xdc00 || 0 == limit || (c2 = s.charAt(limit - 1)) < 0xd800 || c2 >= 0xdc00) {
+                    int lead = c >> 12;
+                    int twoBits = (bmpBlockBits[(c >> 6) & 0x3f] >> lead) & 0x10001;
+                    if (twoBits <= 1) {
+                        // All 64 code points with the same bits 15..6
+                        // are either in the set or not.
+                        if (twoBits != 0) {
+                            break;
+                        }
+                    } else {
+                        // Look up the code point in its 4k block of code points.
+                        if (containsSlow(c, list4kStarts[lead], list4kStarts[lead + 1])) {
+                            break;
+                        }
+                    }
+                } else {
+                    // surrogate pair
+                    int supplementary = UCharacterProperty.getRawSupplementary(c2, c);
+                    if (containsSlow(supplementary, list4kStarts[0x10], list4kStarts[0x11])) {
+                        break;
+                    }
+                    --limit;
+                }
+                if (0 == limit) {
+                    return 0;
+                }
+            }
+        }
+        return limit + 1;
+    }
+
+    /**
+     * Set bits in a bit rectangle in "vertical" bit organization. start<limit<=0x800
+     */
+    private static void set32x64Bits(int[] table, int start, int limit) {
+        assert (64 == table.length);
+        int lead = start >> 6;  // Named for UTF-8 2-byte lead byte with upper 5 bits.
+        int trail = start & 0x3f;  // Named for UTF-8 2-byte trail byte with lower 6 bits.
+
+        // Set one bit indicating an all-one block.
+        int bits = 1 << lead;
+        if ((start + 1) == limit) { // Single-character shortcut.
+            table[trail] |= bits;
+            return;
+        }
+
+        int limitLead = limit >> 6;
+        int limitTrail = limit & 0x3f;
+
+        if (lead == limitLead) {
+            // Partial vertical bit column.
+            while (trail < limitTrail) {
+                table[trail++] |= bits;
+            }
+        } else {
+            // Partial vertical bit column,
+            // followed by a bit rectangle,
+            // followed by another partial vertical bit column.
+            if (trail > 0) {
+                do {
+                    table[trail++] |= bits;
+                } while (trail < 64);
+                ++lead;
+            }
+            if (lead < limitLead) {
+                bits = ~((1 << lead) - 1);
+                if (limitLead < 0x20) {
+                    bits &= (1 << limitLead) - 1;
+                }
+                for (trail = 0; trail < 64; ++trail) {
+                    table[trail] |= bits;
+                }
+            }
+            // limit<=0x800. If limit==0x800 then limitLead=32 and limitTrail=0.
+            // In that case, bits=1<<limitLead == 1<<0 == 1
+            // (because Java << uses only the lower 5 bits of the shift operand)
+            // but the bits value is not used because trail<limitTrail is already false.
+            bits = 1 << limitLead;
+            for (trail = 0; trail < limitTrail; ++trail) {
+                table[trail] |= bits;
+            }
+        }
+    }
+
+    private void initBits() {
+        int start, limit;
+        int listIndex = 0;
+
+        // Set latin1Contains[].
+        do {
+            start = list[listIndex++];
+            if (listIndex < listLength) {
+                limit = list[listIndex++];
+            } else {
+                limit = 0x110000;
+            }
+            if (start >= 0x100) {
+                break;
+            }
+            do {
+                latin1Contains[start++] = true;
+            } while (start < limit && start < 0x100);
+        } while (limit <= 0x100);
+
+        // Set table7FF[].
+        while (start < 0x800) {
+            set32x64Bits(table7FF, start, limit <= 0x800 ? limit : 0x800);
+            if (limit > 0x800) {
+                start = 0x800;
+                break;
+            }
+
+            start = list[listIndex++];
+            if (listIndex < listLength) {
+                limit = list[listIndex++];
+            } else {
+                limit = 0x110000;
+            }
+        }
+
+        // Set bmpBlockBits[].
+        int minStart = 0x800;
+        while (start < 0x10000) {
+            if (limit > 0x10000) {
+                limit = 0x10000;
+            }
+
+            if (start < minStart) {
+                start = minStart;
+            }
+            if (start < limit) { // Else: Another range entirely in a known mixed-value block.
+                if (0 != (start & 0x3f)) {
+                    // Mixed-value block of 64 code points.
+                    start >>= 6;
+                    bmpBlockBits[start & 0x3f] |= 0x10001 << (start >> 6);
+                    start = (start + 1) << 6; // Round up to the next block boundary.
+                    minStart = start; // Ignore further ranges in this block.
+                }
+                if (start < limit) {
+                    if (start < (limit & ~0x3f)) {
+                        // Multiple all-ones blocks of 64 code points each.
+                        set32x64Bits(bmpBlockBits, start >> 6, limit >> 6);
+                    }
+
+                    if (0 != (limit & 0x3f)) {
+                        // Mixed-value block of 64 code points.
+                        limit >>= 6;
+                        bmpBlockBits[limit & 0x3f] |= 0x10001 << (limit >> 6);
+                      limit = (limit + 1) << 6; // Round up to the next block boundary.
+                        minStart = limit; // Ignore further ranges in this block.
+                    }
+                }
+            }
+
+            if (limit == 0x10000) {
+                break;
+          }
+
+            start = list[listIndex++];
+            if (listIndex < listLength) {
+                limit = list[listIndex++];
+            } else {
+                limit = 0x110000;
+            }
+        }
+    }
+
+    /**
+     * Same as UnicodeSet.findCodePoint(int c) except that the binary search is restricted for finding code
+     * points in a certain range.
+     *
+     * For restricting the search for finding in the range start..end, pass in lo=findCodePoint(start) and
+     * hi=findCodePoint(end) with 0<=lo<=hi<len. findCodePoint(c) defaults to lo=0 and hi=len-1.
+     *
+     * @param c
+     *            a character in a subrange of MIN_VALUE..MAX_VALUE
+     * @param lo
+     *            The lowest index to be returned.
+     * @param hi
+     *            The highest index to be returned.
+     * @return the smallest integer i in the range lo..hi, inclusive, such that c < list[i]
+     */
+    private int findCodePoint(int c, int lo, int hi) {
+        /* Examples:
+                                           findCodePoint(c)
+           set              list[]         c=0 1 3 4 7 8
+           ===              ==============   ===========
+           []               [110000]         0 0 0 0 0 0
+           [\u0000-\u0003]  [0, 4, 110000]   1 1 1 2 2 2
+           [\u0004-\u0007]  [4, 8, 110000]   0 0 0 1 1 2
+           [:Any:]          [0, 110000]      1 1 1 1 1 1
+         */
+
+        // Return the smallest i such that c < list[i]. Assume
+        // list[len - 1] == HIGH and that c is legal (0..HIGH-1).
+        if (c < list[lo])
+            return lo;
+        // High runner test. c is often after the last range, so an
+        // initial check for this condition pays off.
+        if (lo >= hi || c >= list[hi - 1])
+            return hi;
+        // invariant: c >= list[lo]
+        // invariant: c < list[hi]
+        for (;;) {
+            int i = (lo + hi) >>> 1;
+            if (i == lo) {
+                break; // Found!
+            } else if (c < list[i]) {
+                hi = i;
+            } else {
+                lo = i;
+            }
+        }
+        return hi;
+    }
+
+    private final boolean containsSlow(int c, int lo, int hi) {
+        return (0 != (findCodePoint(c, lo, hi) & 1));
+    }
+}
+
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/CharTrie.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/CharTrie.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2009, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -22,22 +22,18 @@
  * or visit www.oracle.com if you need additional information or have any
  * questions.
  */
+
 /*
- *******************************************************************************
- * (C) Copyright IBM Corp. and others, 1996-2009 - All Rights Reserved         *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
- *******************************************************************************
+ ******************************************************************************
+ * Copyright (C) 1996-2014, International Business Machines Corporation and
+ * others. All Rights Reserved.
+ ******************************************************************************
  */
 
 package sun.text.normalizer;
 
+import java.io.DataInputStream;
 import java.io.InputStream;
-import java.io.DataInputStream;
 import java.io.IOException;
 
 /**
@@ -73,120 +69,17 @@
             throw new IllegalArgumentException(
                                "Data given does not belong to a char trie.");
         }
-        m_friendAgent_ = new FriendAgent();
-    }
-
-    /**
-     * Make a dummy CharTrie.
-     * A dummy trie is an empty runtime trie, used when a real data trie cannot
-     * be loaded.
-     *
-     * The trie always returns the initialValue,
-     * or the leadUnitValue for lead surrogate code points.
-     * The Latin-1 part is always set up to be linear.
-     *
-     * @param initialValue the initial value that is set for all code points
-     * @param leadUnitValue the value for lead surrogate code _units_ that do not
-     *                      have associated supplementary data
-     * @param dataManipulate object which provides methods to parse the char data
-     */
-    public CharTrie(int initialValue, int leadUnitValue, DataManipulate dataManipulate) {
-        super(new char[BMP_INDEX_LENGTH+SURROGATE_BLOCK_COUNT], HEADER_OPTIONS_LATIN1_IS_LINEAR_MASK_, dataManipulate);
-
-        int dataLength, latin1Length, i, limit;
-        char block;
-
-        /* calculate the actual size of the dummy trie data */
-
-        /* max(Latin-1, block 0) */
-        dataLength=latin1Length= INDEX_STAGE_1_SHIFT_<=8 ? 256 : DATA_BLOCK_LENGTH;
-        if(leadUnitValue!=initialValue) {
-            dataLength+=DATA_BLOCK_LENGTH;
-        }
-        m_data_=new char[dataLength];
-        m_dataLength_=dataLength;
-
-        m_initialValue_=(char)initialValue;
-
-        /* fill the index and data arrays */
-
-        /* indexes are preset to 0 (block 0) */
-
-        /* Latin-1 data */
-        for(i=0; i<latin1Length; ++i) {
-            m_data_[i]=(char)initialValue;
-        }
-
-        if(leadUnitValue!=initialValue) {
-            /* indexes for lead surrogate code units to the block after Latin-1 */
-            block=(char)(latin1Length>>INDEX_STAGE_2_SHIFT_);
-            i=0xd800>>INDEX_STAGE_1_SHIFT_;
-            limit=0xdc00>>INDEX_STAGE_1_SHIFT_;
-            for(; i<limit; ++i) {
-                m_index_[i]=block;
-            }
-
-            /* data for lead surrogate code units */
-            limit=latin1Length+DATA_BLOCK_LENGTH;
-            for(i=latin1Length; i<limit; ++i) {
-                m_data_[i]=(char)leadUnitValue;
-            }
-        }
-
-        m_friendAgent_ = new FriendAgent();
-    }
-
-    /**
-     * Java friend implementation
-     */
-    public class FriendAgent
-    {
-        /**
-         * Gives out the index array of the trie
-         * @return index array of trie
-         */
-        public char[] getPrivateIndex()
-        {
-            return m_index_;
-        }
-        /**
-         * Gives out the data array of the trie
-         * @return data array of trie
-         */
-        public char[] getPrivateData()
-        {
-            return m_data_;
-        }
-        /**
-         * Gives out the data offset in the trie
-         * @return data offset in the trie
-         */
-        public int getPrivateInitialValue()
-        {
-            return m_initialValue_;
-        }
     }
 
     // public methods --------------------------------------------------
 
     /**
-     * Java friend implementation
-     * To store the index and data array into the argument.
-     * @param friend java friend UCharacterProperty object to store the array
+     * Gets the value associated with the codepoint.
+     * If no value is associated with the codepoint, a default value will be
+     * returned.
+     * @param ch codepoint
+     * @return offset to data
      */
-    public void putIndexData(UCharacterProperty friend)
-    {
-        friend.setIndexData(m_friendAgent_);
-    }
-
-    /**
-    * Gets the value associated with the codepoint.
-    * If no value is associated with the codepoint, a default value will be
-    * returned.
-    * @param ch codepoint
-    * @return offset to data
-    * @draft 2.1
-    */
     public final char getCodePointValue(int ch)
     {
         int offset;
@@ -215,52 +108,12 @@
     * This method does not guarantee correct results for trail surrogates.
     * @param ch lead surrogate character
     * @return data value
-    * @draft 2.1
     */
     public final char getLeadValue(char ch)
     {
        return m_data_[getLeadOffset(ch)];
     }
 
-    /**
-    * Get the value associated with a pair of surrogates.
-    * @param lead a lead surrogate
-    * @param trail a trail surrogate
-    * @draft 2.1
-    */
-    public final char getSurrogateValue(char lead, char trail)
-    {
-        int offset = getSurrogateOffset(lead, trail);
-        if (offset > 0) {
-            return m_data_[offset];
-        }
-        return m_initialValue_;
-    }
-
-    /**
-    * <p>Get a value from a folding offset (from the value of a lead surrogate)
-    * and a trail surrogate.</p>
-    * <p>If the
-    * @param leadvalue value associated with the lead surrogate which contains
-    *        the folding offset
-    * @param trail surrogate
-    * @return trie data value associated with the trail character
-    * @draft 2.1
-    */
-    public final char getTrailValue(int leadvalue, char trail)
-    {
-        if (m_dataManipulate_ == null) {
-            throw new NullPointerException(
-                             "The field DataManipulate in this Trie is null");
-        }
-        int offset = m_dataManipulate_.getFoldingOffset(leadvalue);
-        if (offset > 0) {
-            return m_data_[getRawOffset(offset,
-                                        (char)(trail & SURROGATE_MASK_))];
-        }
-        return m_initialValue_;
-    }
-
     // protected methods -----------------------------------------------
 
     /**
@@ -309,41 +162,14 @@
         return -1;
     }
 
-    /**
-    * Gets the value at the argument index.
-    * For use internally in TrieIterator.
-    * @param index value at index will be retrieved
-    * @return 32 bit value
-    * @see com.ibm.icu.impl.TrieIterator
-    * @draft 2.1
-    */
-    protected final int getValue(int index)
-    {
-        return m_data_[index];
-    }
-
-    /**
-    * Gets the default initial value
-    * @return 32 bit value
-    * @draft 2.1
-    */
-    protected final int getInitialValue()
-    {
-        return m_initialValue_;
-    }
-
     // private data members --------------------------------------------
 
     /**
-    * Default value
-    */
+     * Default value
+     */
     private char m_initialValue_;
     /**
-    * Array of char data
-    */
+     * Array of char data
+     */
     private char m_data_[];
-    /**
-     * Agent for friends
-     */
-    private FriendAgent m_friendAgent_;
 }
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/CharacterIteratorWrapper.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/CharacterIteratorWrapper.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -45,7 +45,7 @@
  * @author ram
  */
 
-public class CharacterIteratorWrapper extends UCharacterIterator {
+class CharacterIteratorWrapper extends UCharacterIterator {
 
     private CharacterIterator iterator;
 
@@ -111,7 +111,6 @@
         iterator.setIndex(index);
     }
 
-    //// for StringPrep
     /**
      * @see UCharacterIterator#getText(char[])
      */
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/FilteredNormalizer2.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,266 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/*
+*******************************************************************************
+*   Copyright (C) 2009-2014, International Business Machines
+*   Corporation and others.  All Rights Reserved.
+*******************************************************************************
+*/
+package sun.text.normalizer;
+
+import java.io.IOException;
+
+/**
+ * Normalization filtered by a UnicodeSet.
+ * Normalizes portions of the text contained in the filter set and leaves
+ * portions not contained in the filter set unchanged.
+ * Filtering is done via UnicodeSet.span(..., UnicodeSet.SpanCondition.SIMPLE).
+ * Not-in-the-filter text is treated as "is normalized" and "quick check yes".
+ * This class implements all of (and only) the Normalizer2 API.
+ * An instance of this class is unmodifiable/immutable.
+ * @stable ICU 4.4
+ * @author Markus W. Scherer
+ */
+class FilteredNormalizer2 extends Normalizer2 {
+
+    /**
+     * Constructs a filtered normalizer wrapping any Normalizer2 instance
+     * and a filter set.
+     * Both are aliased and must not be modified or deleted while this object
+     * is used.
+     * The filter set should be frozen; otherwise the performance will suffer greatly.
+     * @param n2 wrapped Normalizer2 instance
+     * @param filterSet UnicodeSet which determines the characters to be normalized
+     * @stable ICU 4.4
+     */
+    public FilteredNormalizer2(Normalizer2 n2, UnicodeSet filterSet) {
+        norm2=n2;
+        set=filterSet;
+    }
+
+    /**
+     * {@inheritDoc}
+     * @stable ICU 4.4
+     */
+    @Override
+    public StringBuilder normalize(CharSequence src, StringBuilder dest) {
+        if(dest==src) {
+            throw new IllegalArgumentException();
+        }
+        dest.setLength(0);
+        normalize(src, dest, UnicodeSet.SpanCondition.SIMPLE);
+        return dest;
+    }
+
+    /**
+     * {@inheritDoc}
+     * @stable ICU 4.6
+     */
+    @Override
+    public Appendable normalize(CharSequence src, Appendable dest) {
+        if(dest==src) {
+            throw new IllegalArgumentException();
+        }
+        return normalize(src, dest, UnicodeSet.SpanCondition.SIMPLE);
+    }
+
+    /**
+     * {@inheritDoc}
+     * @stable ICU 4.4
+     */
+    @Override
+    public StringBuilder normalizeSecondAndAppend(
+            StringBuilder first, CharSequence second) {
+        return normalizeSecondAndAppend(first, second, true);
+    }
+
+    /**
+     * {@inheritDoc}
+     * @stable ICU 4.4
+     */
+    @Override
+    public StringBuilder append(StringBuilder first, CharSequence second) {
+        return normalizeSecondAndAppend(first, second, false);
+    }
+
+    /**
+     * {@inheritDoc}
+     * @stable ICU 4.6
+     */
+    @Override
+    public String getDecomposition(int c) {
+        return set.contains(c) ? norm2.getDecomposition(c) : null;
+    }
+
+    /**
+     * {@inheritDoc}
+     * @stable ICU 49
+     */
+    @Override
+    public int getCombiningClass(int c) {
+        return set.contains(c) ? norm2.getCombiningClass(c) : 0;
+    }
+
+    /**
+     * {@inheritDoc}
+     * @stable ICU 4.4
+     */
+    @Override
+    public boolean isNormalized(CharSequence s) {
+        UnicodeSet.SpanCondition spanCondition=UnicodeSet.SpanCondition.SIMPLE;
+        for(int prevSpanLimit=0; prevSpanLimit<s.length();) {
+            int spanLimit=set.span(s, prevSpanLimit, spanCondition);
+            if(spanCondition==UnicodeSet.SpanCondition.NOT_CONTAINED) {
+                spanCondition=UnicodeSet.SpanCondition.SIMPLE;
+            } else {
+                if(!norm2.isNormalized(s.subSequence(prevSpanLimit, spanLimit))) {
+                    return false;
+                }
+                spanCondition=UnicodeSet.SpanCondition.NOT_CONTAINED;
+            }
+            prevSpanLimit=spanLimit;
+        }
+        return true;
+    }
+
+    /**
+     * {@inheritDoc}
+     * @stable ICU 4.4
+     */
+    @Override
+    public int spanQuickCheckYes(CharSequence s) {
+        UnicodeSet.SpanCondition spanCondition=UnicodeSet.SpanCondition.SIMPLE;
+        for(int prevSpanLimit=0; prevSpanLimit<s.length();) {
+            int spanLimit=set.span(s, prevSpanLimit, spanCondition);
+            if(spanCondition==UnicodeSet.SpanCondition.NOT_CONTAINED) {
+                spanCondition=UnicodeSet.SpanCondition.SIMPLE;
+            } else {
+                int yesLimit=
+                    prevSpanLimit+
+                    norm2.spanQuickCheckYes(s.subSequence(prevSpanLimit, spanLimit));
+                if(yesLimit<spanLimit) {
+                    return yesLimit;
+                }
+                spanCondition=UnicodeSet.SpanCondition.NOT_CONTAINED;
+            }
+            prevSpanLimit=spanLimit;
+        }
+        return s.length();
+    }
+
+    /**
+     * {@inheritDoc}
+     * @stable ICU 4.4
+     */
+    @Override
+    public boolean hasBoundaryBefore(int c) {
+        return !set.contains(c) || norm2.hasBoundaryBefore(c);
+    }
+
+    // Internal: No argument checking, and appends to dest.
+    // Pass as input spanCondition the one that is likely to yield a non-zero
+    // span length at the start of src.
+    // For set=[:age=3.2:], since almost all common characters were in Unicode 3.2,
+    // UnicodeSet.SpanCondition.SIMPLE should be passed in for the start of src
+    // and UnicodeSet.SpanCondition.NOT_CONTAINED should be passed in if we continue after
+    // an in-filter prefix.
+    private Appendable normalize(CharSequence src, Appendable dest,
+                                 UnicodeSet.SpanCondition spanCondition) {
+        // Don't throw away destination buffer between iterations.
+        StringBuilder tempDest=new StringBuilder();
+        try {
+            for(int prevSpanLimit=0; prevSpanLimit<src.length();) {
+                int spanLimit=set.span(src, prevSpanLimit, spanCondition);
+                int spanLength=spanLimit-prevSpanLimit;
+                if(spanCondition==UnicodeSet.SpanCondition.NOT_CONTAINED) {
+                    if(spanLength!=0) {
+                        dest.append(src, prevSpanLimit, spanLimit);
+                    }
+                    spanCondition=UnicodeSet.SpanCondition.SIMPLE;
+                } else {
+                    if(spanLength!=0) {
+                        // Not norm2.normalizeSecondAndAppend() because we do not want
+                        // to modify the non-filter part of dest.
+                        dest.append(norm2.normalize(src.subSequence(prevSpanLimit, spanLimit), tempDest));
+                    }
+                    spanCondition=UnicodeSet.SpanCondition.NOT_CONTAINED;
+                }
+                prevSpanLimit=spanLimit;
+            }
+        } catch(IOException e) {
+            throw new InternalError(e.toString(), e);
+        }
+        return dest;
+    }
+
+    private StringBuilder normalizeSecondAndAppend(StringBuilder first, CharSequence second,
+                                                   boolean doNormalize) {
+        if(first==second) {
+            throw new IllegalArgumentException();
+        }
+        if(first.length()==0) {
+            if(doNormalize) {
+                return normalize(second, first);
+            } else {
+                return first.append(second);
+            }
+        }
+        // merge the in-filter suffix of the first string with the in-filter prefix of the second
+        int prefixLimit=set.span(second, 0, UnicodeSet.SpanCondition.SIMPLE);
+        if(prefixLimit!=0) {
+            CharSequence prefix=second.subSequence(0, prefixLimit);
+            int suffixStart=set.spanBack(first, 0x7fffffff, UnicodeSet.SpanCondition.SIMPLE);
+            if(suffixStart==0) {
+                if(doNormalize) {
+                    norm2.normalizeSecondAndAppend(first, prefix);
+                } else {
+                    norm2.append(first, prefix);
+                }
+            } else {
+                StringBuilder middle=new StringBuilder(
+                        first.subSequence(suffixStart, first.length()));
+                if(doNormalize) {
+                    norm2.normalizeSecondAndAppend(middle, prefix);
+                } else {
+                    norm2.append(middle, prefix);
+                }
+                first.delete(suffixStart, 0x7fffffff).append(middle);
+            }
+        }
+        if(prefixLimit<second.length()) {
+            CharSequence rest=second.subSequence(prefixLimit, second.length());
+            if(doNormalize) {
+                normalize(rest, first, UnicodeSet.SpanCondition.NOT_CONTAINED);
+            } else {
+                first.append(rest);
+            }
+        }
+        return first;
+    }
+
+    private Normalizer2 norm2;
+    private UnicodeSet set;
+};
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/ICUBinary.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/ICUBinary.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2005, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 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
@@ -25,25 +25,38 @@
 
 /*
  *******************************************************************************
- * (C) Copyright IBM Corp. 1996-2005 - All Rights Reserved                     *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
+ * Copyright (C) 1996-2014, International Business Machines Corporation and
+ * others. All Rights Reserved.
  *******************************************************************************
  */
 
 package sun.text.normalizer;
 
-import java.io.InputStream;
+import java.io.BufferedInputStream;
 import java.io.DataInputStream;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.InputStream;
 import java.io.IOException;
+import java.io.UncheckedIOException;
+import java.net.URL;
+import java.nio.ByteBuffer;
+import java.nio.ByteOrder;
+import java.nio.channels.FileChannel;
+import java.nio.file.FileSystems;
 import java.util.Arrays;
+import java.security.AccessController;
+import java.security.PrivilegedAction;
 
-public final class ICUBinary
-{
+public final class ICUBinary {
+
+    private static final class IsAcceptable implements Authenticate {
+        // @Override when we switch to Java 6
+        public boolean isDataVersionAcceptable(byte version[]) {
+            return version[0] == 1;
+        }
+    }
+
     // public inner interface ------------------------------------------------
 
     /**
@@ -63,53 +76,44 @@
     // public methods --------------------------------------------------------
 
     /**
-    * <p>ICU data header reader method.
-    * Takes a ICU generated big-endian input stream, parse the ICU standard
-    * file header and authenticates them.
-    * <p>Header format:
-    * <ul>
-    *     <li> Header size (char)
-    *     <li> Magic number 1 (byte)
-    *     <li> Magic number 2 (byte)
-    *     <li> Rest of the header size (char)
-    *     <li> Reserved word (char)
-    *     <li> Big endian indicator (byte)
-    *     <li> Character set family indicator (byte)
-    *     <li> Size of a char (byte) for c++ and c use
-    *     <li> Reserved byte (byte)
-    *     <li> Data format identifier (4 bytes), each ICU data has its own
-    *          identifier to distinguish them. [0] major [1] minor
-    *                                          [2] milli [3] micro
-    *     <li> Data version (4 bytes), the change version of the ICU data
-    *                             [0] major [1] minor [2] milli [3] micro
-    *     <li> Unicode version (4 bytes) this ICU is based on.
-    * </ul>
-    *
-    * <p>
-    * Example of use:<br>
-    * <pre>
-    * try {
-    *    FileInputStream input = new FileInputStream(filename);
-    *    If (Utility.readICUDataHeader(input, dataformat, dataversion,
-    *                                  unicode) {
-    *        System.out.println("Verified file header, this is a ICU data file");
-    *    }
-    * } catch (IOException e) {
-    *    System.out.println("This is not a ICU data file");
-    * }
-    * </pre>
-    *
-    * @param inputStream input stream that contains the ICU data header
-    * @param dataFormatIDExpected Data format expected. An array of 4 bytes
-    *                     information about the data format.
-    *                     E.g. data format ID 1.2.3.4. will became an array of
-    *                     {1, 2, 3, 4}
-    * @param authenticate user defined extra data authentication. This value
-    *                     can be null, if no extra authentication is needed.
-    * @exception IOException thrown if there is a read error or
-    *            when header authentication fails.
-    * @draft 2.1
-    */
+     * Loads an ICU binary data file and returns it as a ByteBuffer.
+     * The buffer contents is normally read-only, but its position etc. can be modified.
+     *
+     * @param itemPath Relative ICU data item path, for example "root.res" or "coll/ucadata.icu".
+     * @return The data as a read-only ByteBuffer.
+     */
+    public static ByteBuffer getRequiredData(String itemPath) {
+        final Class<ICUBinary> root = ICUBinary.class;
+
+        try (InputStream is = AccessController.doPrivileged(new PrivilegedAction<InputStream>() {
+                public InputStream run() {
+                    return root.getResourceAsStream(itemPath);
+                }
+            })) {
+
+            BufferedInputStream b=new BufferedInputStream(is, 4096 /* data buffer size */);
+            DataInputStream inputStream = new DataInputStream(b);
+            byte[] bb = new byte[120000];
+            int n = inputStream.read(bb);
+            ByteBuffer bytes = ByteBuffer.wrap(bb, 0, n);
+            return bytes;
+        }
+        catch (IOException e) {
+            throw new UncheckedIOException(e);
+        }
+    }
+
+    /**
+     * Same as readHeader(), but returns a VersionInfo rather than a compact int.
+     */
+    public static VersionInfo readHeaderAndDataVersion(ByteBuffer bytes,
+                                                             int dataFormat,
+                                                             Authenticate authenticate)
+                                                                throws IOException {
+        return getVersionInfoFromCompactInt(readHeader(bytes, dataFormat, authenticate));
+    }
+
+    private static final byte BIG_ENDIAN_ = 1;
     public static final byte[] readHeader(InputStream inputStream,
                                         byte dataFormatIDExpected[],
                                         Authenticate authenticate)
@@ -164,6 +168,80 @@
         return unicodeVersion;
     }
 
+    /**
+     * Reads an ICU data header, checks the data format, and returns the data version.
+     *
+     * <p>Assumes that the ByteBuffer position is 0 on input.
+     * The buffer byte order is set according to the data.
+     * The buffer position is advanced past the header (including UDataInfo and comment).
+     *
+     * <p>See C++ ucmndata.h and unicode/udata.h.
+     *
+     * @return dataVersion
+     * @throws IOException if this is not a valid ICU data item of the expected dataFormat
+     */
+    public static int readHeader(ByteBuffer bytes, int dataFormat, Authenticate authenticate)
+            throws IOException {
+        assert bytes.position() == 0;
+        byte magic1 = bytes.get(2);
+        byte magic2 = bytes.get(3);
+        if (magic1 != MAGIC1 || magic2 != MAGIC2) {
+            throw new IOException(MAGIC_NUMBER_AUTHENTICATION_FAILED_);
+        }
+
+        byte isBigEndian = bytes.get(8);
+        byte charsetFamily = bytes.get(9);
+        byte sizeofUChar = bytes.get(10);
+        if (isBigEndian < 0 || 1 < isBigEndian ||
+                charsetFamily != CHAR_SET_ || sizeofUChar != CHAR_SIZE_) {
+            throw new IOException(HEADER_AUTHENTICATION_FAILED_);
+        }
+        bytes.order(isBigEndian != 0 ? ByteOrder.BIG_ENDIAN : ByteOrder.LITTLE_ENDIAN);
+
+        int headerSize = bytes.getChar(0);
+        int sizeofUDataInfo = bytes.getChar(4);
+        if (sizeofUDataInfo < 20 || headerSize < (sizeofUDataInfo + 4)) {
+            throw new IOException("Internal Error: Header size error");
+        }
+        // TODO: Change Authenticate to take int major, int minor, int milli, int micro
+        // to avoid array allocation.
+        byte[] formatVersion = new byte[] {
+            bytes.get(16), bytes.get(17), bytes.get(18), bytes.get(19)
+        };
+        if (bytes.get(12) != (byte)(dataFormat >> 24) ||
+                bytes.get(13) != (byte)(dataFormat >> 16) ||
+                bytes.get(14) != (byte)(dataFormat >> 8) ||
+                bytes.get(15) != (byte)dataFormat ||
+                (authenticate != null && !authenticate.isDataVersionAcceptable(formatVersion))) {
+            throw new IOException(HEADER_AUTHENTICATION_FAILED_ +
+                    String.format("; data format %02x%02x%02x%02x, format version %d.%d.%d.%d",
+                            bytes.get(12), bytes.get(13), bytes.get(14), bytes.get(15),
+                            formatVersion[0] & 0xff, formatVersion[1] & 0xff,
+                            formatVersion[2] & 0xff, formatVersion[3] & 0xff));
+        }
+
+        bytes.position(headerSize);
+        return  // dataVersion
+                ((int)bytes.get(20) << 24) |
+                ((bytes.get(21) & 0xff) << 16) |
+                ((bytes.get(22) & 0xff) << 8) |
+                (bytes.get(23) & 0xff);
+    }
+
+    public static void skipBytes(ByteBuffer bytes, int skipLength) {
+        if (skipLength > 0) {
+            bytes.position(bytes.position() + skipLength);
+        }
+    }
+
+    /**
+     * Returns a VersionInfo for the bytes in the compact version integer.
+     */
+    public static VersionInfo getVersionInfoFromCompactInt(int version) {
+        return VersionInfo.getInstance(
+                version >>> 24, (version >> 16) & 0xff, (version >> 8) & 0xff, version & 0xff);
+    }
+
     // private variables -------------------------------------------------
 
     /**
@@ -175,7 +253,6 @@
     /**
     * File format authentication values
     */
-    private static final byte BIG_ENDIAN_ = 1;
     private static final byte CHAR_SET_ = 0;
     private static final byte CHAR_SIZE_ = 2;
 
@@ -183,7 +260,7 @@
     * Error messages
     */
     private static final String MAGIC_NUMBER_AUTHENTICATION_FAILED_ =
-                       "ICU data file error: Not an ICU data file";
+                       "ICUBinary data file error: Magin number authentication failed";
     private static final String HEADER_AUTHENTICATION_FAILED_ =
-        "ICU data file error: Header authentication failed, please check if you have a valid ICU data file";
+        "ICUBinary data file error: Header authentication failed";
 }
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/ICUData.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,83 +0,0 @@
-/*
- * Copyright (c) 2005, 2011, 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.
- */
-
-/*
- *******************************************************************************
- * (C) Copyright IBM Corp. 1996-2005 - All Rights Reserved                     *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
- *******************************************************************************
- */
-
-package sun.text.normalizer;
-
-import java.io.InputStream;
-import java.net.URL;
-import java.security.AccessController;
-import java.security.PrivilegedAction;
-import java.util.MissingResourceException;
-
-/**
- * Provides access to ICU data files as InputStreams.  Implements security checking.
- */
-public final class ICUData {
-
-    private static InputStream getStream(final Class<ICUData> root, final String resourceName, boolean required) {
-        InputStream i = null;
-
-        if (System.getSecurityManager() != null) {
-            i = AccessController.doPrivileged(new PrivilegedAction<InputStream>() {
-                    public InputStream run() {
-                        return root.getResourceAsStream(resourceName);
-                    }
-                });
-        } else {
-            i = root.getResourceAsStream(resourceName);
-        }
-
-        if (i == null && required) {
-            throw new MissingResourceException("could not locate data", root.getPackage().getName(), resourceName);
-        }
-        return i;
-    }
-
-    /*
-     * Convenience override that calls getStream(ICUData.class, resourceName, false);
-     */
-    public static InputStream getStream(String resourceName) {
-        return getStream(ICUData.class, resourceName, false);
-    }
-
-    /*
-     * Convenience method that calls getStream(ICUData.class, resourceName, true).
-     */
-    public static InputStream getRequiredStream(String resourceName) {
-        return getStream(ICUData.class, resourceName, true);
-    }
-}
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/IntTrie.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,229 +0,0 @@
-/*
- * Copyright (c) 2003, 2005, 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.
- */
-
-/*
- *******************************************************************************
- * (C) Copyright IBM Corp. 1996-2005 - All Rights Reserved                     *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
- *******************************************************************************
- */
-
-package sun.text.normalizer;
-
-import java.io.InputStream;
-import java.io.DataInputStream;
-import java.io.IOException;
-import java.util.Arrays;
-
-/**
- * Trie implementation which stores data in int, 32 bits.
- * @author synwee
- * @see com.ibm.icu.impl.Trie
- * @since release 2.1, Jan 01 2002
- */
-public class IntTrie extends Trie
-{
-    // public constructors ---------------------------------------------
-
-    /**
-    * <p>Creates a new Trie with the settings for the trie data.</p>
-    * <p>Unserialize the 32-bit-aligned input stream and use the data for the
-    * trie.</p>
-    * @param inputStream file input stream to a ICU data file, containing
-    *                    the trie
-    * @param datamanipulate object which provides methods to parse the char
-    *                        data
-    * @throws IOException thrown when data reading fails
-    * @draft 2.1
-    */
-    public IntTrie(InputStream inputStream, DataManipulate datamanipulate)
-                                                    throws IOException
-    {
-        super(inputStream, datamanipulate);
-        if (!isIntTrie()) {
-            throw new IllegalArgumentException(
-                               "Data given does not belong to a int trie.");
-        }
-    }
-
-    // public methods --------------------------------------------------
-
-    /**
-    * Gets the value associated with the codepoint.
-    * If no value is associated with the codepoint, a default value will be
-    * returned.
-    * @param ch codepoint
-    * @return offset to data
-    * @draft 2.1
-    */
-    public final int getCodePointValue(int ch)
-    {
-        int offset = getCodePointOffset(ch);
-        return (offset >= 0) ? m_data_[offset] : m_initialValue_;
-    }
-
-    /**
-    * Gets the value to the data which this lead surrogate character points
-    * to.
-    * Returned data may contain folding offset information for the next
-    * trailing surrogate character.
-    * This method does not guarantee correct results for trail surrogates.
-    * @param ch lead surrogate character
-    * @return data value
-    * @draft 2.1
-    */
-    public final int getLeadValue(char ch)
-    {
-        return m_data_[getLeadOffset(ch)];
-    }
-
-    /**
-    * Get a value from a folding offset (from the value of a lead surrogate)
-    * and a trail surrogate.
-    * @param leadvalue the value of a lead surrogate that contains the
-    *        folding offset
-    * @param trail surrogate
-    * @return trie data value associated with the trail character
-    * @draft 2.1
-    */
-    public final int getTrailValue(int leadvalue, char trail)
-    {
-        if (m_dataManipulate_ == null) {
-            throw new NullPointerException(
-                             "The field DataManipulate in this Trie is null");
-        }
-        int offset = m_dataManipulate_.getFoldingOffset(leadvalue);
-        if (offset > 0) {
-            return m_data_[getRawOffset(offset,
-                                         (char)(trail & SURROGATE_MASK_))];
-        }
-        return m_initialValue_;
-    }
-
-    // protected methods -----------------------------------------------
-
-    /**
-    * <p>Parses the input stream and stores its trie content into a index and
-    * data array</p>
-    * @param inputStream data input stream containing trie data
-    * @exception IOException thrown when data reading fails
-    */
-    protected final void unserialize(InputStream inputStream)
-                                                    throws IOException
-    {
-        super.unserialize(inputStream);
-        // one used for initial value
-        m_data_               = new int[m_dataLength_];
-        DataInputStream input = new DataInputStream(inputStream);
-        for (int i = 0; i < m_dataLength_; i ++) {
-            m_data_[i] = input.readInt();
-        }
-        m_initialValue_ = m_data_[0];
-    }
-
-    /**
-    * Gets the offset to the data which the surrogate pair points to.
-    * @param lead lead surrogate
-    * @param trail trailing surrogate
-    * @return offset to data
-    * @draft 2.1
-    */
-    protected final int getSurrogateOffset(char lead, char trail)
-    {
-        if (m_dataManipulate_ == null) {
-            throw new NullPointerException(
-                             "The field DataManipulate in this Trie is null");
-        }
-        // get fold position for the next trail surrogate
-        int offset = m_dataManipulate_.getFoldingOffset(getLeadValue(lead));
-
-        // get the real data from the folded lead/trail units
-        if (offset > 0) {
-            return getRawOffset(offset, (char)(trail & SURROGATE_MASK_));
-        }
-
-        // return -1 if there is an error, in this case we return the default
-        // value: m_initialValue_
-        return -1;
-    }
-
-    /**
-    * Gets the value at the argument index.
-    * For use internally in TrieIterator
-    * @param index value at index will be retrieved
-    * @return 32 bit value
-    * @see com.ibm.icu.impl.TrieIterator
-    * @draft 2.1
-    */
-    protected final int getValue(int index)
-    {
-      return m_data_[index];
-    }
-
-    /**
-    * Gets the default initial value
-    * @return 32 bit value
-    * @draft 2.1
-    */
-    protected final int getInitialValue()
-    {
-        return m_initialValue_;
-    }
-
-    // package private methods -----------------------------------------
-
-    /**
-     * Internal constructor for builder use
-     * @param index the index array to be slotted into this trie
-     * @param data the data array to be slotted into this trie
-     * @param initialvalue the initial value for this trie
-     * @param options trie options to use
-     * @param datamanipulate folding implementation
-     */
-    IntTrie(char index[], int data[], int initialvalue, int options,
-            DataManipulate datamanipulate)
-    {
-        super(index, options, datamanipulate);
-        m_data_ = data;
-        m_dataLength_ = m_data_.length;
-        m_initialValue_ = initialvalue;
-    }
-
-    // private data members --------------------------------------------
-
-    /**
-    * Default value
-    */
-    private int m_initialValue_;
-    /**
-    * Array of char data
-    */
-    private int m_data_[];
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/Norm2AllModes.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,287 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/*
+ *******************************************************************************
+ *   Copyright (C) 2009-2014, International Business Machines
+ *   Corporation and others.  All Rights Reserved.
+ *******************************************************************************
+ */
+
+package sun.text.normalizer;
+
+import java.io.IOException;
+
+final class Norm2AllModes {
+    // Public API dispatch via Normalizer2 subclasses -------------------------- ***
+
+    // Normalizer2 implementation for the old UNORM_NONE.
+    public static final class NoopNormalizer2 extends Normalizer2 {
+        @Override
+        public StringBuilder normalize(CharSequence src, StringBuilder dest) {
+            if(dest!=src) {
+                dest.setLength(0);
+                return dest.append(src);
+            } else {
+                throw new IllegalArgumentException();
+            }
+        }
+
+        @Override
+        public Appendable normalize(CharSequence src, Appendable dest) {
+            if(dest!=src) {
+                try {
+                    return dest.append(src);
+                } catch(IOException e) {
+                    throw new InternalError(e.toString(), e);
+                }
+            } else {
+                throw new IllegalArgumentException();
+            }
+        }
+
+        @Override
+        public StringBuilder normalizeSecondAndAppend(StringBuilder first, CharSequence second) {
+            if(first!=second) {
+                return first.append(second);
+            } else {
+                throw new IllegalArgumentException();
+            }
+        }
+
+        @Override
+        public StringBuilder append(StringBuilder first, CharSequence second) {
+            if(first!=second) {
+                return first.append(second);
+            } else {
+                throw new IllegalArgumentException();
+            }
+        }
+
+        @Override
+        public String getDecomposition(int c) {
+            return null;
+        }
+
+        // No need to override the default getRawDecomposition().
+        @Override
+        public boolean isNormalized(CharSequence s) { return true; }
+
+        @Override
+        public int spanQuickCheckYes(CharSequence s) { return s.length(); }
+
+        @Override
+        public boolean hasBoundaryBefore(int c) { return true; }
+    }
+
+    // Intermediate class:
+    // Has NormalizerImpl and does boilerplate argument checking and setup.
+    public static abstract class Normalizer2WithImpl extends Normalizer2 {
+        public Normalizer2WithImpl(NormalizerImpl ni) {
+            impl=ni;
+        }
+
+        // normalize
+        @Override
+        public StringBuilder normalize(CharSequence src, StringBuilder dest) {
+            if(dest==src) {
+                throw new IllegalArgumentException();
+            }
+            dest.setLength(0);
+            normalize(src, new NormalizerImpl.ReorderingBuffer(impl, dest, src.length()));
+            return dest;
+        }
+
+        @Override
+        public Appendable normalize(CharSequence src, Appendable dest) {
+            if(dest==src) {
+                throw new IllegalArgumentException();
+            }
+            NormalizerImpl.ReorderingBuffer buffer=
+                new NormalizerImpl.ReorderingBuffer(impl, dest, src.length());
+            normalize(src, buffer);
+            buffer.flush();
+            return dest;
+        }
+
+        protected abstract void normalize(CharSequence src, NormalizerImpl.ReorderingBuffer buffer);
+
+        // normalize and append
+        @Override
+        public StringBuilder normalizeSecondAndAppend(StringBuilder first, CharSequence second) {
+            return normalizeSecondAndAppend(first, second, true);
+        }
+
+        @Override
+        public StringBuilder append(StringBuilder first, CharSequence second) {
+            return normalizeSecondAndAppend(first, second, false);
+        }
+
+        public StringBuilder normalizeSecondAndAppend(
+                StringBuilder first, CharSequence second, boolean doNormalize) {
+            if(first==second) {
+                throw new IllegalArgumentException();
+            }
+            normalizeAndAppend(
+                second, doNormalize,
+                new NormalizerImpl.ReorderingBuffer(impl, first, first.length()+second.length()));
+            return first;
+        }
+
+        protected abstract void normalizeAndAppend(
+                CharSequence src, boolean doNormalize, NormalizerImpl.ReorderingBuffer buffer);
+
+        @Override
+        public String getDecomposition(int c) {
+            return impl.getDecomposition(c);
+        }
+
+        @Override
+        public int getCombiningClass(int c) {
+            return impl.getCC(impl.getNorm16(c));
+        }
+
+        // quick checks
+        @Override
+        public boolean isNormalized(CharSequence s) {
+            return s.length()==spanQuickCheckYes(s);
+        }
+
+        public final NormalizerImpl impl;
+    }
+
+    public static final class DecomposeNormalizer2 extends Normalizer2WithImpl {
+        public DecomposeNormalizer2(NormalizerImpl ni) {
+            super(ni);
+        }
+
+        @Override
+        protected void normalize(CharSequence src, NormalizerImpl.ReorderingBuffer buffer) {
+            impl.decompose(src, 0, src.length(), buffer);
+        }
+
+        @Override
+        protected void normalizeAndAppend(
+                CharSequence src, boolean doNormalize, NormalizerImpl.ReorderingBuffer buffer) {
+            impl.decomposeAndAppend(src, doNormalize, buffer);
+        }
+
+        @Override
+        public int spanQuickCheckYes(CharSequence s) {
+            return impl.decompose(s, 0, s.length(), null);
+        }
+
+        @Override
+        public boolean hasBoundaryBefore(int c) { return impl.hasDecompBoundary(c, true); }
+    }
+
+    public static final class ComposeNormalizer2 extends Normalizer2WithImpl {
+        public ComposeNormalizer2(NormalizerImpl ni, boolean fcc) {
+            super(ni);
+            onlyContiguous=fcc;
+        }
+
+        @Override
+        protected void normalize(CharSequence src, NormalizerImpl.ReorderingBuffer buffer) {
+            impl.compose(src, 0, src.length(), onlyContiguous, true, buffer);
+        }
+
+        @Override
+        protected void normalizeAndAppend(
+                CharSequence src, boolean doNormalize, NormalizerImpl.ReorderingBuffer buffer) {
+            impl.composeAndAppend(src, doNormalize, onlyContiguous, buffer);
+        }
+
+        @Override
+        public boolean isNormalized(CharSequence s) {
+            // 5: small destCapacity for substring normalization
+            return impl.compose(s, 0, s.length(),
+                                onlyContiguous, false,
+                                new NormalizerImpl.ReorderingBuffer(impl, new StringBuilder(), 5));
+        }
+
+        @Override
+        public int spanQuickCheckYes(CharSequence s) {
+            return impl.composeQuickCheck(s, 0, s.length(), onlyContiguous, true)>>>1;
+        }
+
+        @Override
+        public boolean hasBoundaryBefore(int c) { return impl.hasCompBoundaryBefore(c); }
+
+        private final boolean onlyContiguous;
+    }
+
+    // instance cache ---------------------------------------------------------- ***
+
+    private Norm2AllModes(NormalizerImpl ni) {
+        impl=ni;
+        comp=new ComposeNormalizer2(ni, false);
+        decomp=new DecomposeNormalizer2(ni);
+    }
+
+    public final NormalizerImpl impl;
+    public final ComposeNormalizer2 comp;
+    public final DecomposeNormalizer2 decomp;
+
+    private static Norm2AllModes getInstanceFromSingleton(Norm2AllModesSingleton singleton) {
+        if(singleton.exception!=null) {
+            throw singleton.exception;
+        }
+        return singleton.allModes;
+    }
+
+    public static Norm2AllModes getNFCInstance() {
+        return getInstanceFromSingleton(NFCSingleton.INSTANCE);
+    }
+
+    public static Norm2AllModes getNFKCInstance() {
+        return getInstanceFromSingleton(NFKCSingleton.INSTANCE);
+    }
+
+    public static final NoopNormalizer2 NOOP_NORMALIZER2=new NoopNormalizer2();
+
+    private static final class Norm2AllModesSingleton {
+        private Norm2AllModesSingleton(String name) {
+            try {
+                String DATA_FILE_NAME = "/sun/text/resources/" + name + ".icu";
+                NormalizerImpl impl=new NormalizerImpl().load(DATA_FILE_NAME);
+                allModes=new Norm2AllModes(impl);
+            } catch (RuntimeException e) {
+                exception=e;
+            }
+        }
+
+        private Norm2AllModes allModes;
+        private RuntimeException exception;
+    }
+
+    private static final class NFCSingleton {
+        private static final Norm2AllModesSingleton INSTANCE=new Norm2AllModesSingleton("nfc");
+    }
+
+    private static final class NFKCSingleton {
+        private static final Norm2AllModesSingleton INSTANCE=new Norm2AllModesSingleton("nfkc");
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/Normalizer2.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,271 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/*
+ *******************************************************************************
+ *   Copyright (C) 2009-2014, International Business Machines
+ *   Corporation and others.  All Rights Reserved.
+ *******************************************************************************
+ */
+
+package sun.text.normalizer;
+
+/**
+ * Unicode normalization functionality for standard Unicode normalization or
+ * for using custom mapping tables.
+ * All instances of this class are unmodifiable/immutable.
+ * The Normalizer2 class is not intended for public subclassing.
+ * <p>
+ * The primary functions are to produce a normalized string and to detect whether
+ * a string is already normalized.
+ * The most commonly used normalization forms are those defined in
+ * http://www.unicode.org/unicode/reports/tr15/
+ * However, this API supports additional normalization forms for specialized purposes.
+ * For example, NFKC_Casefold is provided via getInstance("nfkc_cf", COMPOSE)
+ * and can be used in implementations of UTS #46.
+ * <p>
+ * Not only are the standard compose and decompose modes supplied,
+ * but additional modes are provided as documented in the Mode enum.
+ * <p>
+ * Some of the functions in this class identify normalization boundaries.
+ * At a normalization boundary, the portions of the string
+ * before it and starting from it do not interact and can be handled independently.
+ * <p>
+ * The spanQuickCheckYes() stops at a normalization boundary.
+ * When the goal is a normalized string, then the text before the boundary
+ * can be copied, and the remainder can be processed with normalizeSecondAndAppend().
+ * <p>
+ * The hasBoundaryBefore(), hasBoundaryAfter() and isInert() functions test whether
+ * a character is guaranteed to be at a normalization boundary,
+ * regardless of context.
+ * This is used for moving from one normalization boundary to the next
+ * or preceding boundary, and for performing iterative normalization.
+ * <p>
+ * Iterative normalization is useful when only a small portion of a
+ * longer string needs to be processed.
+ * For example, in ICU, iterative normalization is used by the NormalizationTransliterator
+ * (to avoid replacing already-normalized text) and ucol_nextSortKeyPart()
+ * (to process only the substring for which sort key bytes are computed).
+ * <p>
+ * The set of normalization boundaries returned by these functions may not be
+ * complete: There may be more boundaries that could be returned.
+ * Different functions may return different boundaries.
+ * @stable ICU 4.4
+ * @author Markus W. Scherer
+ */
+abstract class Normalizer2 {
+
+    /**
+     * Returns a Normalizer2 instance for Unicode NFC normalization.
+     * Same as getInstance(null, "nfc", Mode.COMPOSE).
+     * Returns an unmodifiable singleton instance.
+     * @return the requested Normalizer2, if successful
+     * @stable ICU 49
+     */
+    public static Normalizer2 getNFCInstance() {
+        return Norm2AllModes.getNFCInstance().comp;
+    }
+
+    /**
+     * Returns a Normalizer2 instance for Unicode NFD normalization.
+     * Same as getInstance(null, "nfc", Mode.DECOMPOSE).
+     * Returns an unmodifiable singleton instance.
+     * @return the requested Normalizer2, if successful
+     * @stable ICU 49
+     */
+    public static Normalizer2 getNFDInstance() {
+        return Norm2AllModes.getNFCInstance().decomp;
+    }
+
+    /**
+     * Returns a Normalizer2 instance for Unicode NFKC normalization.
+     * Same as getInstance(null, "nfkc", Mode.COMPOSE).
+     * Returns an unmodifiable singleton instance.
+     * @return the requested Normalizer2, if successful
+     * @stable ICU 49
+     */
+    public static Normalizer2 getNFKCInstance() {
+        return Norm2AllModes.getNFKCInstance().comp;
+    }
+
+    /**
+     * Returns a Normalizer2 instance for Unicode NFKD normalization.
+     * Same as getInstance(null, "nfkc", Mode.DECOMPOSE).
+     * Returns an unmodifiable singleton instance.
+     * @return the requested Normalizer2, if successful
+     * @stable ICU 49
+     */
+    public static Normalizer2 getNFKDInstance() {
+        return Norm2AllModes.getNFKCInstance().decomp;
+    }
+
+    /**
+     * Returns the normalized form of the source string.
+     * @param src source string
+     * @return normalized src
+     * @stable ICU 4.4
+     */
+    public String normalize(CharSequence src) {
+        if(src instanceof String) {
+            // Fastpath: Do not construct a new String if the src is a String
+            // and is already normalized.
+            int spanLength=spanQuickCheckYes(src);
+            if(spanLength==src.length()) {
+                return (String)src;
+            }
+            StringBuilder sb=new StringBuilder(src.length()).append(src, 0, spanLength);
+            return normalizeSecondAndAppend(sb, src.subSequence(spanLength, src.length())).toString();
+        }
+        return normalize(src, new StringBuilder(src.length())).toString();
+    }
+
+    /**
+     * Writes the normalized form of the source string to the destination string
+     * (replacing its contents) and returns the destination string.
+     * The source and destination strings must be different objects.
+     * @param src source string
+     * @param dest destination string; its contents is replaced with normalized src
+     * @return dest
+     * @stable ICU 4.4
+     */
+    public abstract StringBuilder normalize(CharSequence src, StringBuilder dest);
+
+    /**
+     * Writes the normalized form of the source string to the destination Appendable
+     * and returns the destination Appendable.
+     * The source and destination strings must be different objects.
+     *
+     * <p>Any {@link java.io.IOException} is wrapped into a {@link com.ibm.icu.util.ICUUncheckedIOException}.
+     *
+     * @param src source string
+     * @param dest destination Appendable; gets normalized src appended
+     * @return dest
+     * @stable ICU 4.6
+     */
+    public abstract Appendable normalize(CharSequence src, Appendable dest);
+
+    /**
+     * Appends the normalized form of the second string to the first string
+     * (merging them at the boundary) and returns the first string.
+     * The result is normalized if the first string was normalized.
+     * The first and second strings must be different objects.
+     * @param first string, should be normalized
+     * @param second string, will be normalized
+     * @return first
+     * @stable ICU 4.4
+     */
+    public abstract StringBuilder normalizeSecondAndAppend(
+            StringBuilder first, CharSequence second);
+
+    /**
+     * Appends the second string to the first string
+     * (merging them at the boundary) and returns the first string.
+     * The result is normalized if both the strings were normalized.
+     * The first and second strings must be different objects.
+     * @param first string, should be normalized
+     * @param second string, should be normalized
+     * @return first
+     * @stable ICU 4.4
+     */
+    public abstract StringBuilder append(StringBuilder first, CharSequence second);
+
+    /**
+     * Gets the decomposition mapping of c.
+     * Roughly equivalent to normalizing the String form of c
+     * on a DECOMPOSE Normalizer2 instance, but much faster, and except that this function
+     * returns null if c does not have a decomposition mapping in this instance's data.
+     * This function is independent of the mode of the Normalizer2.
+     * @param c code point
+     * @return c's decomposition mapping, if any; otherwise null
+     * @stable ICU 4.6
+     */
+    public abstract String getDecomposition(int c);
+
+    /**
+     * Gets the combining class of c.
+     * The default implementation returns 0
+     * but all standard implementations return the Unicode Canonical_Combining_Class value.
+     * @param c code point
+     * @return c's combining class
+     * @stable ICU 49
+     */
+    public int getCombiningClass(int c) { return 0; }
+
+    /**
+     * Tests if the string is normalized.
+     * Internally, in cases where the quickCheck() method would return "maybe"
+     * (which is only possible for the two COMPOSE modes) this method
+     * resolves to "yes" or "no" to provide a definitive result,
+     * at the cost of doing more work in those cases.
+     * @param s input string
+     * @return true if s is normalized
+     * @stable ICU 4.4
+     */
+    public abstract boolean isNormalized(CharSequence s);
+
+    /**
+     * Returns the end of the normalized substring of the input string.
+     * In other words, with <code>end=spanQuickCheckYes(s);</code>
+     * the substring <code>s.subSequence(0, end)</code>
+     * will pass the quick check with a "yes" result.
+     * <p>
+     * The returned end index is usually one or more characters before the
+     * "no" or "maybe" character: The end index is at a normalization boundary.
+     * (See the class documentation for more about normalization boundaries.)
+     * <p>
+     * When the goal is a normalized string and most input strings are expected
+     * to be normalized already, then call this method,
+     * and if it returns a prefix shorter than the input string,
+     * copy that prefix and use normalizeSecondAndAppend() for the remainder.
+     * @param s input string
+     * @return "yes" span end index
+     * @stable ICU 4.4
+     */
+    public abstract int spanQuickCheckYes(CharSequence s);
+
+    /**
+     * Tests if the character always has a normalization boundary before it,
+     * regardless of context.
+     * If true, then the character does not normalization-interact with
+     * preceding characters.
+     * In other words, a string containing this character can be normalized
+     * by processing portions before this character and starting from this
+     * character independently.
+     * This is used for iterative normalization. See the class documentation for details.
+     * @param c character to test
+     * @return true if c has a normalization boundary before it
+     * @stable ICU 4.4
+     */
+    public abstract boolean hasBoundaryBefore(int c);
+
+    /**
+     * Sole constructor.  (For invocation by subclass constructors,
+     * typically implicit.)
+     * @internal
+     * deprecated This API is ICU internal only.
+     */
+    protected Normalizer2() {
+    }
+}
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/NormalizerBase.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/NormalizerBase.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -22,18 +22,13 @@
  * or visit www.oracle.com if you need additional information or have any
  * questions.
  */
+
 /*
  *******************************************************************************
- * (C) Copyright IBM Corp. and others, 1996-2009 - All Rights Reserved         *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
+ * Copyright (C) 2000-2014, International Business Machines Corporation and
+ * others. All Rights Reserved.
  *******************************************************************************
  */
-
 package sun.text.normalizer;
 
 import java.text.CharacterIterator;
@@ -125,8 +120,8 @@
  *
  * normalize(FCD) may be implemented with NFD.
  *
- * For more details on FCD see the collation design document:
- * http://source.icu-project.org/repos/icu/icuhtml/trunk/design/collation/ICU_collation_design.htm
+ * For more details on FCD see Unicode Technical Note #5 (Canonical Equivalence in Applications):
+ * http://www.unicode.org/notes/tn5/#FCD
  *
  * ICU collation performs either NFD or FCD normalization automatically if
  * normalization is turned on for the collator object. Beyond collation and
@@ -138,26 +133,88 @@
  * often do not encode any combining marks by themselves. For conversion to such
  * character encodings the Unicode text needs to be normalized to NFC.
  * For more usage examples, see the Unicode Standard Annex.
+ *
+ * Note: The Normalizer class also provides API for iterative normalization.
+ * While the setIndex() and getIndex() refer to indices in the
+ * underlying Unicode input text, the next() and previous() methods
+ * iterate through characters in the normalized output.
+ * This means that there is not necessarily a one-to-one correspondence
+ * between characters returned by next() and previous() and the indices
+ * passed to and returned from setIndex() and getIndex().
+ * It is for this reason that Normalizer does not implement the CharacterIterator interface.
+ *
  * @stable ICU 2.8
  */
-
+// Original filename in ICU4J: Normalizer.java
 public final class NormalizerBase implements Cloneable {
 
-    //-------------------------------------------------------------------------
-    // Private data
-    //-------------------------------------------------------------------------
-    private char[] buffer = new char[100];
-    private int bufferStart = 0;
-    private int bufferPos   = 0;
-    private int bufferLimit = 0;
-
     // The input text and our position in it
     private UCharacterIterator  text;
-    private Mode                mode = NFC;
-    private int                 options = 0;
+    private Normalizer2         norm2;
+    private Mode                mode;
+    private int                 options;
+
+    // The normalization buffer is the result of normalization
+    // of the source in [currentIndex..nextIndex] .
     private int                 currentIndex;
     private int                 nextIndex;
 
+    // A buffer for holding intermediate results
+    private StringBuilder       buffer;
+    private int                 bufferPos;
+
+    // Helper classes to defer loading of normalization data.
+    private static final class ModeImpl {
+        private ModeImpl(Normalizer2 n2) {
+            normalizer2 = n2;
+        }
+        private final Normalizer2 normalizer2;
+    }
+
+    private static final class NFDModeImpl {
+        private static final ModeImpl INSTANCE = new ModeImpl(Normalizer2.getNFDInstance());
+    }
+
+    private static final class NFKDModeImpl {
+        private static final ModeImpl INSTANCE = new ModeImpl(Normalizer2.getNFKDInstance());
+    }
+
+    private static final class NFCModeImpl {
+        private static final ModeImpl INSTANCE = new ModeImpl(Normalizer2.getNFCInstance());
+    }
+
+    private static final class NFKCModeImpl {
+        private static final ModeImpl INSTANCE = new ModeImpl(Normalizer2.getNFKCInstance());
+    }
+
+    private static final class Unicode32 {
+        private static final UnicodeSet INSTANCE = new UnicodeSet("[:age=3.2:]").freeze();
+    }
+
+    private static final class NFD32ModeImpl {
+        private static final ModeImpl INSTANCE =
+            new ModeImpl(new FilteredNormalizer2(Normalizer2.getNFDInstance(),
+                                                 Unicode32.INSTANCE));
+    }
+
+    private static final class NFKD32ModeImpl {
+        private static final ModeImpl INSTANCE =
+            new ModeImpl(new FilteredNormalizer2(Normalizer2.getNFKDInstance(),
+                                                 Unicode32.INSTANCE));
+    }
+
+    private static final class NFC32ModeImpl {
+        private static final ModeImpl INSTANCE =
+            new ModeImpl(new FilteredNormalizer2(Normalizer2.getNFCInstance(),
+                                                 Unicode32.INSTANCE));
+    }
+
+    private static final class NFKC32ModeImpl {
+        private static final ModeImpl INSTANCE =
+            new ModeImpl(new FilteredNormalizer2(Normalizer2.getNFKCInstance(),
+                                                 Unicode32.INSTANCE));
+    }
+
     /**
      * Options bit set value to select Unicode 3.2 normalization
      * (except NormalizationCorrections).
@@ -166,6 +223,17 @@
      */
     public static final int UNICODE_3_2=0x20;
 
+    public static final int UNICODE_3_2_0_ORIGINAL=UNICODE_3_2;
+
+    /*
+     * Default option for the latest Unicode normalization. This option is
+     * provided mainly for testing.
+     * The value zero means that normalization is done with the fixes for
+     *   - Corrigendum 4 (Five CJK Canonical Mapping Errors)
+     *   - Corrigendum 5 (Normalization Idempotency)
+     */
+    public static final int UNICODE_LATEST = 0x00;
+
     /**
      * Constant indicating that the end of the iteration has been reached.
      * This is guaranteed to have the same value as {@link UCharacterIterator#DONE}.
@@ -175,101 +243,80 @@
 
     /**
      * Constants for normalization modes.
+     * <p>
+     * The Mode class is not intended for public subclassing.
+     * Only the Mode constants provided by the Normalizer class should be used,
+     * and any fields or methods should not be called or overridden by users.
      * @stable ICU 2.8
      */
-    public static class Mode {
-        private int modeValue;
-        private Mode(int value) {
-            modeValue = value;
-        }
+    public static abstract class Mode {
 
         /**
-         * This method is used for method dispatch
-         * @stable ICU 2.6
+         * Sole constructor
+         * @internal
+         * @deprecated This API is ICU internal only.
          */
-        protected int normalize(char[] src, int srcStart, int srcLimit,
-                                char[] dest,int destStart,int destLimit,
-                                UnicodeSet nx) {
-            int srcLen = (srcLimit - srcStart);
-            int destLen = (destLimit - destStart);
-            if( srcLen > destLen ) {
-                return srcLen;
-            }
-            System.arraycopy(src,srcStart,dest,destStart,srcLen);
-            return srcLen;
-        }
-
-        /**
-         * This method is used for method dispatch
-         * @stable ICU 2.6
-         */
-        protected int normalize(char[] src, int srcStart, int srcLimit,
-                                char[] dest,int destStart,int destLimit,
-                                int options) {
-            return normalize(   src, srcStart, srcLimit,
-                                dest,destStart,destLimit,
-                                NormalizerImpl.getNX(options)
-                                );
-        }
-
-        /**
-         * This method is used for method dispatch
-         * @stable ICU 2.6
-         */
-        protected String normalize(String src, int options) {
-            return src;
+        @Deprecated
+        protected Mode() {
         }
 
         /**
-         * This method is used for method dispatch
-         * @stable ICU 2.8
-         */
-        protected int getMinC() {
-            return -1;
-        }
-
-        /**
-         * This method is used for method dispatch
-         * @stable ICU 2.8
+         * @internal
+         * @deprecated This API is ICU internal only.
          */
-        protected int getMask() {
-            return -1;
-        }
+        @Deprecated
+        protected abstract Normalizer2 getNormalizer2(int options);
+    }
 
-        /**
-         * This method is used for method dispatch
-         * @stable ICU 2.8
-         */
-        protected IsPrevBoundary getPrevBoundary() {
-            return null;
+    private static Mode toMode(Normalizer.Form form) {
+        switch (form) {
+        case NFC :
+            return NFC;
+        case NFD :
+            return NFD;
+        case NFKC :
+            return NFKC;
+        case NFKD :
+            return NFKD;
         }
 
-        /**
-         * This method is used for method dispatch
-         * @stable ICU 2.8
-         */
-        protected IsNextBoundary getNextBoundary() {
-            return null;
+        throw new IllegalArgumentException("Unexpected normalization form: " +
+                                           form);
+    }
+
+    private static final class NONEMode extends Mode {
+        protected Normalizer2 getNormalizer2(int options) { return Norm2AllModes.NOOP_NORMALIZER2; }
+    }
+
+    private static final class NFDMode extends Mode {
+        protected Normalizer2 getNormalizer2(int options) {
+            return (options&UNICODE_3_2) != 0 ?
+                    NFD32ModeImpl.INSTANCE.normalizer2 :
+                    NFDModeImpl.INSTANCE.normalizer2;
         }
+    }
 
-        /**
-         * This method is used for method dispatch
-         * @stable ICU 2.6
-         */
-        protected QuickCheckResult quickCheck(char[] src,int start, int limit,
-                                              boolean allowMaybe,UnicodeSet nx) {
-            if(allowMaybe) {
-                return MAYBE;
-            }
-            return NO;
+    private static final class NFKDMode extends Mode {
+        protected Normalizer2 getNormalizer2(int options) {
+            return (options&UNICODE_3_2) != 0 ?
+                    NFKD32ModeImpl.INSTANCE.normalizer2 :
+                    NFKDModeImpl.INSTANCE.normalizer2;
         }
+    }
 
-        /**
-         * This method is used for method dispatch
-         * @stable ICU 2.8
-         */
-        protected boolean isNFSkippable(int c) {
-            return true;
+    private static final class NFCMode extends Mode {
+        protected Normalizer2 getNormalizer2(int options) {
+            return (options&UNICODE_3_2) != 0 ?
+                    NFC32ModeImpl.INSTANCE.normalizer2 :
+                    NFCModeImpl.INSTANCE.normalizer2;
+        }
+    }
+
+    private static final class NFKCMode extends Mode {
+        protected Normalizer2 getNormalizer2(int options) {
+            return (options&UNICODE_3_2) != 0 ?
+                    NFKC32ModeImpl.INSTANCE.normalizer2 :
+                    NFKCModeImpl.INSTANCE.normalizer2;
         }
     }
 
@@ -277,290 +324,39 @@
      * No decomposition/composition.
      * @stable ICU 2.8
      */
-    public static final Mode NONE = new Mode(1);
+    public static final Mode NONE = new NONEMode();
 
     /**
      * Canonical decomposition.
      * @stable ICU 2.8
      */
-    public static final Mode NFD = new NFDMode(2);
-
-    private static final class NFDMode extends Mode {
-        private NFDMode(int value) {
-            super(value);
-        }
-
-        protected int normalize(char[] src, int srcStart, int srcLimit,
-                                char[] dest,int destStart,int destLimit,
-                                UnicodeSet nx) {
-            int[] trailCC = new int[1];
-            return NormalizerImpl.decompose(src,  srcStart,srcLimit,
-                                            dest, destStart,destLimit,
-                                            false, trailCC,nx);
-        }
-
-        protected String normalize( String src, int options) {
-            return decompose(src,false,options);
-        }
-
-        protected int getMinC() {
-            return NormalizerImpl.MIN_WITH_LEAD_CC;
-        }
-
-        protected IsPrevBoundary getPrevBoundary() {
-            return new IsPrevNFDSafe();
-        }
-
-        protected IsNextBoundary getNextBoundary() {
-            return new IsNextNFDSafe();
-        }
-
-        protected int getMask() {
-            return (NormalizerImpl.CC_MASK|NormalizerImpl.QC_NFD);
-        }
-
-        protected QuickCheckResult quickCheck(char[] src,int start,
-                                              int limit,boolean allowMaybe,
-                                              UnicodeSet nx) {
-            return NormalizerImpl.quickCheck(
-                                             src, start,limit,
-                                             NormalizerImpl.getFromIndexesArr(
-                                                                              NormalizerImpl.INDEX_MIN_NFD_NO_MAYBE
-                                                                              ),
-                                             NormalizerImpl.QC_NFD,
-                                             0,
-                                             allowMaybe,
-                                             nx
-                                             );
-        }
-
-        protected boolean isNFSkippable(int c) {
-            return NormalizerImpl.isNFSkippable(c,this,
-                                                (NormalizerImpl.CC_MASK|NormalizerImpl.QC_NFD)
-                                                );
-        }
-    }
+    public static final Mode NFD = new NFDMode();
 
     /**
      * Compatibility decomposition.
      * @stable ICU 2.8
      */
-    public static final Mode NFKD = new NFKDMode(3);
-
-    private static final class NFKDMode extends Mode {
-        private NFKDMode(int value) {
-            super(value);
-        }
-
-        protected int normalize(char[] src, int srcStart, int srcLimit,
-                                char[] dest,int destStart,int destLimit,
-                                UnicodeSet nx) {
-            int[] trailCC = new int[1];
-            return NormalizerImpl.decompose(src,  srcStart,srcLimit,
-                                            dest, destStart,destLimit,
-                                            true, trailCC, nx);
-        }
-
-        protected String normalize( String src, int options) {
-            return decompose(src,true,options);
-        }
-
-        protected int getMinC() {
-            return NormalizerImpl.MIN_WITH_LEAD_CC;
-        }
-
-        protected IsPrevBoundary getPrevBoundary() {
-            return new IsPrevNFDSafe();
-        }
-
-        protected IsNextBoundary getNextBoundary() {
-            return new IsNextNFDSafe();
-        }
-
-        protected int getMask() {
-            return (NormalizerImpl.CC_MASK|NormalizerImpl.QC_NFKD);
-        }
-
-        protected QuickCheckResult quickCheck(char[] src,int start,
-                                              int limit,boolean allowMaybe,
-                                              UnicodeSet nx) {
-            return NormalizerImpl.quickCheck(
-                                             src,start,limit,
-                                             NormalizerImpl.getFromIndexesArr(
-                                                                              NormalizerImpl.INDEX_MIN_NFKD_NO_MAYBE
-                                                                              ),
-                                             NormalizerImpl.QC_NFKD,
-                                             NormalizerImpl.OPTIONS_COMPAT,
-                                             allowMaybe,
-                                             nx
-                                             );
-        }
-
-        protected boolean isNFSkippable(int c) {
-            return NormalizerImpl.isNFSkippable(c, this,
-                                                (NormalizerImpl.CC_MASK|NormalizerImpl.QC_NFKD)
-                                                );
-        }
-    }
+    public static final Mode NFKD = new NFKDMode();
 
     /**
      * Canonical decomposition followed by canonical composition.
      * @stable ICU 2.8
      */
-    public static final Mode NFC = new NFCMode(4);
-
-    private static final class NFCMode extends Mode{
-        private NFCMode(int value) {
-            super(value);
-        }
-        protected int normalize(char[] src, int srcStart, int srcLimit,
-                                char[] dest,int destStart,int destLimit,
-                                UnicodeSet nx) {
-            return NormalizerImpl.compose( src, srcStart, srcLimit,
-                                           dest,destStart,destLimit,
-                                           0, nx);
-        }
-
-        protected String normalize( String src, int options) {
-            return compose(src, false, options);
-        }
-
-        protected int getMinC() {
-            return NormalizerImpl.getFromIndexesArr(
-                                                    NormalizerImpl.INDEX_MIN_NFC_NO_MAYBE
-                                                    );
-        }
-        protected IsPrevBoundary getPrevBoundary() {
-            return new IsPrevTrueStarter();
-        }
-        protected IsNextBoundary getNextBoundary() {
-            return new IsNextTrueStarter();
-        }
-        protected int getMask() {
-            return (NormalizerImpl.CC_MASK|NormalizerImpl.QC_NFC);
-        }
-        protected QuickCheckResult quickCheck(char[] src,int start,
-                                              int limit,boolean allowMaybe,
-                                              UnicodeSet nx) {
-            return NormalizerImpl.quickCheck(
-                                             src,start,limit,
-                                             NormalizerImpl.getFromIndexesArr(
-                                                                              NormalizerImpl.INDEX_MIN_NFC_NO_MAYBE
-                                                                              ),
-                                             NormalizerImpl.QC_NFC,
-                                             0,
-                                             allowMaybe,
-                                             nx
-                                             );
-        }
-        protected boolean isNFSkippable(int c) {
-            return NormalizerImpl.isNFSkippable(c,this,
-                                                ( NormalizerImpl.CC_MASK|NormalizerImpl.COMBINES_ANY|
-                                                  (NormalizerImpl.QC_NFC & NormalizerImpl.QC_ANY_NO)
-                                                  )
-                                                );
-        }
-    };
-
-    /**
-     * Compatibility decomposition followed by canonical composition.
-     * @stable ICU 2.8
-     */
-    public static final Mode NFKC =new NFKCMode(5);
+    public static final Mode NFC = new NFCMode();
 
-    private static final class NFKCMode extends Mode{
-        private NFKCMode(int value) {
-            super(value);
-        }
-        protected int normalize(char[] src, int srcStart, int srcLimit,
-                                char[] dest,int destStart,int destLimit,
-                                UnicodeSet nx) {
-            return NormalizerImpl.compose(src,  srcStart,srcLimit,
-                                          dest, destStart,destLimit,
-                                          NormalizerImpl.OPTIONS_COMPAT, nx);
-        }
-
-        protected String normalize( String src, int options) {
-            return compose(src, true, options);
-        }
-        protected int getMinC() {
-            return NormalizerImpl.getFromIndexesArr(
-                                                    NormalizerImpl.INDEX_MIN_NFKC_NO_MAYBE
-                                                    );
-        }
-        protected IsPrevBoundary getPrevBoundary() {
-            return new IsPrevTrueStarter();
-        }
-        protected IsNextBoundary getNextBoundary() {
-            return new IsNextTrueStarter();
-        }
-        protected int getMask() {
-            return (NormalizerImpl.CC_MASK|NormalizerImpl.QC_NFKC);
-        }
-        protected QuickCheckResult quickCheck(char[] src,int start,
-                                              int limit,boolean allowMaybe,
-                                              UnicodeSet nx) {
-            return NormalizerImpl.quickCheck(
-                                             src,start,limit,
-                                             NormalizerImpl.getFromIndexesArr(
-                                                                              NormalizerImpl.INDEX_MIN_NFKC_NO_MAYBE
-                                                                              ),
-                                             NormalizerImpl.QC_NFKC,
-                                             NormalizerImpl.OPTIONS_COMPAT,
-                                             allowMaybe,
-                                             nx
-                                             );
-        }
-        protected boolean isNFSkippable(int c) {
-            return NormalizerImpl.isNFSkippable(c, this,
-                                                ( NormalizerImpl.CC_MASK|NormalizerImpl.COMBINES_ANY|
-                                                  (NormalizerImpl.QC_NFKC & NormalizerImpl.QC_ANY_NO)
-                                                  )
-                                                );
-        }
-    };
-
-    /**
-     * Result values for quickCheck().
-     * For details see Unicode Technical Report 15.
-     * @stable ICU 2.8
-     */
-    public static final class QuickCheckResult{
-        private int resultValue;
-        private QuickCheckResult(int value) {
-            resultValue=value;
-        }
-    }
-    /**
-     * Indicates that string is not in the normalized format
-     * @stable ICU 2.8
-     */
-    public static final QuickCheckResult NO = new QuickCheckResult(0);
-
-    /**
-     * Indicates that string is in the normalized format
-     * @stable ICU 2.8
-     */
-    public static final QuickCheckResult YES = new QuickCheckResult(1);
-
-    /**
-     * Indicates it cannot be determined if string is in the normalized
-     * format without further thorough checks.
-     * @stable ICU 2.8
-     */
-    public static final QuickCheckResult MAYBE = new QuickCheckResult(2);
+    public static final Mode NFKC =new NFKCMode();
 
     //-------------------------------------------------------------------------
-    // Constructors
+    // Iterator constructors
     //-------------------------------------------------------------------------
 
     /**
-     * Creates a new {@code Normalizer} object for iterating over the
+     * Creates a new {@code NormalizerBase} object for iterating over the
      * normalized form of a given string.
      * <p>
      * The {@code options} parameter specifies which optional
-     * {@code Normalizer} features are to be enabled for this object.
-     *
+     * {@code NormalizerBase} features are to be enabled for this object.
+     * <p>
      * @param str  The string to be normalized.  The normalization
      *              will start at the beginning of the string.
      *
@@ -576,25 +372,19 @@
         this.text = UCharacterIterator.getInstance(str);
         this.mode = mode;
         this.options=opt;
+        norm2 = mode.getNormalizer2(opt);
+        buffer = new StringBuilder();
     }
 
+    public NormalizerBase(String str, Mode mode) {
+       this(str, mode, 0);
+    }
+
+
     /**
-     * Creates a new {@code Normalizer} object for iterating over the
+     * Creates a new {@code NormalizerBase} object for iterating over the
      * normalized form of the given text.
-     *
-     * @param iter  The input text to be normalized.  The normalization
-     *              will start at the beginning of the string.
-     *
-     * @param mode  The normalization mode.
-     */
-    public NormalizerBase(CharacterIterator iter, Mode mode) {
-          this(iter, mode, UNICODE_LATEST);
-    }
-
-    /**
-     * Creates a new {@code Normalizer} object for iterating over the
-     * normalized form of the given text.
-     *
+     * <p>
      * @param iter  The input text to be normalized.  The normalization
      *              will start at the beginning of the string.
      *
@@ -607,15 +397,19 @@
      * @stable ICU 2.6
      */
     public NormalizerBase(CharacterIterator iter, Mode mode, int opt) {
-        this.text = UCharacterIterator.getInstance(
-                                                   (CharacterIterator)iter.clone()
-                                                   );
+        this.text = UCharacterIterator.getInstance((CharacterIterator)iter.clone());
         this.mode = mode;
         this.options = opt;
+        norm2 = mode.getNormalizer2(opt);
+        buffer = new StringBuilder();
+    }
+
+    public NormalizerBase(CharacterIterator iter, Mode mode) {
+       this(iter, mode, 0);
     }
 
     /**
-     * Clones this {@code Normalizer} object.  All properties of this
+     * Clones this {@code NormalizerBase} object.  All properties of this
      * object are duplicated in the new object, including the cloning of any
      * {@link CharacterIterator} that was passed in to the constructor
      * or to {@link #setText(CharacterIterator) setText}.
@@ -628,11 +422,13 @@
         try {
             NormalizerBase copy = (NormalizerBase) super.clone();
             copy.text = (UCharacterIterator) text.clone();
-            //clone the internal buffer
-            if (buffer != null) {
-                copy.buffer = new char[buffer.length];
-                System.arraycopy(buffer,0,copy.buffer,0,buffer.length);
-            }
+            copy.mode = mode;
+            copy.options = options;
+            copy.norm2 = norm2;
+            copy.buffer = new StringBuilder(buffer);
+            copy.bufferPos = bufferPos;
+            copy.currentIndex = currentIndex;
+            copy.nextIndex = nextIndex;
             return copy;
         }
         catch (CloneNotSupportedException e) {
@@ -640,150 +436,60 @@
         }
     }
 
-    //--------------------------------------------------------------------------
-    // Static Utility methods
-    //--------------------------------------------------------------------------
-
     /**
-     * Compose a string.
-     * The string will be composed according to the specified mode.
-     * @param str        The string to compose.
-     * @param compat     If true the string will be composed according to
-     *                    NFKC rules and if false will be composed according to
-     *                    NFC rules.
-     * @param options    The only recognized option is UNICODE_3_2
-     * @return String    The composed string
+     * Normalizes a {@code String} using the given normalization operation.
+     * <p>
+     * The {@code options} parameter specifies which optional
+     * {@code NormalizerBase} features are to be enabled for this operation.
+     * Currently the only available option is {@link #UNICODE_3_2}.
+     * If you want the default behavior corresponding to one of the standard
+     * Unicode Normalization Forms, use 0 for this argument.
+     * <p>
+     * @param str       the input string to be normalized.
+     * @param mode      the normalization mode
+     * @param options   the optional features to be enabled.
+     * @return String   the normalized string
      * @stable ICU 2.6
      */
-    public static String compose(String str, boolean compat, int options) {
-
-        char[] dest, src;
-        if (options == UNICODE_3_2_0_ORIGINAL) {
-            String mappedStr = NormalizerImpl.convert(str);
-            dest = new char[mappedStr.length()*MAX_BUF_SIZE_COMPOSE];
-            src = mappedStr.toCharArray();
-        } else {
-            dest = new char[str.length()*MAX_BUF_SIZE_COMPOSE];
-            src = str.toCharArray();
-        }
-        int destSize=0;
-
-        UnicodeSet nx = NormalizerImpl.getNX(options);
-
-        /* reset options bits that should only be set here or inside compose() */
-        options&=~(NormalizerImpl.OPTIONS_SETS_MASK|NormalizerImpl.OPTIONS_COMPAT|NormalizerImpl.OPTIONS_COMPOSE_CONTIGUOUS);
-
-        if(compat) {
-            options|=NormalizerImpl.OPTIONS_COMPAT;
-        }
-
-        for(;;) {
-            destSize=NormalizerImpl.compose(src,0,src.length,
-                                            dest,0,dest.length,options,
-                                            nx);
-            if(destSize<=dest.length) {
-                return new String(dest,0,destSize);
-            } else {
-                dest = new char[destSize];
-            }
-        }
+    public static String normalize(String str, Mode mode, int options) {
+        return mode.getNormalizer2(options).normalize(str);
     }
 
-    private static final int MAX_BUF_SIZE_COMPOSE = 2;
-    private static final int MAX_BUF_SIZE_DECOMPOSE = 3;
+    public static String normalize(String str, Normalizer.Form form) {
+        return NormalizerBase.normalize(str, toMode(form), UNICODE_LATEST);
+    }
 
-    /**
-     * Decompose a string.
-     * The string will be decomposed according to the specified mode.
-     * @param str       The string to decompose.
-     * @param compat    If true the string will be decomposed according to NFKD
-     *                   rules and if false will be decomposed according to NFD
-     *                   rules.
-     * @return String   The decomposed string
-     * @stable ICU 2.8
-     */
-    public static String decompose(String str, boolean compat) {
-        return decompose(str,compat,UNICODE_LATEST);
+    public static String normalize(String str, Normalizer.Form form, int options) {
+        return NormalizerBase.normalize(str, toMode(form), options);
     }
 
     /**
-     * Decompose a string.
-     * The string will be decomposed according to the specified mode.
-     * @param str     The string to decompose.
-     * @param compat  If true the string will be decomposed according to NFKD
-     *                 rules and if false will be decomposed according to NFD
-     *                 rules.
-     * @param options The normalization options, ORed together (0 for no options).
-     * @return String The decomposed string
+     * Test if a string is in a given normalization form.
+     * This is semantically equivalent to source.equals(normalize(source, mode)).
+     *
+     * Unlike quickCheck(), this function returns a definitive result,
+     * never a "maybe".
+     * For NFD, NFKD, and FCD, both functions work exactly the same.
+     * For NFC and NFKC where quickCheck may return "maybe", this function will
+     * perform further tests to arrive at a true/false result.
+     * @param str       the input string to be checked to see if it is
+     *                   normalized
+     * @param mode      the normalization mode
+     * @param options   Options for use with exclusion set and tailored Normalization
+     *                  The only option that is currently recognized is UNICODE_3_2
+     * @see #isNormalized
      * @stable ICU 2.6
      */
-    public static String decompose(String str, boolean compat, int options) {
-
-        int[] trailCC = new int[1];
-        int destSize=0;
-        UnicodeSet nx = NormalizerImpl.getNX(options);
-        char[] dest;
-
-        if (options == UNICODE_3_2_0_ORIGINAL) {
-            String mappedStr = NormalizerImpl.convert(str);
-            dest = new char[mappedStr.length()*MAX_BUF_SIZE_DECOMPOSE];
-
-            for(;;) {
-                destSize=NormalizerImpl.decompose(mappedStr.toCharArray(),0,mappedStr.length(),
-                                                  dest,0,dest.length,
-                                                  compat,trailCC, nx);
-                if(destSize<=dest.length) {
-                    return new String(dest,0,destSize);
-                } else {
-                    dest = new char[destSize];
-                }
-            }
-        } else {
-            dest = new char[str.length()*MAX_BUF_SIZE_DECOMPOSE];
-
-            for(;;) {
-                destSize=NormalizerImpl.decompose(str.toCharArray(),0,str.length(),
-                                                  dest,0,dest.length,
-                                                  compat,trailCC, nx);
-                if(destSize<=dest.length) {
-                    return new String(dest,0,destSize);
-                } else {
-                    dest = new char[destSize];
-                }
-            }
-        }
+    public static boolean isNormalized(String str, Mode mode, int options) {
+        return mode.getNormalizer2(options).isNormalized(str);
     }
 
-    /**
-     * Normalize a string.
-     * The string will be normalized according to the specified normalization
-     * mode and options.
-     * @param src       The char array to compose.
-     * @param srcStart  Start index of the source
-     * @param srcLimit  Limit index of the source
-     * @param dest      The char buffer to fill in
-     * @param destStart Start index of the destination buffer
-     * @param destLimit End index of the destination buffer
-     * @param mode      The normalization mode; one of Normalizer.NONE,
-     *                   Normalizer.NFD, Normalizer.NFC, Normalizer.NFKC,
-     *                   Normalizer.NFKD, Normalizer.DEFAULT
-     * @param options The normalization options, ORed together (0 for no options).
-     * @return int      The total buffer size needed;if greater than length of
-     *                   result, the output was truncated.
-     * @exception       IndexOutOfBoundsException if the target capacity is
-     *                   less than the required length
-     * @stable ICU 2.6
-     */
-    public static int normalize(char[] src,int srcStart, int srcLimit,
-                                char[] dest,int destStart, int destLimit,
-                                Mode  mode, int options) {
-        int length = mode.normalize(src,srcStart,srcLimit,dest,destStart,destLimit, options);
+    public static boolean isNormalized(String str, Normalizer.Form form) {
+        return NormalizerBase.isNormalized(str, toMode(form), UNICODE_LATEST);
+    }
 
-        if(length<=(destLimit-destStart)) {
-            return length;
-        } else {
-            throw new IndexOutOfBoundsException(Integer.toString(length));
-        }
+    public static boolean isNormalized(String str, Normalizer.Form form, int options) {
+        return NormalizerBase.isNormalized(str, toMode(form), options);
     }
 
     //-------------------------------------------------------------------------
@@ -796,8 +502,8 @@
      * @stable ICU 2.8
      */
     public int current() {
-        if(bufferPos<bufferLimit || nextNormalize()) {
-            return getCodePointAt(bufferPos);
+        if(bufferPos<buffer.length() || nextNormalize()) {
+            return buffer.codePointAt(bufferPos);
         } else {
             return DONE;
         }
@@ -811,16 +517,15 @@
      * @stable ICU 2.8
      */
     public int next() {
-        if(bufferPos<bufferLimit ||  nextNormalize()) {
-            int c=getCodePointAt(bufferPos);
-            bufferPos+=(c>0xFFFF) ? 2 : 1;
+        if(bufferPos<buffer.length() ||  nextNormalize()) {
+            int c=buffer.codePointAt(bufferPos);
+            bufferPos+=Character.charCount(c);
             return c;
         } else {
             return DONE;
         }
     }
 
-
     /**
      * Return the previous character in the normalized text and decrement
      * the iteration position by one.  If the beginning
@@ -830,8 +535,8 @@
      */
     public int previous() {
         if(bufferPos>0 || previousNormalize()) {
-            int c=getCodePointAt(bufferPos-1);
-            bufferPos-=(c>0xFFFF) ? 2 : 1;
+            int c=buffer.codePointBefore(bufferPos);
+            bufferPos-=Character.charCount(c);
             return c;
         } else {
             return DONE;
@@ -859,8 +564,8 @@
      * @stable ICU 2.8
      */
     public void setIndexOnly(int index) {
-        text.setIndex(index);
-        currentIndex=nextIndex=index; // validates index
+        text.setIndex(index);  // validates index
+        currentIndex=nextIndex=index;
         clearBuffer();
     }
 
@@ -874,7 +579,7 @@
      * necessarily a one-to-one correspondence between characters returned
      * by {@code next} and {@code previous} and the indices passed to and
      * returned from {@code setIndex} and {@link #getIndex}.
-     *
+     * <p>
      * @param index the desired index in the input text.
      *
      * @return   the first normalized character that is the result of iterating
@@ -882,11 +587,9 @@
      *
      * @throws IllegalArgumentException if the given index is less than
      *          {@link #getBeginIndex} or greater than {@link #getEndIndex}.
-     * @return The codepoint as an int
-     * @deprecated ICU 3.2
+     * deprecated ICU 3.2
      * @obsolete ICU 3.2
      */
-     @Deprecated
      public int setIndex(int index) {
          setIndexOnly(index);
          return current();
@@ -895,7 +598,7 @@
     /**
      * Retrieve the index of the start of the input text. This is the begin
      * index of the {@code CharacterIterator} or the start (i.e. 0) of the
-     * {@code String} over which this {@code Normalizer} is iterating
+     * {@code String} over which this {@code NormalizerBase} is iterating
      * @deprecated ICU 2.2. Use startIndex() instead.
      * @return The codepoint as an int
      * @see #startIndex
@@ -908,7 +611,7 @@
     /**
      * Retrieve the index of the end of the input text.  This is the end index
      * of the {@code CharacterIterator} or the length of the {@code String}
-     * over which this {@code Normalizer} is iterating
+     * over which this {@code NormalizerBase} is iterating
      * @deprecated ICU 2.2. Use endIndex() instead.
      * @return The codepoint as an int
      * @see #endIndex
@@ -934,7 +637,7 @@
      * @stable ICU 2.8
      */
     public int getIndex() {
-        if(bufferPos<bufferLimit) {
+        if(bufferPos<buffer.length()) {
             return currentIndex;
         } else {
             return nextIndex;
@@ -942,9 +645,9 @@
     }
 
     /**
-     * Retrieve the index of the end of the input text. This is the end index
+     * Retrieve the index of the end of the input text.  This is the end index
      * of the {@code CharacterIterator} or the length of the {@code String}
-     * over which this {@code Normalizer} is iterating
+     * over which this {@code NormalizerBase} is iterating
      * @return The current iteration position
      * @stable ICU 2.8
      */
@@ -953,7 +656,7 @@
     }
 
     //-------------------------------------------------------------------------
-    // Property access methods
+    // Iterator attributes
     //-------------------------------------------------------------------------
     /**
      * Set the normalization mode for this object.
@@ -964,18 +667,18 @@
      * until the iteration is able to re-sync at the next base character.
      * It is safest to call {@link #setText setText()}, {@link #first},
      * {@link #last}, etc. after calling {@code setMode}.
-     *
-     * @param newMode the new mode for this {@code Normalizer}.
+     * <p>
+     * @param newMode the new mode for this {@code NormalizerBase}.
      * The supported modes are:
      * <ul>
-     *  <li>{@link #COMPOSE}        - Unicode canonical decompositiion
-     *                                  followed by canonical composition.
-     *  <li>{@link #COMPOSE_COMPAT} - Unicode compatibility decompositiion
-     *                                  follwed by canonical composition.
-     *  <li>{@link #DECOMP}         - Unicode canonical decomposition
-     *  <li>{@link #DECOMP_COMPAT}  - Unicode compatibility decomposition.
-     *  <li>{@link #NO_OP}          - Do nothing but return characters
-     *                                  from the underlying input text.
+     *  <li>{@link #NFC}    - Unicode canonical decompositiion
+     *                        followed by canonical composition.
+     *  <li>{@link #NFKC}   - Unicode compatibility decompositiion
+     *                        follwed by canonical composition.
+     *  <li>{@link #NFD}    - Unicode canonical decomposition
+     *  <li>{@link #NFKD}   - Unicode compatibility decomposition.
+     *  <li>{@link #NONE}   - Do nothing but return characters
+     *                        from the underlying input text.
      * </ul>
      *
      * @see #getMode
@@ -983,9 +686,11 @@
      */
     public void setMode(Mode newMode) {
         mode = newMode;
+        norm2 = mode.getNormalizer2(options);
     }
+
     /**
-     * Return the basic operation performed by this {@code Normalizer}
+     * Return the basic operation performed by this {@code NormalizerBase}
      *
      * @see #setMode
      * @stable ICU 2.8
@@ -995,688 +700,83 @@
     }
 
     /**
-     * Set the input text over which this {@code Normalizer} will iterate.
+     * Set the input text over which this {@code NormalizerBase} will iterate.
      * The iteration position is set to the beginning of the input text.
      * @param newText   The new string to be normalized.
      * @stable ICU 2.8
      */
     public void setText(String newText) {
-
         UCharacterIterator newIter = UCharacterIterator.getInstance(newText);
         if (newIter == null) {
-            throw new InternalError("Could not create a new UCharacterIterator");
+            throw new IllegalStateException("Could not create a new UCharacterIterator");
         }
         text = newIter;
         reset();
     }
 
     /**
-     * Set the input text over which this {@code Normalizer} will iterate.
+     * Set the input text over which this {@code NormalizerBase} will iterate.
      * The iteration position is set to the beginning of the input text.
      * @param newText   The new string to be normalized.
      * @stable ICU 2.8
      */
     public void setText(CharacterIterator newText) {
-
         UCharacterIterator newIter = UCharacterIterator.getInstance(newText);
         if (newIter == null) {
-            throw new InternalError("Could not create a new UCharacterIterator");
+            throw new IllegalStateException("Could not create a new UCharacterIterator");
         }
         text = newIter;
         currentIndex=nextIndex=0;
         clearBuffer();
     }
 
-    //-------------------------------------------------------------------------
-    // Private utility methods
-    //-------------------------------------------------------------------------
-
-
-    /* backward iteration --------------------------------------------------- */
-
-    /*
-     * read backwards and get norm32
-     * return 0 if the character is <minC
-     * if c2!=0 then (c2, c) is a surrogate pair (reversed - c2 is first
-     * surrogate but read second!)
-     */
-
-    private static  long getPrevNorm32(UCharacterIterator src,
-                                       int/*unsigned*/ minC,
-                                       int/*unsigned*/ mask,
-                                       char[] chars) {
-        long norm32;
-        int ch=0;
-        /* need src.hasPrevious() */
-        if((ch=src.previous()) == UCharacterIterator.DONE) {
-            return 0;
-        }
-        chars[0]=(char)ch;
-        chars[1]=0;
-
-        /* check for a surrogate before getting norm32 to see if we need to
-         * predecrement further */
-        if(chars[0]<minC) {
-            return 0;
-        } else if(!UTF16.isSurrogate(chars[0])) {
-            return NormalizerImpl.getNorm32(chars[0]);
-        } else if(UTF16.isLeadSurrogate(chars[0]) || (src.getIndex()==0)) {
-            /* unpaired surrogate */
-            chars[1]=(char)src.current();
-            return 0;
-        } else if(UTF16.isLeadSurrogate(chars[1]=(char)src.previous())) {
-            norm32=NormalizerImpl.getNorm32(chars[1]);
-            if((norm32&mask)==0) {
-                /* all surrogate pairs with this lead surrogate have irrelevant
-                 * data */
-                return 0;
-            } else {
-                /* norm32 must be a surrogate special */
-                return NormalizerImpl.getNorm32FromSurrogatePair(norm32,chars[0]);
-            }
-        } else {
-            /* unpaired second surrogate, undo the c2=src.previous() movement */
-            src.moveIndex( 1);
-            return 0;
-        }
+    private void clearBuffer() {
+        buffer.setLength(0);
+        bufferPos=0;
     }
 
-    private interface IsPrevBoundary{
-        public boolean isPrevBoundary(UCharacterIterator src,
-                                      int/*unsigned*/ minC,
-                                      int/*unsigned*/ mask,
-                                      char[] chars);
-    }
-    private static final class IsPrevNFDSafe implements IsPrevBoundary{
-        /*
-         * for NF*D:
-         * read backwards and check if the lead combining class is 0
-         * if c2!=0 then (c2, c) is a surrogate pair (reversed - c2 is first
-         * surrogate but read second!)
-         */
-        public boolean isPrevBoundary(UCharacterIterator src,
-                                      int/*unsigned*/ minC,
-                                      int/*unsigned*/ ccOrQCMask,
-                                      char[] chars) {
-
-            return NormalizerImpl.isNFDSafe(getPrevNorm32(src, minC,
-                                                          ccOrQCMask, chars),
-                                            ccOrQCMask,
-                                            ccOrQCMask& NormalizerImpl.QC_MASK);
+    private boolean nextNormalize() {
+        clearBuffer();
+        currentIndex=nextIndex;
+        text.setIndex(nextIndex);
+        // Skip at least one character so we make progress.
+        int c=text.nextCodePoint();
+        if(c<0) {
+            return false;
         }
+        StringBuilder segment=new StringBuilder().appendCodePoint(c);
+        while((c=text.nextCodePoint())>=0) {
+            if(norm2.hasBoundaryBefore(c)) {
+                text.moveCodePointIndex(-1);
+                break;
+            }
+            segment.appendCodePoint(c);
+        }
+        nextIndex=text.getIndex();
+        norm2.normalize(segment, buffer);
+        return buffer.length()!=0;
     }
 
-    private static final class IsPrevTrueStarter implements IsPrevBoundary{
-        /*
-         * read backwards and check if the character is (or its decomposition
-         * begins with) a "true starter" (cc==0 and NF*C_YES)
-         * if c2!=0 then (c2, c) is a surrogate pair (reversed - c2 is first
-         * surrogate but read second!)
-         */
-        public boolean isPrevBoundary(UCharacterIterator src,
-                                      int/*unsigned*/ minC,
-                                      int/*unsigned*/ ccOrQCMask,
-                                      char[] chars) {
-            long norm32;
-            int/*unsigned*/ decompQCMask;
-
-            decompQCMask=(ccOrQCMask<<2)&0xf; /*decomposition quick check mask*/
-            norm32=getPrevNorm32(src, minC, ccOrQCMask|decompQCMask, chars);
-            return NormalizerImpl.isTrueStarter(norm32,ccOrQCMask,decompQCMask);
-        }
-    }
-
-    private static int findPreviousIterationBoundary(UCharacterIterator src,
-                                                     IsPrevBoundary obj,
-                                                     int/*unsigned*/ minC,
-                                                     int/*mask*/ mask,
-                                                     char[] buffer,
-                                                     int[] startIndex) {
-        char[] chars=new char[2];
-        boolean isBoundary;
-
-        /* fill the buffer from the end backwards */
-        startIndex[0] = buffer.length;
-        chars[0]=0;
-        while(src.getIndex()>0 && chars[0]!=UCharacterIterator.DONE) {
-            isBoundary=obj.isPrevBoundary(src, minC, mask, chars);
-
-            /* always write this character to the front of the buffer */
-            /* make sure there is enough space in the buffer */
-            if(startIndex[0] < (chars[1]==0 ? 1 : 2)) {
-
-                // grow the buffer
-                char[] newBuf = new char[buffer.length*2];
-                /* move the current buffer contents up */
-                System.arraycopy(buffer,startIndex[0],newBuf,
-                                 newBuf.length-(buffer.length-startIndex[0]),
-                                 buffer.length-startIndex[0]);
-                //adjust the startIndex
-                startIndex[0]+=newBuf.length-buffer.length;
-
-                buffer=newBuf;
-                newBuf=null;
-
+    private boolean previousNormalize() {
+        clearBuffer();
+        nextIndex=currentIndex;
+        text.setIndex(currentIndex);
+        StringBuilder segment=new StringBuilder();
+        int c;
+        while((c=text.previousCodePoint())>=0) {
+            if(c<=0xffff) {
+                segment.insert(0, (char)c);
+            } else {
+                segment.insert(0, Character.toChars(c));
             }
-
-            buffer[--startIndex[0]]=chars[0];
-            if(chars[1]!=0) {
-                buffer[--startIndex[0]]=chars[1];
-            }
-
-            /* stop if this just-copied character is a boundary */
-            if(isBoundary) {
+            if(norm2.hasBoundaryBefore(c)) {
                 break;
             }
         }
-
-        /* return the length of the buffer contents */
-        return buffer.length-startIndex[0];
-    }
-
-    private static int previous(UCharacterIterator src,
-                                char[] dest, int destStart, int destLimit,
-                                Mode mode,
-                                boolean doNormalize,
-                                boolean[] pNeededToNormalize,
-                                int options) {
-
-        IsPrevBoundary isPreviousBoundary;
-        int destLength, bufferLength;
-        int/*unsigned*/ mask;
-        int c,c2;
-
-        char minC;
-        int destCapacity = destLimit-destStart;
-        destLength=0;
-
-        if(pNeededToNormalize!=null) {
-            pNeededToNormalize[0]=false;
-        }
-        minC = (char)mode.getMinC();
-        mask = mode.getMask();
-        isPreviousBoundary = mode.getPrevBoundary();
-
-        if(isPreviousBoundary==null) {
-            destLength=0;
-            if((c=src.previous())>=0) {
-                destLength=1;
-                if(UTF16.isTrailSurrogate((char)c)) {
-                    c2= src.previous();
-                    if(c2!= UCharacterIterator.DONE) {
-                        if(UTF16.isLeadSurrogate((char)c2)) {
-                            if(destCapacity>=2) {
-                                dest[1]=(char)c; // trail surrogate
-                                destLength=2;
-                            }
-                            // lead surrogate to be written below
-                            c=c2;
-                        } else {
-                            src.moveIndex(1);
-                        }
-                    }
-                }
-
-                if(destCapacity>0) {
-                    dest[0]=(char)c;
-                }
-            }
-            return destLength;
-        }
-
-        char[] buffer = new char[100];
-        int[] startIndex= new int[1];
-        bufferLength=findPreviousIterationBoundary(src,
-                                                   isPreviousBoundary,
-                                                   minC, mask,buffer,
-                                                   startIndex);
-        if(bufferLength>0) {
-            if(doNormalize) {
-                destLength=NormalizerBase.normalize(buffer,startIndex[0],
-                                                startIndex[0]+bufferLength,
-                                                dest, destStart,destLimit,
-                                                mode, options);
-
-                if(pNeededToNormalize!=null) {
-                    pNeededToNormalize[0]=destLength!=bufferLength ||
-                                          Utility.arrayRegionMatches(
-                                            buffer,0,dest,
-                                            destStart,destLimit
-                                          );
-                }
-            } else {
-                /* just copy the source characters */
-                if(destCapacity>0) {
-                    System.arraycopy(buffer,startIndex[0],dest,0,
-                                     (bufferLength<destCapacity) ?
-                                     bufferLength : destCapacity
-                                     );
-                }
-            }
-        }
-
-
-        return destLength;
-    }
-
-
-
-    /* forward iteration ---------------------------------------------------- */
-    /*
-     * read forward and check if the character is a next-iteration boundary
-     * if c2!=0 then (c, c2) is a surrogate pair
-     */
-    private interface IsNextBoundary{
-        boolean isNextBoundary(UCharacterIterator src,
-                               int/*unsigned*/ minC,
-                               int/*unsigned*/ mask,
-                               int[] chars);
-    }
-    /*
-     * read forward and get norm32
-     * return 0 if the character is <minC
-     * if c2!=0 then (c2, c) is a surrogate pair
-     * always reads complete characters
-     */
-    private static long /*unsigned*/ getNextNorm32(UCharacterIterator src,
-                                                   int/*unsigned*/ minC,
-                                                   int/*unsigned*/ mask,
-                                                   int[] chars) {
-        long norm32;
-
-        /* need src.hasNext() to be true */
-        chars[0]=src.next();
-        chars[1]=0;
-
-        if(chars[0]<minC) {
-            return 0;
-        }
-
-        norm32=NormalizerImpl.getNorm32((char)chars[0]);
-        if(UTF16.isLeadSurrogate((char)chars[0])) {
-            if(src.current()!=UCharacterIterator.DONE &&
-               UTF16.isTrailSurrogate((char)(chars[1]=src.current()))) {
-                src.moveIndex(1); /* skip the c2 surrogate */
-                if((norm32&mask)==0) {
-                    /* irrelevant data */
-                    return 0;
-                } else {
-                    /* norm32 must be a surrogate special */
-                    return NormalizerImpl.getNorm32FromSurrogatePair(norm32,(char)chars[1]);
-                }
-            } else {
-                /* unmatched surrogate */
-                return 0;
-            }
-        }
-        return norm32;
-    }
-
-
-    /*
-     * for NF*D:
-     * read forward and check if the lead combining class is 0
-     * if c2!=0 then (c, c2) is a surrogate pair
-     */
-    private static final class IsNextNFDSafe implements IsNextBoundary{
-        public boolean isNextBoundary(UCharacterIterator src,
-                                      int/*unsigned*/ minC,
-                                      int/*unsigned*/ ccOrQCMask,
-                                      int[] chars) {
-            return NormalizerImpl.isNFDSafe(getNextNorm32(src,minC,ccOrQCMask,chars),
-                                            ccOrQCMask, ccOrQCMask&NormalizerImpl.QC_MASK);
-        }
-    }
-
-    /*
-     * for NF*C:
-     * read forward and check if the character is (or its decomposition begins
-     * with) a "true starter" (cc==0 and NF*C_YES)
-     * if c2!=0 then (c, c2) is a surrogate pair
-     */
-    private static final class IsNextTrueStarter implements IsNextBoundary{
-        public boolean isNextBoundary(UCharacterIterator src,
-                                      int/*unsigned*/ minC,
-                                      int/*unsigned*/ ccOrQCMask,
-                                      int[] chars) {
-            long norm32;
-            int/*unsigned*/ decompQCMask;
-
-            decompQCMask=(ccOrQCMask<<2)&0xf; /*decomposition quick check mask*/
-            norm32=getNextNorm32(src, minC, ccOrQCMask|decompQCMask, chars);
-            return NormalizerImpl.isTrueStarter(norm32, ccOrQCMask, decompQCMask);
-        }
-    }
-
-    private static int findNextIterationBoundary(UCharacterIterator src,
-                                                 IsNextBoundary obj,
-                                                 int/*unsigned*/ minC,
-                                                 int/*unsigned*/ mask,
-                                                 char[] buffer) {
-        if(src.current()==UCharacterIterator.DONE) {
-            return 0;
-        }
-
-        /* get one character and ignore its properties */
-        int[] chars = new int[2];
-        chars[0]=src.next();
-        buffer[0]=(char)chars[0];
-        int bufferIndex = 1;
-
-        if(UTF16.isLeadSurrogate((char)chars[0])&&
-           src.current()!=UCharacterIterator.DONE) {
-            if(UTF16.isTrailSurrogate((char)(chars[1]=src.next()))) {
-                buffer[bufferIndex++]=(char)chars[1];
-            } else {
-                src.moveIndex(-1); /* back out the non-trail-surrogate */
-            }
-        }
-
-        /* get all following characters until we see a boundary */
-        /* checking hasNext() instead of c!=DONE on the off-chance that U+ffff
-         * is part of the string */
-        while( src.current()!=UCharacterIterator.DONE) {
-            if(obj.isNextBoundary(src, minC, mask, chars)) {
-                /* back out the latest movement to stop at the boundary */
-                src.moveIndex(chars[1]==0 ? -1 : -2);
-                break;
-            } else {
-                if(bufferIndex+(chars[1]==0 ? 1 : 2)<=buffer.length) {
-                    buffer[bufferIndex++]=(char)chars[0];
-                    if(chars[1]!=0) {
-                        buffer[bufferIndex++]=(char)chars[1];
-                    }
-                } else {
-                    char[] newBuf = new char[buffer.length*2];
-                    System.arraycopy(buffer,0,newBuf,0,bufferIndex);
-                    buffer = newBuf;
-                    buffer[bufferIndex++]=(char)chars[0];
-                    if(chars[1]!=0) {
-                        buffer[bufferIndex++]=(char)chars[1];
-                    }
-                }
-            }
-        }
-
-        /* return the length of the buffer contents */
-        return bufferIndex;
+        currentIndex=text.getIndex();
+        norm2.normalize(segment, buffer);
+        bufferPos=buffer.length();
+        return buffer.length()!=0;
     }
 
-    private static int next(UCharacterIterator src,
-                            char[] dest, int destStart, int destLimit,
-                            NormalizerBase.Mode mode,
-                            boolean doNormalize,
-                            boolean[] pNeededToNormalize,
-                            int options) {
-
-        IsNextBoundary isNextBoundary;
-        int /*unsigned*/ mask;
-        int /*unsigned*/ bufferLength;
-        int c,c2;
-        char minC;
-        int destCapacity = destLimit - destStart;
-        int destLength = 0;
-        if(pNeededToNormalize!=null) {
-            pNeededToNormalize[0]=false;
-        }
-
-        minC = (char)mode.getMinC();
-        mask = mode.getMask();
-        isNextBoundary = mode.getNextBoundary();
-
-        if(isNextBoundary==null) {
-            destLength=0;
-            c=src.next();
-            if(c!=UCharacterIterator.DONE) {
-                destLength=1;
-                if(UTF16.isLeadSurrogate((char)c)) {
-                    c2= src.next();
-                    if(c2!= UCharacterIterator.DONE) {
-                        if(UTF16.isTrailSurrogate((char)c2)) {
-                            if(destCapacity>=2) {
-                                dest[1]=(char)c2; // trail surrogate
-                                destLength=2;
-                            }
-                            // lead surrogate to be written below
-                        } else {
-                            src.moveIndex(-1);
-                        }
-                    }
-                }
-
-                if(destCapacity>0) {
-                    dest[0]=(char)c;
-                }
-            }
-            return destLength;
-        }
-
-        char[] buffer=new char[100];
-        int[] startIndex = new int[1];
-        bufferLength=findNextIterationBoundary(src,isNextBoundary, minC, mask,
-                                               buffer);
-        if(bufferLength>0) {
-            if(doNormalize) {
-                destLength=mode.normalize(buffer,startIndex[0],bufferLength,
-                                          dest,destStart,destLimit, options);
-
-                if(pNeededToNormalize!=null) {
-                    pNeededToNormalize[0]=destLength!=bufferLength ||
-                                          Utility.arrayRegionMatches(buffer,startIndex[0],
-                                            dest,destStart,
-                                            destLength);
-                }
-            } else {
-                /* just copy the source characters */
-                if(destCapacity>0) {
-                    System.arraycopy(buffer,0,dest,destStart,
-                                     Math.min(bufferLength,destCapacity)
-                                     );
-                }
-
-
-            }
-        }
-        return destLength;
-    }
-
-    private void clearBuffer() {
-        bufferLimit=bufferStart=bufferPos=0;
-    }
-
-    private boolean nextNormalize() {
-
-        clearBuffer();
-        currentIndex=nextIndex;
-        text.setIndex(nextIndex);
-
-        bufferLimit=next(text,buffer,bufferStart,buffer.length,mode,true,null,options);
-
-        nextIndex=text.getIndex();
-        return (bufferLimit>0);
-    }
-
-    private boolean previousNormalize() {
-
-        clearBuffer();
-        nextIndex=currentIndex;
-        text.setIndex(currentIndex);
-        bufferLimit=previous(text,buffer,bufferStart,buffer.length,mode,true,null,options);
-
-        currentIndex=text.getIndex();
-        bufferPos = bufferLimit;
-        return bufferLimit>0;
-    }
-
-    private int getCodePointAt(int index) {
-        if( UTF16.isSurrogate(buffer[index])) {
-            if(UTF16.isLeadSurrogate(buffer[index])) {
-                if((index+1)<bufferLimit &&
-                   UTF16.isTrailSurrogate(buffer[index+1])) {
-                    return UCharacterProperty.getRawSupplementary(
-                                                                  buffer[index],
-                                                                  buffer[index+1]
-                                                                  );
-                }
-            }else if(UTF16.isTrailSurrogate(buffer[index])) {
-                if(index>0 && UTF16.isLeadSurrogate(buffer[index-1])) {
-                    return UCharacterProperty.getRawSupplementary(
-                                                                  buffer[index-1],
-                                                                  buffer[index]
-                                                                  );
-                }
-            }
-        }
-        return buffer[index];
-
-    }
-
-    /**
-     * Internal API
-     * @internal
-     */
-    public static boolean isNFSkippable(int c, Mode mode) {
-        return mode.isNFSkippable(c);
-    }
-
-    //
-    // Options
-    //
-
-    /*
-     * Default option for Unicode 3.2.0 normalization.
-     * Corrigendum 4 was fixed in Unicode 3.2.0 but isn't supported in
-     * IDNA/StringPrep.
-     * The public review issue #29 was fixed in Unicode 4.1.0. Corrigendum 5
-     * allowed Unicode 3.2 to 4.0.1 to apply the fix for PRI #29, but it isn't
-     * supported by IDNA/StringPrep as well as Corrigendum 4.
-     */
-    public static final int UNICODE_3_2_0_ORIGINAL =
-                               UNICODE_3_2 |
-                               NormalizerImpl.WITHOUT_CORRIGENDUM4_CORRECTIONS |
-                               NormalizerImpl.BEFORE_PRI_29;
-
-    /*
-     * Default option for the latest Unicode normalization. This option is
-     * provided mainly for testing.
-     * The value zero means that normalization is done with the fixes for
-     *   - Corrigendum 4 (Five CJK Canonical Mapping Errors)
-     *   - Corrigendum 5 (Normalization Idempotency)
-     */
-    public static final int UNICODE_LATEST = 0x00;
-
-    //
-    // public constructor and methods for java.text.Normalizer and
-    // sun.text.Normalizer
-    //
-
-    /**
-     * Creates a new {@code Normalizer} object for iterating over the
-     * normalized form of a given string.
-     *
-     * @param str  The string to be normalized.  The normalization
-     *              will start at the beginning of the string.
-     *
-     * @param mode The normalization mode.
-     */
-    public NormalizerBase(String str, Mode mode) {
-          this(str, mode, UNICODE_LATEST);
-    }
-
-    /**
-     * Normalizes a <code>String</code> using the given normalization form.
-     *
-     * @param str      the input string to be normalized.
-     * @param form     the normalization form
-     */
-    public static String normalize(String str, Normalizer.Form form) {
-        return normalize(str, form, UNICODE_LATEST);
-    }
-
-    /**
-     * Normalizes a <code>String</code> using the given normalization form.
-     *
-     * @param str      the input string to be normalized.
-     * @param form     the normalization form
-     * @param options   the optional features to be enabled.
-     */
-    public static String normalize(String str, Normalizer.Form form, int options) {
-        int len = str.length();
-        boolean asciiOnly = true;
-        if (len < 80) {
-            for (int i = 0; i < len; i++) {
-                if (str.charAt(i) > 127) {
-                    asciiOnly = false;
-                    break;
-                }
-            }
-        } else {
-            char[] a = str.toCharArray();
-            for (int i = 0; i < len; i++) {
-                if (a[i] > 127) {
-                    asciiOnly = false;
-                    break;
-                }
-            }
-        }
-
-        switch (form) {
-        case NFC :
-            return asciiOnly ? str : NFC.normalize(str, options);
-        case NFD :
-            return asciiOnly ? str : NFD.normalize(str, options);
-        case NFKC :
-            return asciiOnly ? str : NFKC.normalize(str, options);
-        case NFKD :
-            return asciiOnly ? str : NFKD.normalize(str, options);
-        }
-
-        throw new IllegalArgumentException("Unexpected normalization form: " +
-                                           form);
-    }
-
-    /**
-     * Test if a string is in a given normalization form.
-     * This is semantically equivalent to source.equals(normalize(source, mode)).
-     *
-     * Unlike quickCheck(), this function returns a definitive result,
-     * never a "maybe".
-     * For NFD, NFKD, and FCD, both functions work exactly the same.
-     * For NFC and NFKC where quickCheck may return "maybe", this function will
-     * perform further tests to arrive at a true/false result.
-     * @param str       the input string to be checked to see if it is normalized
-     * @param form      the normalization form
-     */
-    public static boolean isNormalized(String str, Normalizer.Form form) {
-        return isNormalized(str, form, UNICODE_LATEST);
-    }
-
-    /**
-     * Test if a string is in a given normalization form.
-     * This is semantically equivalent to source.equals(normalize(source, mode)).
-     *
-     * Unlike quickCheck(), this function returns a definitive result,
-     * never a "maybe".
-     * For NFD, NFKD, and FCD, both functions work exactly the same.
-     * For NFC and NFKC where quickCheck may return "maybe", this function will
-     * perform further tests to arrive at a true/false result.
-     * @param str       the input string to be checked to see if it is normalized
-     * @param form      the normalization form
-     * @param options   the optional features to be enabled.
-     */
-    public static boolean isNormalized(String str, Normalizer.Form form, int options) {
-        switch (form) {
-        case NFC:
-            return (NFC.quickCheck(str.toCharArray(),0,str.length(),false,NormalizerImpl.getNX(options))==YES);
-        case NFD:
-            return (NFD.quickCheck(str.toCharArray(),0,str.length(),false,NormalizerImpl.getNX(options))==YES);
-        case NFKC:
-            return (NFKC.quickCheck(str.toCharArray(),0,str.length(),false,NormalizerImpl.getNX(options))==YES);
-        case NFKD:
-            return (NFKD.quickCheck(str.toCharArray(),0,str.length(),false,NormalizerImpl.getNX(options))==YES);
-        }
-
-        throw new IllegalArgumentException("Unexpected normalization form: " +
-                                           form);
-    }
 }
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/NormalizerDataReader.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,389 +0,0 @@
-/*
- * Copyright (c) 2005, 2009, 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.
- */
-/*
- *******************************************************************************
- * (C) Copyright IBM Corp. and others, 1996-2009 - All Rights Reserved         *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
- *******************************************************************************
- */
-
-package sun.text.normalizer;
-
-import java.io.DataInputStream;
-import java.io.InputStream;
-import java.io.IOException;
-
-/**
- * @author        Ram Viswanadha
- */
-
-    /*
-     * Description of the format of unorm.icu version 2.1.
-     *
-     * Main change from version 1 to version 2:
-     * Use of new, common Trie instead of normalization-specific tries.
-     * Change to version 2.1: add third/auxiliary trie with associated data.
-     *
-     * For more details of how to use the data structures see the code
-     * in unorm.cpp (runtime normalization code) and
-     * in gennorm.c and gennorm/store.c (build-time data generation).
-     *
-     * For the serialized format of Trie see Trie.c/TrieHeader.
-     *
-     * - Overall partition
-     *
-     * unorm.icu customarily begins with a UDataInfo structure, see udata.h and .c.
-     * After that there are the following structures:
-     *
-     * char indexes[INDEX_TOP];                   -- INDEX_TOP=32, see enum in this file
-     *
-     * Trie normTrie;                           -- size in bytes=indexes[INDEX_TRIE_SIZE]
-     *
-     * char extraData[extraDataTop];            -- extraDataTop=indexes[INDEX_UCHAR_COUNT]
-     *                                                 extraData[0] contains the number of units for
-     *                                                 FC_NFKC_Closure (formatVersion>=2.1)
-     *
-     * char combiningTable[combiningTableTop];  -- combiningTableTop=indexes[INDEX_COMBINE_DATA_COUNT]
-     *                                                 combiningTableTop may include one 16-bit padding unit
-     *                                                 to make sure that fcdTrie is 32-bit-aligned
-     *
-     * Trie fcdTrie;                            -- size in bytes=indexes[INDEX_FCD_TRIE_SIZE]
-     *
-     * Trie auxTrie;                            -- size in bytes=indexes[INDEX_AUX_TRIE_SIZE]
-     *
-     *
-     * The indexes array contains lengths and sizes of the following arrays and structures
-     * as well as the following values:
-     *  indexes[INDEX_COMBINE_FWD_COUNT]=combineFwdTop
-     *      -- one more than the highest combining index computed for forward-only-combining characters
-     *  indexes[INDEX_COMBINE_BOTH_COUNT]=combineBothTop-combineFwdTop
-     *      -- number of combining indexes computed for both-ways-combining characters
-     *  indexes[INDEX_COMBINE_BACK_COUNT]=combineBackTop-combineBothTop
-     *      -- number of combining indexes computed for backward-only-combining characters
-     *
-     *  indexes[INDEX_MIN_NF*_NO_MAYBE] (where *={ C, D, KC, KD })
-     *      -- first code point with a quick check NF* value of NO/MAYBE
-     *
-     *
-     * - Tries
-     *
-     * The main structures are two Trie tables ("compact arrays"),
-     * each with one index array and one data array.
-     * See Trie.h and Trie.c.
-     *
-     *
-     * - Tries in unorm.icu
-     *
-     * The first trie (normTrie above)
-     * provides data for the NF* quick checks and normalization.
-     * The second trie (fcdTrie above) provides data just for FCD checks.
-     *
-     *
-     * - norm32 data words from the first trie
-     *
-     * The norm32Table contains one 32-bit word "norm32" per code point.
-     * It contains the following bit fields:
-     * 31..16   extra data index, EXTRA_SHIFT is used to shift this field down
-     *          if this index is <EXTRA_INDEX_TOP then it is an index into
-     *              extraData[] where variable-length normalization data for this
-     *              code point is found
-     *          if this index is <EXTRA_INDEX_TOP+EXTRA_SURROGATE_TOP
-     *              then this is a norm32 for a leading surrogate, and the index
-     *              value is used together with the following trailing surrogate
-     *              code unit in the second trie access
-     *          if this index is >=EXTRA_INDEX_TOP+EXTRA_SURROGATE_TOP
-     *              then this is a norm32 for a "special" character,
-     *              i.e., the character is a Hangul syllable or a Jamo
-     *              see EXTRA_HANGUL etc.
-     *          generally, instead of extracting this index from the norm32 and
-     *              comparing it with the above constants,
-     *              the normalization code compares the entire norm32 value
-     *              with MIN_SPECIAL, SURROGATES_TOP, MIN_HANGUL etc.
-     *
-     * 15..8    combining class (cc) according to UnicodeData.txt
-     *
-     *  7..6    COMBINES_ANY flags, used in composition to see if a character
-     *              combines with any following or preceding character(s)
-     *              at all
-     *     7    COMBINES_BACK
-     *     6    COMBINES_FWD
-     *
-     *  5..0    quick check flags, set for "no" or "maybe", with separate flags for
-     *              each normalization form
-     *              the higher bits are "maybe" flags; for NF*D there are no such flags
-     *              the lower bits are "no" flags for all forms, in the same order
-     *              as the "maybe" flags,
-     *              which is (MSB to LSB): NFKD NFD NFKC NFC
-     *  5..4    QC_ANY_MAYBE
-     *  3..0    QC_ANY_NO
-     *              see further related constants
-     *
-     *
-     * - Extra data per code point
-     *
-     * "Extra data" is referenced by the index in norm32.
-     * It is variable-length data. It is only present, and only those parts
-     * of it are, as needed for a given character.
-     * The norm32 extra data index is added to the beginning of extraData[]
-     * to get to a vector of 16-bit words with data at the following offsets:
-     *
-     * [-1]     Combining index for composition.
-     *              Stored only if norm32&COMBINES_ANY .
-     * [0]      Lengths of the canonical and compatibility decomposition strings.
-     *              Stored only if there are decompositions, i.e.,
-     *              if norm32&(QC_NFD|QC_NFKD)
-     *          High byte: length of NFKD, or 0 if none
-     *          Low byte: length of NFD, or 0 if none
-     *          Each length byte also has another flag:
-     *              Bit 7 of a length byte is set if there are non-zero
-     *              combining classes (cc's) associated with the respective
-     *              decomposition. If this flag is set, then the decomposition
-     *              is preceded by a 16-bit word that contains the
-     *              leading and trailing cc's.
-     *              Bits 6..0 of a length byte are the length of the
-     *              decomposition string, not counting the cc word.
-     * [1..n]   NFD
-     * [n+1..]  NFKD
-     *
-     * Each of the two decompositions consists of up to two parts:
-     * - The 16-bit words with the leading and trailing cc's.
-     *   This is only stored if bit 7 of the corresponding length byte
-     *   is set. In this case, at least one of the cc's is not zero.
-     *   High byte: leading cc==cc of the first code point in the decomposition string
-     *   Low byte: trailing cc==cc of the last code point in the decomposition string
-     * - The decomposition string in UTF-16, with length code units.
-     *
-     *
-     * - Combining indexes and combiningTable[]
-     *
-     * Combining indexes are stored at the [-1] offset of the extra data
-     * if the character combines forward or backward with any other characters.
-     * They are used for (re)composition in NF*C.
-     * Values of combining indexes are arranged according to whether a character
-     * combines forward, backward, or both ways:
-     *    forward-only < both ways < backward-only
-     *
-     * The index values for forward-only and both-ways combining characters
-     * are indexes into the combiningTable[].
-     * The index values for backward-only combining characters are simply
-     * incremented from the preceding index values to be unique.
-     *
-     * In the combiningTable[], a variable-length list
-     * of variable-length (back-index, code point) pair entries is stored
-     * for each forward-combining character.
-     *
-     * These back-indexes are the combining indexes of both-ways or backward-only
-     * combining characters that the forward-combining character combines with.
-     *
-     * Each list is sorted in ascending order of back-indexes.
-     * Each list is terminated with the last back-index having bit 15 set.
-     *
-     * Each pair (back-index, code point) takes up either 2 or 3
-     * 16-bit words.
-     * The first word of a list entry is the back-index, with its bit 15 set if
-     * this is the last pair in the list.
-     *
-     * The second word contains flags in bits 15..13 that determine
-     * if there is a third word and how the combined character is encoded:
-     * 15   set if there is a third word in this list entry
-     * 14   set if the result is a supplementary character
-     * 13   set if the result itself combines forward
-     *
-     * According to these bits 15..14 of the second word,
-     * the result character is encoded as follows:
-     * 00 or 01 The result is <=0x1fff and stored in bits 12..0 of
-     *          the second word.
-     * 10       The result is 0x2000..0xffff and stored in the third word.
-     *          Bits 12..0 of the second word are not used.
-     * 11       The result is a supplementary character.
-     *          Bits 9..0 of the leading surrogate are in bits 9..0 of
-     *          the second word.
-     *          Add 0xd800 to these bits to get the complete surrogate.
-     *          Bits 12..10 of the second word are not used.
-     *          The trailing surrogate is stored in the third word.
-     *
-     *
-     * - FCD trie
-     *
-     * The FCD trie is very simple.
-     * It is a folded trie with 16-bit data words.
-     * In each word, the high byte contains the leading cc of the character,
-     * and the low byte contains the trailing cc of the character.
-     * These cc's are the cc's of the first and last code points in the
-     * canonical decomposition of the character.
-     *
-     * Since all 16 bits are used for cc's, lead surrogates must be tested
-     * by checking the code unit instead of the trie data.
-     * This is done only if the 16-bit data word is not zero.
-     * If the code unit is a leading surrogate and the data word is not zero,
-     * then instead of cc's it contains the offset for the second trie lookup.
-     *
-     *
-     * - Auxiliary trie and data
-     *
-     *
-     * The auxiliary 16-bit trie contains data for additional properties.
-     * Bits
-     * 15..13   reserved
-     *     12   not NFC_Skippable (f) (formatVersion>=2.2)
-     *     11   flag: not a safe starter for canonical closure
-     *     10   composition exclusion
-     *  9.. 0   index into extraData[] to FC_NFKC_Closure string
-     *          (not for lead surrogate),
-     *          or lead surrogate offset (for lead surrogate, if 9..0 not zero)
-     *
-     * Conditions for "NF* Skippable" from Mark Davis' com.ibm.text.UCD.NFSkippable:
-     * (used in NormalizerTransliterator)
-     *
-     * A skippable character is
-     * a) unassigned, or ALL of the following:
-     * b) of combining class 0.
-     * c) not decomposed by this normalization form.
-     * AND if NFC or NFKC,
-     * d) can never compose with a previous character.
-     * e) can never compose with a following character.
-     * f) can never change if another character is added.
-     *    Example: a-breve might satisfy all but f, but if you
-     *    add an ogonek it changes to a-ogonek + breve
-     *
-     * a)..e) must be tested from norm32.
-     * Since f) is more complicated, the (not-)NFC_Skippable flag (f) is built
-     * into the auxiliary trie.
-     * The same bit is used for NFC and NFKC; (c) differs for them.
-     * As usual, we build the "not skippable" flags so that unassigned
-     * code points get a 0 bit.
-     * This bit is only valid after (a)..(e) test FALSE; test NFD_NO before (f) as well.
-     * Test Hangul LV syllables entirely in code.
-     *
-     *
-     * - FC_NFKC_Closure strings in extraData[]
-     *
-     * Strings are either stored as a single code unit or as the length
-     * followed by that many units.
-     *
-     */
-final class NormalizerDataReader implements ICUBinary.Authenticate {
-
-   /**
-    * <p>Protected constructor.</p>
-    * @param inputStream ICU uprop.dat file input stream
-    * @exception IOException throw if data file fails authentication
-    * @draft 2.1
-    */
-    protected NormalizerDataReader(InputStream inputStream)
-                                        throws IOException{
-
-        unicodeVersion = ICUBinary.readHeader(inputStream, DATA_FORMAT_ID, this);
-        dataInputStream = new DataInputStream(inputStream);
-    }
-
-    // protected methods -------------------------------------------------
-
-    protected int[] readIndexes(int length)throws IOException{
-        int[] indexes = new int[length];
-        //Read the indexes
-        for (int i = 0; i <length ; i++) {
-             indexes[i] = dataInputStream.readInt();
-        }
-        return indexes;
-    }
-    /**
-    * <p>Reads unorm.icu, parse it into blocks of data to be stored in
-    * NormalizerImpl.</P
-    * @param normBytes
-    * @param fcdBytes
-    * @param auxBytes
-    * @param extraData
-    * @param combiningTable
-    * @exception thrown when data reading fails
-    * @draft 2.1
-    */
-    protected void read(byte[] normBytes, byte[] fcdBytes, byte[] auxBytes,
-                        char[] extraData, char[] combiningTable)
-                        throws IOException{
-
-         //Read the bytes that make up the normTrie
-         dataInputStream.readFully(normBytes);
-
-         //normTrieStream= new ByteArrayInputStream(normBytes);
-
-         //Read the extra data
-         for(int i=0;i<extraData.length;i++){
-             extraData[i]=dataInputStream.readChar();
-         }
-
-         //Read the combining class table
-         for(int i=0; i<combiningTable.length; i++){
-             combiningTable[i]=dataInputStream.readChar();
-         }
-
-         //Read the fcdTrie
-         dataInputStream.readFully(fcdBytes);
-
-
-         //Read the AuxTrie
-        dataInputStream.readFully(auxBytes);
-    }
-
-    public byte[] getDataFormatVersion(){
-        return DATA_FORMAT_VERSION;
-    }
-
-    public boolean isDataVersionAcceptable(byte version[])
-    {
-        return version[0] == DATA_FORMAT_VERSION[0]
-               && version[2] == DATA_FORMAT_VERSION[2]
-               && version[3] == DATA_FORMAT_VERSION[3];
-    }
-
-    public byte[] getUnicodeVersion(){
-        return unicodeVersion;
-    }
-    // private data members -------------------------------------------------
-
-
-    /**
-    * ICU data file input stream
-    */
-    private DataInputStream dataInputStream;
-
-    private byte[] unicodeVersion;
-
-    /**
-    * File format version that this class understands.
-    * No guarantees are made if a older version is used
-    * see store.c of gennorm for more information and values
-    */
-    private static final byte DATA_FORMAT_ID[] = {(byte)0x4E, (byte)0x6F,
-                                                    (byte)0x72, (byte)0x6D};
-    private static final byte DATA_FORMAT_VERSION[] = {(byte)0x2, (byte)0x2,
-                                                        (byte)0x5, (byte)0x2};
-
-}
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/NormalizerImpl.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/NormalizerImpl.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2009, 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
@@ -22,614 +22,1898 @@
  * or visit www.oracle.com if you need additional information or have any
  * questions.
  */
+
 /*
  *******************************************************************************
- * (C) Copyright IBM Corp. and others, 1996-2009 - All Rights Reserved         *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
+ *   Copyright (C) 2009-2014, International Business Machines
+ *   Corporation and others.  All Rights Reserved.
  *******************************************************************************
  */
 
 package sun.text.normalizer;
 
-import java.io.BufferedInputStream;
-import java.io.ByteArrayInputStream;
 import java.io.IOException;
-import java.io.BufferedInputStream;
-import java.io.InputStream;
+import java.nio.ByteBuffer;
+import java.text.Normalizer;
 
-/**
- * @author  Ram Viswanadha
- */
+// Original filename in ICU4J: Normalizer2Impl.java
 public final class NormalizerImpl {
-    // Static block for the class to initialize its own self
-    static final NormalizerImpl IMPL;
+
+    public static final class Hangul {
+        /* Korean Hangul and Jamo constants */
+        public static final int JAMO_L_BASE=0x1100;     /* "lead" jamo */
+        public static final int JAMO_V_BASE=0x1161;     /* "vowel" jamo */
+        public static final int JAMO_T_BASE=0x11a7;     /* "trail" jamo */
+
+        public static final int HANGUL_BASE=0xac00;
+        public static final int HANGUL_END=0xd7a3;
+
+        public static final int JAMO_L_COUNT=19;
+        public static final int JAMO_V_COUNT=21;
+        public static final int JAMO_T_COUNT=28;
+
+        public static final int HANGUL_COUNT=JAMO_L_COUNT*JAMO_V_COUNT*JAMO_T_COUNT;
+        public static final int HANGUL_LIMIT=HANGUL_BASE+HANGUL_COUNT;
+
+        public static boolean isHangul(int c) {
+            return HANGUL_BASE<=c && c<HANGUL_LIMIT;
+        }
 
-    static
-    {
-        try
-        {
-            IMPL = new NormalizerImpl();
+        public static boolean isHangulWithoutJamoT(char c) {
+            c-=HANGUL_BASE;
+            return c<HANGUL_COUNT && c%JAMO_T_COUNT==0;
         }
-        catch (Exception e)
-        {
-            throw new RuntimeException(e.getMessage());
+
+        /**
+         * Decomposes c, which must be a Hangul syllable, into buffer
+         * and returns the length of the decomposition (2 or 3).
+         */
+        public static int decompose(int c, Appendable buffer) {
+            try {
+                c-=HANGUL_BASE;
+                int c2=c%JAMO_T_COUNT;
+                c/=JAMO_T_COUNT;
+                buffer.append((char)(JAMO_L_BASE+c/JAMO_V_COUNT));
+                buffer.append((char)(JAMO_V_BASE+c%JAMO_V_COUNT));
+                if(c2==0) {
+                    return 2;
+                } else {
+                    buffer.append((char)(JAMO_T_BASE+c2));
+                    return 3;
+                }
+            } catch(IOException e) {
+                throw new InternalError(e);
+            }
         }
     }
 
-    static final int UNSIGNED_BYTE_MASK =0xFF;
-    static final long UNSIGNED_INT_MASK = 0xffffffffL;
-    /*
-     * This new implementation of the normalization code loads its data from
-     * unorm.icu, which is generated with the gennorm tool.
-     * The format of that file is described at the end of this file.
-     */
-    private static final String DATA_FILE_NAME = "/sun/text/resources/unorm.icu";
-
-    // norm32 value constants
-
-    // quick check flags 0..3 set mean "no" for their forms
-    public static final int QC_NFC=0x11;          /* no|maybe */
-    public static final int QC_NFKC=0x22;         /* no|maybe */
-    public static final int QC_NFD=4;             /* no */
-    public static final int QC_NFKD=8;            /* no */
-
-    public static final int QC_ANY_NO=0xf;
-
-    /* quick check flags 4..5 mean "maybe" for their forms;
-     * test flags>=QC_MAYBE
+    /**
+     * Writable buffer that takes care of canonical ordering.
+     * Its Appendable methods behave like the C++ implementation's
+     * appendZeroCC() methods.
+     * <p>
+     * If dest is a StringBuilder, then the buffer writes directly to it.
+     * Otherwise, the buffer maintains a StringBuilder for intermediate text segments
+     * until no further changes are necessary and whole segments are appended.
+     * append() methods that take combining-class values always write to the StringBuilder.
+     * Other append() methods flush and append to the Appendable.
      */
-    public static final int QC_MAYBE=0x10;
-    public static final int QC_ANY_MAYBE=0x30;
-
-    public static final int QC_MASK=0x3f;
+    public static final class ReorderingBuffer implements Appendable {
+        public ReorderingBuffer(NormalizerImpl ni, Appendable dest, int destCapacity) {
+            impl=ni;
+            app=dest;
+            if (app instanceof StringBuilder) {
+                appIsStringBuilder=true;
+                str=(StringBuilder)dest;
+                // In Java, the constructor subsumes public void init(int destCapacity)
+                str.ensureCapacity(destCapacity);
+                reorderStart=0;
+                if(str.length()==0) {
+                    lastCC=0;
+                } else {
+                    setIterator();
+                    lastCC=previousCC();
+                    // Set reorderStart after the last code point with cc<=1 if there is one.
+                    if(lastCC>1) {
+                        while(previousCC()>1) {}
+                    }
+                    reorderStart=codePointLimit;
+                }
+            } else {
+                appIsStringBuilder=false;
+                str=new StringBuilder();
+                reorderStart=0;
+                lastCC=0;
+            }
+        }
 
-    private static final int COMBINES_FWD=0x40;
-    private static final int COMBINES_BACK=0x80;
-    public  static final int COMBINES_ANY=0xc0;
-    // UnicodeData.txt combining class in bits 15.
-    private static final int CC_SHIFT=8;
-    public  static final int CC_MASK=0xff00;
-    // 16 bits for the index to UChars and other extra data
-    private static final int EXTRA_SHIFT=16;
+        public boolean isEmpty() { return str.length()==0; }
+        public int length() { return str.length(); }
+        public int getLastCC() { return lastCC; }
+
+        public StringBuilder getStringBuilder() { return str; }
+
+        public boolean equals(CharSequence s, int start, int limit) {
+            return UTF16Plus.equal(str, 0, str.length(), s, start, limit);
+        }
 
-    /* norm32 value constants using >16 bits */
-    private static final long  MIN_SPECIAL    =  0xfc000000 & UNSIGNED_INT_MASK;
-    private static final long  SURROGATES_TOP =  0xfff00000 & UNSIGNED_INT_MASK;
-    private static final long  MIN_HANGUL     =  0xfff00000 & UNSIGNED_INT_MASK;
-//  private static final long  MIN_JAMO_V     =  0xfff20000 & UNSIGNED_INT_MASK;
-    private static final long  JAMO_V_TOP     =  0xfff30000 & UNSIGNED_INT_MASK;
+        // For Hangul composition, replacing the Leading consonant Jamo with the syllable.
+        public void setLastChar(char c) {
+            str.setCharAt(str.length()-1, c);
+        }
 
+        public void append(int c, int cc) {
+            if(lastCC<=cc || cc==0) {
+                str.appendCodePoint(c);
+                lastCC=cc;
+                if(cc<=1) {
+                    reorderStart=str.length();
+                }
+            } else {
+                insert(c, cc);
+            }
+        }
 
-    /* indexes[] value names */
-    /* number of bytes in normalization trie */
-    static final int INDEX_TRIE_SIZE           = 0;
-    /* number of chars in extra data */
-    static final int INDEX_CHAR_COUNT           = 1;
-    /* number of uint16_t words for combining data */
-    static final int INDEX_COMBINE_DATA_COUNT = 2;
-    /* first code point with quick check NFC NO/MAYBE */
-    public static final int INDEX_MIN_NFC_NO_MAYBE   = 6;
-    /* first code point with quick check NFKC NO/MAYBE */
-    public static final int INDEX_MIN_NFKC_NO_MAYBE  = 7;
-    /* first code point with quick check NFD NO/MAYBE */
-    public static final int INDEX_MIN_NFD_NO_MAYBE   = 8;
-    /* first code point with quick check NFKD NO/MAYBE */
-    public static final int INDEX_MIN_NFKD_NO_MAYBE  = 9;
-    /* number of bytes in FCD trie */
-    static final int INDEX_FCD_TRIE_SIZE      = 10;
-    /* number of bytes in the auxiliary trie */
-    static final int INDEX_AUX_TRIE_SIZE      = 11;
-    /* changing this requires a new formatVersion */
-    static final int INDEX_TOP                = 32;
-
+        // s must be in NFD, otherwise change the implementation.
+        public void append(CharSequence s, int start, int limit,
+                           int leadCC, int trailCC) {
+            if(start==limit) {
+                return;
+            }
+            if(lastCC<=leadCC || leadCC==0) {
+                if(trailCC<=1) {
+                    reorderStart=str.length()+(limit-start);
+                } else if(leadCC<=1) {
+                    reorderStart=str.length()+1;  // Ok if not a code point boundary.
+                }
+                str.append(s, start, limit);
+                lastCC=trailCC;
+            } else {
+                int c=Character.codePointAt(s, start);
+                start+=Character.charCount(c);
+                insert(c, leadCC);  // insert first code point
+                while(start<limit) {
+                    c=Character.codePointAt(s, start);
+                    start+=Character.charCount(c);
+                    if(start<limit) {
+                        // s must be in NFD, otherwise we need to use getCC().
+                        leadCC=getCCFromYesOrMaybe(impl.getNorm16(c));
+                    } else {
+                        leadCC=trailCC;
+                    }
+                    append(c, leadCC);
+                }
+            }
+        }
 
-    /* AUX constants */
-    /* value constants for auxTrie */
-    private static final int AUX_UNSAFE_SHIFT           = 11;
-    private static final int AUX_COMP_EX_SHIFT           = 10;
-    private static final int AUX_NFC_SKIPPABLE_F_SHIFT = 12;
+        // The following append() methods work like C++ appendZeroCC().
+        // They assume that the cc or trailCC of their input is 0.
+        // Most of them implement Appendable interface methods.
+        // @Override when we switch to Java 6
+        public ReorderingBuffer append(char c) {
+            str.append(c);
+            lastCC=0;
+            reorderStart=str.length();
+            return this;
+        }
 
-    private static final int AUX_MAX_FNC          =   1<<AUX_COMP_EX_SHIFT;
-    private static final int AUX_UNSAFE_MASK      =   (int)((1<<AUX_UNSAFE_SHIFT) & UNSIGNED_INT_MASK);
-    private static final int AUX_FNC_MASK         =   (int)((AUX_MAX_FNC-1) & UNSIGNED_INT_MASK);
-    private static final int AUX_COMP_EX_MASK     =   (int)((1<<AUX_COMP_EX_SHIFT) & UNSIGNED_INT_MASK);
-    private static final long AUX_NFC_SKIP_F_MASK =   ((UNSIGNED_INT_MASK&1)<<AUX_NFC_SKIPPABLE_F_SHIFT);
-
-    private static final int MAX_BUFFER_SIZE                    = 20;
-
-    /*******************************/
+        public void appendZeroCC(int c) {
+            str.appendCodePoint(c);
+            lastCC=0;
+            reorderStart=str.length();
+        }
 
-    /* Wrappers for Trie implementations */
-    static final class NormTrieImpl implements Trie.DataManipulate{
-        static IntTrie normTrie= null;
-       /**
-        * Called by com.ibm.icu.util.Trie to extract from a lead surrogate's
-        * data the index array offset of the indexes for that lead surrogate.
-        * @param property data value for a surrogate from the trie, including
-        *         the folding offset
-        * @return data offset or 0 if there is no data for the lead surrogate
-        */
-        /* normTrie: 32-bit trie result may contain a special extraData index with the folding offset */
-        public int getFoldingOffset(int value){
-            return  BMP_INDEX_LENGTH+
-                    ((value>>(EXTRA_SHIFT-SURROGATE_BLOCK_BITS))&
-                    (0x3ff<<SURROGATE_BLOCK_BITS));
+        // @Override when we switch to Java 6
+        public ReorderingBuffer append(CharSequence s) {
+            if(s.length()!=0) {
+                str.append(s);
+                lastCC=0;
+                reorderStart=str.length();
+            }
+            return this;
+        }
+
+        // @Override when we switch to Java 6
+        public ReorderingBuffer append(CharSequence s, int start, int limit) {
+            if(start!=limit) {
+                str.append(s, start, limit);
+                lastCC=0;
+                reorderStart=str.length();
+            }
+            return this;
         }
 
+        /**
+         * Flushes from the intermediate StringBuilder to the Appendable,
+         * if they are different objects.
+         * Used after recomposition.
+         * Must be called at the end when writing to a non-StringBuilder Appendable.
+         */
+        public void flush() {
+            if(appIsStringBuilder) {
+                reorderStart=str.length();
+            } else {
+                try {
+                    app.append(str);
+                    str.setLength(0);
+                    reorderStart=0;
+                } catch(IOException e) {
+                    throw new InternalError(e);  // Avoid declaring "throws IOException".
+                }
+            }
+            lastCC=0;
+        }
+
+        /**
+         * Flushes from the intermediate StringBuilder to the Appendable,
+         * if they are different objects.
+         * Then appends the new text to the Appendable or StringBuilder.
+         * Normally used after quick check loops find a non-empty sequence.
+         */
+        public ReorderingBuffer flushAndAppendZeroCC(CharSequence s, int start, int limit) {
+            if(appIsStringBuilder) {
+                str.append(s, start, limit);
+                reorderStart=str.length();
+            } else {
+                try {
+                    app.append(str).append(s, start, limit);
+                    str.setLength(0);
+                    reorderStart=0;
+                } catch(IOException e) {
+                    throw new InternalError(e);  // Avoid declaring "throws IOException".
+                }
+            }
+            lastCC=0;
+            return this;
+        }
+
+        public void remove() {
+            str.setLength(0);
+            lastCC=0;
+            reorderStart=0;
+        }
+
+        public void removeSuffix(int suffixLength) {
+            int oldLength=str.length();
+            str.delete(oldLength-suffixLength, oldLength);
+            lastCC=0;
+            reorderStart=str.length();
+        }
+
+        // Inserts c somewhere before the last character.
+        // Requires 0<cc<lastCC which implies reorderStart<limit.
+        private void insert(int c, int cc) {
+            for(setIterator(), skipPrevious(); previousCC()>cc;) {}
+            // insert c at codePointLimit, after the character with prevCC<=cc
+            if(c<=0xffff) {
+                str.insert(codePointLimit, (char)c);
+                if(cc<=1) {
+                    reorderStart=codePointLimit+1;
+                }
+            } else {
+                str.insert(codePointLimit, Character.toChars(c));
+                if(cc<=1) {
+                    reorderStart=codePointLimit+2;
+                }
+            }
+        }
+
+        private final NormalizerImpl impl;
+        private final Appendable app;
+        private final StringBuilder str;
+        private final boolean appIsStringBuilder;
+        private int reorderStart;
+        private int lastCC;
+
+        // private backward iterator
+        private void setIterator() { codePointStart=str.length(); }
+        private void skipPrevious() {  // Requires 0<codePointStart.
+            codePointLimit=codePointStart;
+            codePointStart=str.offsetByCodePoints(codePointStart, -1);
+        }
+        private int previousCC() {  // Returns 0 if there is no previous character.
+            codePointLimit=codePointStart;
+            if(reorderStart>=codePointStart) {
+                return 0;
+            }
+            int c=str.codePointBefore(codePointStart);
+            codePointStart-=Character.charCount(c);
+            if(c<MIN_CCC_LCCC_CP) {
+                return 0;
+            }
+            return getCCFromYesOrMaybe(impl.getNorm16(c));
+        }
+
+        private int codePointStart, codePointLimit;
     }
-    static final class FCDTrieImpl implements Trie.DataManipulate{
-        static CharTrie fcdTrie=null;
-       /**
-        * Called by com.ibm.icu.util.Trie to extract from a lead surrogate's
-        * data the index array offset of the indexes for that lead surrogate.
-        * @param property data value for a surrogate from the trie, including
-        *         the folding offset
-        * @return data offset or 0 if there is no data for the lead surrogate
-        */
-        /* fcdTrie: the folding offset is the lead FCD value itself */
-        public int getFoldingOffset(int value){
-            return value;
+
+    // TODO: Propose as public API on the UTF16 class.
+    // TODO: Propose widening UTF16 methods that take char to take int.
+    // TODO: Propose widening UTF16 methods that take String to take CharSequence.
+    public static final class UTF16Plus {
+        /**
+         * Assuming c is a surrogate code point (UTF16.isSurrogate(c)),
+         * is it a lead surrogate?
+         * @param c code unit or code point
+         * @return true or false
+         */
+        public static boolean isSurrogateLead(int c) { return (c&0x400)==0; }
+
+        /**
+         * Compares two CharSequence subsequences for binary equality.
+         * @param s1 first sequence
+         * @param start1 start offset in first sequence
+         * @param limit1 limit offset in first sequence
+         * @param s2 second sequence
+         * @param start2 start offset in second sequence
+         * @param limit2 limit offset in second sequence
+         * @return true if s1.subSequence(start1, limit1) contains the same text
+         *              as s2.subSequence(start2, limit2)
+         */
+        public static boolean equal(CharSequence s1, int start1, int limit1,
+                                    CharSequence s2, int start2, int limit2) {
+            if((limit1-start1)!=(limit2-start2)) {
+                return false;
+            }
+            if(s1==s2 && start1==start2) {
+                return true;
+            }
+            while(start1<limit1) {
+                if(s1.charAt(start1++)!=s2.charAt(start2++)) {
+                    return false;
+                }
+            }
+            return true;
         }
     }
 
-    static final class AuxTrieImpl implements Trie.DataManipulate{
-        static CharTrie auxTrie = null;
-       /**
-        * Called by com.ibm.icu.util.Trie to extract from a lead surrogate's
-        * data the index array offset of the indexes for that lead surrogate.
-        * @param property data value for a surrogate from the trie, including
-        *        the folding offset
-        * @return data offset or 0 if there is no data for the lead surrogate
-        */
-        /* auxTrie: the folding offset is in bits 9..0 of the 16-bit trie result */
-        public int getFoldingOffset(int value){
-            return (value &AUX_FNC_MASK)<<SURROGATE_BLOCK_BITS;
+    public NormalizerImpl() {}
+
+    private static final class IsAcceptable implements ICUBinary.Authenticate {
+        // @Override when we switch to Java 6
+        public boolean isDataVersionAcceptable(byte version[]) {
+            return version[0]==2;
+        }
+    }
+
+    private static final IsAcceptable IS_ACCEPTABLE = new IsAcceptable();
+    private static final int DATA_FORMAT = 0x4e726d32;  // "Nrm2"
+
+    public NormalizerImpl load(ByteBuffer bytes) {
+        try {
+            dataVersion=ICUBinary.readHeaderAndDataVersion(bytes, DATA_FORMAT, IS_ACCEPTABLE);
+            int indexesLength=bytes.getInt()/4;  // inIndexes[IX_NORM_TRIE_OFFSET]/4
+            if(indexesLength<=IX_MIN_MAYBE_YES) {
+                throw new IOException("Normalizer2 data: not enough indexes");
+            }
+            int[] inIndexes=new int[indexesLength];
+            inIndexes[0]=indexesLength*4;
+            for(int i=1; i<indexesLength; ++i) {
+                inIndexes[i]=bytes.getInt();
+            }
+
+            minDecompNoCP=inIndexes[IX_MIN_DECOMP_NO_CP];
+            minCompNoMaybeCP=inIndexes[IX_MIN_COMP_NO_MAYBE_CP];
+
+            minYesNo=inIndexes[IX_MIN_YES_NO];
+            minYesNoMappingsOnly=inIndexes[IX_MIN_YES_NO_MAPPINGS_ONLY];
+            minNoNo=inIndexes[IX_MIN_NO_NO];
+            limitNoNo=inIndexes[IX_LIMIT_NO_NO];
+            minMaybeYes=inIndexes[IX_MIN_MAYBE_YES];
+
+            // Read the normTrie.
+            int offset=inIndexes[IX_NORM_TRIE_OFFSET];
+            int nextOffset=inIndexes[IX_EXTRA_DATA_OFFSET];
+            normTrie=Trie2_16.createFromSerialized(bytes);
+            int trieLength=normTrie.getSerializedLength();
+            if(trieLength>(nextOffset-offset)) {
+                throw new IOException("Normalizer2 data: not enough bytes for normTrie");
+            }
+            ICUBinary.skipBytes(bytes, (nextOffset-offset)-trieLength);  // skip padding after trie bytes
+
+            // Read the composition and mapping data.
+            offset=nextOffset;
+            nextOffset=inIndexes[IX_SMALL_FCD_OFFSET];
+            int numChars=(nextOffset-offset)/2;
+            char[] chars;
+            if(numChars!=0) {
+                chars=new char[numChars];
+                for(int i=0; i<numChars; ++i) {
+                    chars[i]=bytes.getChar();
+                }
+                maybeYesCompositions=new String(chars);
+                extraData=maybeYesCompositions.substring(MIN_NORMAL_MAYBE_YES-minMaybeYes);
+            }
+
+            // smallFCD: new in formatVersion 2
+            offset=nextOffset;
+            smallFCD=new byte[0x100];
+            for(int i=0; i<0x100; ++i) {
+                smallFCD[i]=bytes.get();
+            }
+
+            // Build tccc180[].
+            // gennorm2 enforces lccc=0 for c<MIN_CCC_LCCC_CP=U+0300.
+            tccc180=new int[0x180];
+            int bits=0;
+            for(int c=0; c<0x180; bits>>=1) {
+                if((c&0xff)==0) {
+                    bits=smallFCD[c>>8];  // one byte per 0x100 code points
+                }
+                if((bits&1)!=0) {
+                    for(int i=0; i<0x20; ++i, ++c) {
+                        tccc180[c]=getFCD16FromNormData(c)&0xff;
+                    }
+                } else {
+                    c+=0x20;
+                }
+            }
+
+            return this;
+        } catch(IOException e) {
+            throw new InternalError(e);
+        }
+    }
+
+    public NormalizerImpl load(String name) {
+        return load(ICUBinary.getRequiredData(name));
+    }
+
+    public int getNorm16(int c) {
+        return normTrie.get(c);
+    }
+
+    public boolean isDecompYes(int norm16) { return norm16<minYesNo || minMaybeYes<=norm16; }
+
+    public int getCC(int norm16) {
+        if(norm16>=MIN_NORMAL_MAYBE_YES) {
+            return norm16&0xff;
+        }
+        if(norm16<minNoNo || limitNoNo<=norm16) {
+            return 0;
+        }
+        return getCCFromNoNo(norm16);
+    }
+
+    public static int getCCFromYesOrMaybe(int norm16) {
+        return norm16>=MIN_NORMAL_MAYBE_YES ? norm16&0xff : 0;
+    }
+
+    /**
+     * Returns the FCD data for code point c.
+     * @param c A Unicode code point.
+     * @return The lccc(c) in bits 15..8 and tccc(c) in bits 7..0.
+     */
+    public int getFCD16(int c) {
+        if(c<0) {
+            return 0;
+        } else if(c<0x180) {
+            return tccc180[c];
+        } else if(c<=0xffff) {
+            if(!singleLeadMightHaveNonZeroFCD16(c)) { return 0; }
+        }
+        return getFCD16FromNormData(c);
+    }
+
+    /** Returns the FCD data for U+0000<=c<U+0180. */
+    public int getFCD16FromBelow180(int c) { return tccc180[c]; }
+    /** Returns true if the single-or-lead code unit c might have non-zero FCD data. */
+    public boolean singleLeadMightHaveNonZeroFCD16(int lead) {
+        // 0<=lead<=0xffff
+        byte bits=smallFCD[lead>>8];
+        if(bits==0) { return false; }
+        return ((bits>>((lead>>5)&7))&1)!=0;
+    }
+
+    /** Gets the FCD value from the regular normalization data. */
+    public int getFCD16FromNormData(int c) {
+        // Only loops for 1:1 algorithmic mappings.
+        for(;;) {
+            int norm16=getNorm16(c);
+            if(norm16<=minYesNo) {
+                // no decomposition or Hangul syllable, all zeros
+                return 0;
+            } else if(norm16>=MIN_NORMAL_MAYBE_YES) {
+                // combining mark
+                norm16&=0xff;
+                return norm16|(norm16<<8);
+            } else if(norm16>=minMaybeYes) {
+                return 0;
+            } else if(isDecompNoAlgorithmic(norm16)) {
+                c=mapAlgorithmic(c, norm16);
+            } else {
+                // c decomposes, get everything from the variable-length extra data
+                int firstUnit=extraData.charAt(norm16);
+                if((firstUnit&MAPPING_LENGTH_MASK)==0) {
+                    // A character that is deleted (maps to an empty string) must
+                    // get the worst-case lccc and tccc values because arbitrary
+                    // characters on both sides will become adjacent.
+                    return 0x1ff;
+                } else {
+                    int fcd16=firstUnit>>8;  // tccc
+                    if((firstUnit&MAPPING_HAS_CCC_LCCC_WORD)!=0) {
+                        fcd16|=extraData.charAt(norm16-1)&0xff00;  // lccc
+                    }
+                    return fcd16;
+                }
+            }
+        }
+    }
+
+    /**
+     * Gets the decomposition for one code point.
+     * @param c code point
+     * @return c's decomposition, if it has one; returns null if it does not have a decomposition
+     */
+    public String getDecomposition(int c) {
+        int decomp=-1;
+        int norm16;
+        for(;;) {
+            if(c<minDecompNoCP || isDecompYes(norm16=getNorm16(c))) {
+                // c does not decompose
+            } else if(isHangul(norm16)) {
+                // Hangul syllable: decompose algorithmically
+                StringBuilder buffer=new StringBuilder();
+                Hangul.decompose(c, buffer);
+                return buffer.toString();
+            } else if(isDecompNoAlgorithmic(norm16)) {
+                decomp=c=mapAlgorithmic(c, norm16);
+                continue;
+            } else {
+                // c decomposes, get everything from the variable-length extra data
+                int length=extraData.charAt(norm16++)&MAPPING_LENGTH_MASK;
+                return extraData.substring(norm16, norm16+length);
+            }
+            if(decomp<0) {
+                return null;
+            } else {
+                return UTF16.valueOf(decomp);
+            }
         }
     }
 
-    /****************************************************/
+    public static final int MIN_CCC_LCCC_CP=0x300;
 
+    public static final int MIN_YES_YES_WITH_CC=0xff01;
+    public static final int JAMO_VT=0xff00;
+    public static final int MIN_NORMAL_MAYBE_YES=0xfe00;
+    public static final int MAX_DELTA=0x40;
 
-    private static FCDTrieImpl fcdTrieImpl;
-    private static NormTrieImpl normTrieImpl;
-    private static AuxTrieImpl auxTrieImpl;
-    private static int[] indexes;
-    private static char[] combiningTable;
-    private static char[] extraData;
+    // Byte offsets from the start of the data, after the generic header.
+    public static final int IX_NORM_TRIE_OFFSET=0;
+    public static final int IX_EXTRA_DATA_OFFSET=1;
+    public static final int IX_SMALL_FCD_OFFSET=2;
+
+    // Code point thresholds for quick check codes.
+    public static final int IX_MIN_DECOMP_NO_CP=8;
+    public static final int IX_MIN_COMP_NO_MAYBE_CP=9;
 
-    private static boolean isDataLoaded;
-    private static boolean isFormatVersion_2_1;
-    private static boolean isFormatVersion_2_2;
-    private static byte[] unicodeVersion;
+    // Norm16 value thresholds for quick check combinations and types of extra data.
+    // Mappings & compositions in [minYesNo..minYesNoMappingsOnly[.
+    public static final int IX_MIN_YES_NO=10;
+    public static final int IX_MIN_NO_NO=11;
+    public static final int IX_LIMIT_NO_NO=12;
+    public static final int IX_MIN_MAYBE_YES=13;
+
+    // Mappings only in [minYesNoMappingsOnly..minNoNo[.
+    public static final int IX_MIN_YES_NO_MAPPINGS_ONLY=14;
 
-    /**
-     * Default buffer size of datafile
-     */
-    private static final int DATA_BUFFER_SIZE = 25000;
+    public static final int MAPPING_HAS_CCC_LCCC_WORD=0x80;
+    public static final int MAPPING_LENGTH_MASK=0x1f;
 
-    /**
-     * FCD check: everything below this code point is known to have a 0
-     * lead combining class
-     */
-    public static final int MIN_WITH_LEAD_CC=0x300;
+    public static final int COMP_1_LAST_TUPLE=0x8000;
+    public static final int COMP_1_TRIPLE=1;
+    public static final int COMP_1_TRAIL_LIMIT=0x3400;
+    public static final int COMP_1_TRAIL_MASK=0x7ffe;
+    public static final int COMP_1_TRAIL_SHIFT=9;  // 10-1 for the "triple" bit
+    public static final int COMP_2_TRAIL_SHIFT=6;
+    public static final int COMP_2_TRAIL_MASK=0xffc0;
 
+    // higher-level functionality ------------------------------------------ ***
 
     /**
-     * Bit 7 of the length byte for a decomposition string in extra data is
-     * a flag indicating whether the decomposition string is
-     * preceded by a 16-bit word with the leading and trailing cc
-     * of the decomposition (like for A-umlaut);
-     * if not, then both cc's are zero (like for compatibility ideographs).
+     * Decomposes s[src, limit[ and writes the result to dest.
+     * limit can be NULL if src is NUL-terminated.
+     * destLengthEstimate is the initial dest buffer capacity and can be -1.
      */
-    private static final int DECOMP_FLAG_LENGTH_HAS_CC=0x80;
-    /**
-     * Bits 6..0 of the length byte contain the actual length.
-     */
-    private static final int DECOMP_LENGTH_MASK=0x7f;
+    public void decompose(CharSequence s, int src, int limit, StringBuilder dest,
+                   int destLengthEstimate) {
+        if(destLengthEstimate<0) {
+            destLengthEstimate=limit-src;
+        }
+        dest.setLength(0);
+        ReorderingBuffer buffer=new ReorderingBuffer(this, dest, destLengthEstimate);
+        decompose(s, src, limit, buffer);
+    }
+
+    // Dual functionality:
+    // buffer!=NULL: normalize
+    // buffer==NULL: isNormalized/quickCheck/spanQuickCheckYes
+    public int decompose(CharSequence s, int src, int limit,
+                         ReorderingBuffer buffer) {
+        int minNoCP=minDecompNoCP;
+
+        int prevSrc;
+        int c=0;
+        int norm16=0;
+
+        // only for quick check
+        int prevBoundary=src;
+        int prevCC=0;
+
+        for(;;) {
+            // count code units below the minimum or with irrelevant data for the quick check
+            for(prevSrc=src; src!=limit;) {
+                if( (c=s.charAt(src))<minNoCP ||
+                    isMostDecompYesAndZeroCC(norm16=normTrie.getFromU16SingleLead((char)c))
+                ) {
+                    ++src;
+                } else if(!UTF16.isSurrogate((char)c)) {
+                    break;
+                } else {
+                    char c2;
+                    if(UTF16Plus.isSurrogateLead(c)) {
+                        if((src+1)!=limit && Character.isLowSurrogate(c2=s.charAt(src+1))) {
+                            c=Character.toCodePoint((char)c, c2);
+                        }
+                    } else /* trail surrogate */ {
+                        if(prevSrc<src && Character.isHighSurrogate(c2=s.charAt(src-1))) {
+                            --src;
+                            c=Character.toCodePoint(c2, (char)c);
+                        }
+                    }
+                    if(isMostDecompYesAndZeroCC(norm16=getNorm16(c))) {
+                        src+=Character.charCount(c);
+                    } else {
+                        break;
+                    }
+                }
+            }
+            // copy these code units all at once
+            if(src!=prevSrc) {
+                if(buffer!=null) {
+                    buffer.flushAndAppendZeroCC(s, prevSrc, src);
+                } else {
+                    prevCC=0;
+                    prevBoundary=src;
+                }
+            }
+            if(src==limit) {
+                break;
+            }
+
+            // Check one above-minimum, relevant code point.
+            src+=Character.charCount(c);
+            if(buffer!=null) {
+                decompose(c, norm16, buffer);
+            } else {
+                if(isDecompYes(norm16)) {
+                    int cc=getCCFromYesOrMaybe(norm16);
+                    if(prevCC<=cc || cc==0) {
+                        prevCC=cc;
+                        if(cc<=1) {
+                            prevBoundary=src;
+                        }
+                        continue;
+                    }
+                }
+                return prevBoundary;  // "no" or cc out of order
+            }
+        }
+        return src;
+    }
+
+    public void decomposeAndAppend(CharSequence s, boolean doDecompose, ReorderingBuffer buffer) {
+        int limit=s.length();
+        if(limit==0) {
+            return;
+        }
+        if(doDecompose) {
+            decompose(s, 0, limit, buffer);
+            return;
+        }
+        // Just merge the strings at the boundary.
+        int c=Character.codePointAt(s, 0);
+        int src=0;
+        int firstCC, prevCC, cc;
+        firstCC=prevCC=cc=getCC(getNorm16(c));
+        while(cc!=0) {
+            prevCC=cc;
+            src+=Character.charCount(c);
+            if(src>=limit) {
+                break;
+            }
+            c=Character.codePointAt(s, src);
+            cc=getCC(getNorm16(c));
+        };
+        buffer.append(s, 0, src, firstCC, prevCC);
+        buffer.append(s, src, limit);
+    }
+
+    // Very similar to composeQuickCheck(): Make the same changes in both places if relevant.
+    // doCompose: normalize
+    // !doCompose: isNormalized (buffer must be empty and initialized)
+    public boolean compose(CharSequence s, int src, int limit,
+                           boolean onlyContiguous,
+                           boolean doCompose,
+                           ReorderingBuffer buffer) {
+        int minNoMaybeCP=minCompNoMaybeCP;
+
+        /*
+         * prevBoundary points to the last character before the current one
+         * that has a composition boundary before it with ccc==0 and quick check "yes".
+         * Keeping track of prevBoundary saves us looking for a composition boundary
+         * when we find a "no" or "maybe".
+         *
+         * When we back out from prevSrc back to prevBoundary,
+         * then we also remove those same characters (which had been simply copied
+         * or canonically-order-inserted) from the ReorderingBuffer.
+         * Therefore, at all times, the [prevBoundary..prevSrc[ source units
+         * must correspond 1:1 to destination units at the end of the destination buffer.
+         */
+        int prevBoundary=src;
+        int prevSrc;
+        int c=0;
+        int norm16=0;
+
+        // only for isNormalized
+        int prevCC=0;
 
-    /** Length of the BMP portion of the index (stage 1) array. */
-    private static final int BMP_INDEX_LENGTH=0x10000>>Trie.INDEX_STAGE_1_SHIFT_;
-    /** Number of bits of a trail surrogate that are used in index table
-     * lookups.
-     */
-    private static final int SURROGATE_BLOCK_BITS=10-Trie.INDEX_STAGE_1_SHIFT_;
+        for(;;) {
+            // count code units below the minimum or with irrelevant data for the quick check
+            for(prevSrc=src; src!=limit;) {
+                if( (c=s.charAt(src))<minNoMaybeCP ||
+                    isCompYesAndZeroCC(norm16=normTrie.getFromU16SingleLead((char)c))
+                ) {
+                    ++src;
+                } else if(!UTF16.isSurrogate((char)c)) {
+                    break;
+                } else {
+                    char c2;
+                    if(UTF16Plus.isSurrogateLead(c)) {
+                        if((src+1)!=limit && Character.isLowSurrogate(c2=s.charAt(src+1))) {
+                            c=Character.toCodePoint((char)c, c2);
+                        }
+                    } else /* trail surrogate */ {
+                        if(prevSrc<src && Character.isHighSurrogate(c2=s.charAt(src-1))) {
+                            --src;
+                            c=Character.toCodePoint(c2, (char)c);
+                        }
+                    }
+                    if(isCompYesAndZeroCC(norm16=getNorm16(c))) {
+                        src+=Character.charCount(c);
+                    } else {
+                        break;
+                    }
+                }
+            }
+            // copy these code units all at once
+            if(src!=prevSrc) {
+                if(src==limit) {
+                    if(doCompose) {
+                        buffer.flushAndAppendZeroCC(s, prevSrc, src);
+                    }
+                    break;
+                }
+                // Set prevBoundary to the last character in the quick check loop.
+                prevBoundary=src-1;
+                if( Character.isLowSurrogate(s.charAt(prevBoundary)) && prevSrc<prevBoundary &&
+                    Character.isHighSurrogate(s.charAt(prevBoundary-1))
+                ) {
+                    --prevBoundary;
+                }
+                if(doCompose) {
+                    // The last "quick check yes" character is excluded from the
+                    // flush-and-append call in case it needs to be modified.
+                    buffer.flushAndAppendZeroCC(s, prevSrc, prevBoundary);
+                    buffer.append(s, prevBoundary, src);
+                } else {
+                    prevCC=0;
+                }
+                // The start of the current character (c).
+                prevSrc=src;
+            } else if(src==limit) {
+                break;
+            }
 
+            src+=Character.charCount(c);
+            /*
+             * isCompYesAndZeroCC(norm16) is false, that is, norm16>=minNoNo.
+             * c is either a "noNo" (has a mapping) or a "maybeYes" (combines backward)
+             * or has ccc!=0.
+             * Check for Jamo V/T, then for regular characters.
+             * c is not a Hangul syllable or Jamo L because those have "yes" properties.
+             */
+            if(isJamoVT(norm16) && prevBoundary!=prevSrc) {
+                char prev=s.charAt(prevSrc-1);
+                boolean needToDecompose=false;
+                if(c<Hangul.JAMO_T_BASE) {
+                    // c is a Jamo Vowel, compose with previous Jamo L and following Jamo T.
+                    prev-=Hangul.JAMO_L_BASE;
+                    if(prev<Hangul.JAMO_L_COUNT) {
+                        if(!doCompose) {
+                            return false;
+                        }
+                        char syllable=(char)
+                            (Hangul.HANGUL_BASE+
+                             (prev*Hangul.JAMO_V_COUNT+(c-Hangul.JAMO_V_BASE))*
+                             Hangul.JAMO_T_COUNT);
+                        char t;
+                        if(src!=limit && (t=(char)(s.charAt(src)-Hangul.JAMO_T_BASE))<Hangul.JAMO_T_COUNT) {
+                            ++src;
+                            syllable+=t;  // The next character was a Jamo T.
+                            prevBoundary=src;
+                            buffer.setLastChar(syllable);
+                            continue;
+                        }
+                        // If we see L+V+x where x!=T then we drop to the slow path,
+                        // decompose and recompose.
+                        // This is to deal with NFKC finding normal L and V but a
+                        // compatibility variant of a T. We need to either fully compose that
+                        // combination here (which would complicate the code and may not work
+                        // with strange custom data) or use the slow path -- or else our replacing
+                        // two input characters (L+V) with one output character (LV syllable)
+                        // would violate the invariant that [prevBoundary..prevSrc[ has the same
+                        // length as what we appended to the buffer since prevBoundary.
+                        needToDecompose=true;
+                    }
+                } else if(Hangul.isHangulWithoutJamoT(prev)) {
+                    // c is a Jamo Trailing consonant,
+                    // compose with previous Hangul LV that does not contain a Jamo T.
+                    if(!doCompose) {
+                        return false;
+                    }
+                    buffer.setLastChar((char)(prev+c-Hangul.JAMO_T_BASE));
+                    prevBoundary=src;
+                    continue;
+                }
+                if(!needToDecompose) {
+                    // The Jamo V/T did not compose into a Hangul syllable.
+                    if(doCompose) {
+                        buffer.append((char)c);
+                    } else {
+                        prevCC=0;
+                    }
+                    continue;
+                }
+            }
+            /*
+             * Source buffer pointers:
+             *
+             *  all done      quick check   current char  not yet
+             *                "yes" but     (c)           processed
+             *                may combine
+             *                forward
+             * [-------------[-------------[-------------[-------------[
+             * |             |             |             |             |
+             * orig. src     prevBoundary  prevSrc       src           limit
+             *
+             *
+             * Destination buffer pointers inside the ReorderingBuffer:
+             *
+             *  all done      might take    not filled yet
+             *                characters for
+             *                reordering
+             * [-------------[-------------[-------------[
+             * |             |             |             |
+             * start         reorderStart  limit         |
+             *                             +remainingCap.+
+             */
+            if(norm16>=MIN_YES_YES_WITH_CC) {
+                int cc=norm16&0xff;  // cc!=0
+                if( onlyContiguous &&  // FCC
+                    (doCompose ? buffer.getLastCC() : prevCC)==0 &&
+                    prevBoundary<prevSrc &&
+                    // buffer.getLastCC()==0 && prevBoundary<prevSrc tell us that
+                    // [prevBoundary..prevSrc[ (which is exactly one character under these conditions)
+                    // passed the quick check "yes && ccc==0" test.
+                    // Check whether the last character was a "yesYes" or a "yesNo".
+                    // If a "yesNo", then we get its trailing ccc from its
+                    // mapping and check for canonical order.
+                    // All other cases are ok.
+                    getTrailCCFromCompYesAndZeroCC(s, prevBoundary, prevSrc)>cc
+                ) {
+                    // Fails FCD test, need to decompose and contiguously recompose.
+                    if(!doCompose) {
+                        return false;
+                    }
+                } else if(doCompose) {
+                    buffer.append(c, cc);
+                    continue;
+                } else if(prevCC<=cc) {
+                    prevCC=cc;
+                    continue;
+                } else {
+                    return false;
+                }
+            } else if(!doCompose && !isMaybeOrNonZeroCC(norm16)) {
+                return false;
+            }
 
-   // public utility
-   public static int getFromIndexesArr(int index){
-        return indexes[index];
-   }
+            /*
+             * Find appropriate boundaries around this character,
+             * decompose the source text from between the boundaries,
+             * and recompose it.
+             *
+             * We may need to remove the last few characters from the ReorderingBuffer
+             * to account for source text that was copied or appended
+             * but needs to take part in the recomposition.
+             */
+
+            /*
+             * Find the last composition boundary in [prevBoundary..src[.
+             * It is either the decomposition of the current character (at prevSrc),
+             * or prevBoundary.
+             */
+            if(hasCompBoundaryBefore(c, norm16)) {
+                prevBoundary=prevSrc;
+            } else if(doCompose) {
+                buffer.removeSuffix(prevSrc-prevBoundary);
+            }
 
-   // protected constructor ---------------------------------------------
+            // Find the next composition boundary in [src..limit[ -
+            // modifies src to point to the next starter.
+            src=findNextCompBoundary(s, src, limit);
+
+            // Decompose [prevBoundary..src[ into the buffer and then recompose that part of it.
+            int recomposeStartIndex=buffer.length();
+            decomposeShort(s, prevBoundary, src, buffer);
+            recompose(buffer, recomposeStartIndex, onlyContiguous);
+            if(!doCompose) {
+                if(!buffer.equals(s, prevBoundary, src)) {
+                    return false;
+                }
+                buffer.remove();
+                prevCC=0;
+            }
+
+            // Move to the next starter. We never need to look back before this point again.
+            prevBoundary=src;
+        }
+        return true;
+    }
 
     /**
-    * Constructor
-    * @exception thrown when data reading fails or data corrupted
-    */
-    private NormalizerImpl() throws IOException {
-        //data should be loaded only once
-        if(!isDataLoaded){
-
-            // jar access
-            InputStream i = ICUData.getRequiredStream(DATA_FILE_NAME);
-            BufferedInputStream b = new BufferedInputStream(i,DATA_BUFFER_SIZE);
-            NormalizerDataReader reader = new NormalizerDataReader(b);
+     * Very similar to compose(): Make the same changes in both places if relevant.
+     * doSpan: spanQuickCheckYes (ignore bit 0 of the return value)
+     * !doSpan: quickCheck
+     * @return bits 31..1: spanQuickCheckYes (==s.length() if "yes") and
+     *         bit 0: set if "maybe"; otherwise, if the span length&lt;s.length()
+     *         then the quick check result is "no"
+     */
+    public int composeQuickCheck(CharSequence s, int src, int limit,
+                                 boolean onlyContiguous, boolean doSpan) {
+        int qcResult=0;
+        int minNoMaybeCP=minCompNoMaybeCP;
 
-            // read the indexes
-            indexes = reader.readIndexes(NormalizerImpl.INDEX_TOP);
-
-            byte[] normBytes = new byte[indexes[NormalizerImpl.INDEX_TRIE_SIZE]];
-
-            int combiningTableTop = indexes[NormalizerImpl.INDEX_COMBINE_DATA_COUNT];
-            combiningTable = new char[combiningTableTop];
-
-            int extraDataTop = indexes[NormalizerImpl.INDEX_CHAR_COUNT];
-            extraData = new char[extraDataTop];
-
-            byte[] fcdBytes = new byte[indexes[NormalizerImpl.INDEX_FCD_TRIE_SIZE]];
-            byte[] auxBytes = new byte[indexes[NormalizerImpl.INDEX_AUX_TRIE_SIZE]];
+        /*
+         * prevBoundary points to the last character before the current one
+         * that has a composition boundary before it with ccc==0 and quick check "yes".
+         */
+        int prevBoundary=src;
+        int prevSrc;
+        int c=0;
+        int norm16=0;
+        int prevCC=0;
 
-            fcdTrieImpl = new FCDTrieImpl();
-            normTrieImpl = new NormTrieImpl();
-            auxTrieImpl = new AuxTrieImpl();
-
-            // load the rest of the data data and initialize the data members
-            reader.read(normBytes, fcdBytes,auxBytes, extraData, combiningTable);
-
-            NormTrieImpl.normTrie = new IntTrie( new ByteArrayInputStream(normBytes),normTrieImpl );
-            FCDTrieImpl.fcdTrie   = new CharTrie( new ByteArrayInputStream(fcdBytes),fcdTrieImpl  );
-            AuxTrieImpl.auxTrie   = new CharTrie( new ByteArrayInputStream(auxBytes),auxTrieImpl  );
+        for(;;) {
+            // count code units below the minimum or with irrelevant data for the quick check
+            for(prevSrc=src;;) {
+                if(src==limit) {
+                    return (src<<1)|qcResult;  // "yes" or "maybe"
+                }
+                if( (c=s.charAt(src))<minNoMaybeCP ||
+                    isCompYesAndZeroCC(norm16=normTrie.getFromU16SingleLead((char)c))
+                ) {
+                    ++src;
+                } else if(!UTF16.isSurrogate((char)c)) {
+                    break;
+                } else {
+                    char c2;
+                    if(UTF16Plus.isSurrogateLead(c)) {
+                        if((src+1)!=limit && Character.isLowSurrogate(c2=s.charAt(src+1))) {
+                            c=Character.toCodePoint((char)c, c2);
+                        }
+                    } else /* trail surrogate */ {
+                        if(prevSrc<src && Character.isHighSurrogate(c2=s.charAt(src-1))) {
+                            --src;
+                            c=Character.toCodePoint(c2, (char)c);
+                        }
+                    }
+                    if(isCompYesAndZeroCC(norm16=getNorm16(c))) {
+                        src+=Character.charCount(c);
+                    } else {
+                        break;
+                    }
+                }
+            }
+            if(src!=prevSrc) {
+                // Set prevBoundary to the last character in the quick check loop.
+                prevBoundary=src-1;
+                if( Character.isLowSurrogate(s.charAt(prevBoundary)) && prevSrc<prevBoundary &&
+                        Character.isHighSurrogate(s.charAt(prevBoundary-1))
+                ) {
+                    --prevBoundary;
+                }
+                prevCC=0;
+                // The start of the current character (c).
+                prevSrc=src;
+            }
 
-            // we reached here without any exceptions so the data is fully
-            // loaded set the variable to true
-            isDataLoaded = true;
-
-            // get the data format version
-            byte[] formatVersion = reader.getDataFormatVersion();
-
-            isFormatVersion_2_1 =( formatVersion[0]>2
-                                    ||
-                                   (formatVersion[0]==2 && formatVersion[1]>=1)
-                                 );
-            isFormatVersion_2_2 =( formatVersion[0]>2
-                                    ||
-                                   (formatVersion[0]==2 && formatVersion[1]>=2)
-                                 );
-            unicodeVersion = reader.getUnicodeVersion();
-            b.close();
+            src+=Character.charCount(c);
+            /*
+             * isCompYesAndZeroCC(norm16) is false, that is, norm16>=minNoNo.
+             * c is either a "noNo" (has a mapping) or a "maybeYes" (combines backward)
+             * or has ccc!=0.
+             */
+            if(isMaybeOrNonZeroCC(norm16)) {
+                int cc=getCCFromYesOrMaybe(norm16);
+                if( onlyContiguous &&  // FCC
+                    cc!=0 &&
+                    prevCC==0 &&
+                    prevBoundary<prevSrc &&
+                    // prevCC==0 && prevBoundary<prevSrc tell us that
+                    // [prevBoundary..prevSrc[ (which is exactly one character under these conditions)
+                    // passed the quick check "yes && ccc==0" test.
+                    // Check whether the last character was a "yesYes" or a "yesNo".
+                    // If a "yesNo", then we get its trailing ccc from its
+                    // mapping and check for canonical order.
+                    // All other cases are ok.
+                    getTrailCCFromCompYesAndZeroCC(s, prevBoundary, prevSrc)>cc
+                ) {
+                    // Fails FCD test.
+                } else if(prevCC<=cc || cc==0) {
+                    prevCC=cc;
+                    if(norm16<MIN_YES_YES_WITH_CC) {
+                        if(!doSpan) {
+                            qcResult=1;
+                        } else {
+                            return prevBoundary<<1;  // spanYes does not care to know it's "maybe"
+                        }
+                    }
+                    continue;
+                }
+            }
+            return prevBoundary<<1;  // "no"
         }
     }
 
-    /* ---------------------------------------------------------------------- */
-
-    /* Korean Hangul and Jamo constants */
-
-    public static final int JAMO_L_BASE=0x1100;     /* "lead" jamo */
-    public static final int JAMO_V_BASE=0x1161;     /* "vowel" jamo */
-    public static final int JAMO_T_BASE=0x11a7;     /* "trail" jamo */
-
-    public static final int HANGUL_BASE=0xac00;
-
-    public static final int JAMO_L_COUNT=19;
-    public static final int JAMO_V_COUNT=21;
-    public static final int JAMO_T_COUNT=28;
-    public  static final int HANGUL_COUNT=JAMO_L_COUNT*JAMO_V_COUNT*JAMO_T_COUNT;
-
-    private static boolean isHangulWithoutJamoT(char c) {
-        c-=HANGUL_BASE;
-        return c<HANGUL_COUNT && c%JAMO_T_COUNT==0;
-    }
-
-    /* norm32 helpers */
-
-    /* is this a norm32 with a regular index? */
-    private static boolean isNorm32Regular(long norm32) {
-        return norm32<MIN_SPECIAL;
-    }
-
-    /* is this a norm32 with a special index for a lead surrogate? */
-    private static boolean isNorm32LeadSurrogate(long norm32) {
-        return MIN_SPECIAL<=norm32 && norm32<SURROGATES_TOP;
-    }
-
-    /* is this a norm32 with a special index for a Hangul syllable or a Jamo? */
-    private static boolean isNorm32HangulOrJamo(long norm32) {
-        return norm32>=MIN_HANGUL;
-    }
-
-    /*
-     * Given norm32 for Jamo V or T,
-     * is this a Jamo V?
-     */
-    private static boolean isJamoVTNorm32JamoV(long norm32) {
-        return norm32<JAMO_V_TOP;
-    }
-
-    /* data access primitives ----------------------------------------------- */
-
-    public static long/*unsigned*/ getNorm32(char c) {
-        return ((UNSIGNED_INT_MASK) & (NormTrieImpl.normTrie.getLeadValue(c)));
-    }
-
-    public static long/*unsigned*/ getNorm32FromSurrogatePair(long norm32,
-                                                               char c2) {
-        /*
-         * the surrogate index in norm32 stores only the number of the surrogate
-         * index block see gennorm/store.c/getFoldedNormValue()
-         */
-        return ((UNSIGNED_INT_MASK) &
-                    NormTrieImpl.normTrie.getTrailValue((int)norm32, c2));
-    }
-    ///CLOVER:OFF
-    private static long getNorm32(int c){
-        return (UNSIGNED_INT_MASK&(NormTrieImpl.normTrie.getCodePointValue(c)));
-    }
-
-    /*
-     * get a norm32 from text with complete code points
-     * (like from decompositions)
-     */
-    private static long/*unsigned*/ getNorm32(char[] p,int start,
-                                              int/*unsigned*/ mask) {
-        long/*unsigned*/ norm32= getNorm32(p[start]);
-        if(((norm32&mask)>0) && isNorm32LeadSurrogate(norm32)) {
-            /* *p is a lead surrogate, get the real norm32 */
-            norm32=getNorm32FromSurrogatePair(norm32, p[start+1]);
+    public void composeAndAppend(CharSequence s,
+                                 boolean doCompose,
+                                 boolean onlyContiguous,
+                                 ReorderingBuffer buffer) {
+        int src=0, limit=s.length();
+        if(!buffer.isEmpty()) {
+            int firstStarterInSrc=findNextCompBoundary(s, 0, limit);
+            if(0!=firstStarterInSrc) {
+                int lastStarterInDest=findPreviousCompBoundary(buffer.getStringBuilder(),
+                                                               buffer.length());
+                StringBuilder middle=new StringBuilder((buffer.length()-lastStarterInDest)+
+                                                       firstStarterInSrc+16);
+                middle.append(buffer.getStringBuilder(), lastStarterInDest, buffer.length());
+                buffer.removeSuffix(buffer.length()-lastStarterInDest);
+                middle.append(s, 0, firstStarterInSrc);
+                compose(middle, 0, middle.length(), onlyContiguous, true, buffer);
+                src=firstStarterInSrc;
+            }
         }
-        return norm32;
-    }
-
-    //// for StringPrep
-    public static VersionInfo getUnicodeVersion(){
-        return VersionInfo.getInstance(unicodeVersion[0], unicodeVersion[1],
-                                       unicodeVersion[2], unicodeVersion[3]);
-    }
-
-    public static char    getFCD16(char c) {
-        return  FCDTrieImpl.fcdTrie.getLeadValue(c);
-    }
-
-    public static char getFCD16FromSurrogatePair(char fcd16, char c2) {
-        /* the surrogate index in fcd16 is an absolute offset over the
-         * start of stage 1
-         * */
-        return FCDTrieImpl.fcdTrie.getTrailValue(fcd16, c2);
-    }
-    public static int getFCD16(int c) {
-        return  FCDTrieImpl.fcdTrie.getCodePointValue(c);
-    }
-
-    private static int getExtraDataIndex(long norm32) {
-        return (int)(norm32>>EXTRA_SHIFT);
-    }
-
-    private static final class DecomposeArgs{
-        int /*unsigned byte*/ cc;
-        int /*unsigned byte*/ trailCC;
-        int length;
-    }
-    /**
-     *
-     * get the canonical or compatibility decomposition for one character
-     *
-     * @return index into the extraData array
-     */
-    private static int/*index*/ decompose(long/*unsigned*/ norm32,
-                                          int/*unsigned*/ qcMask,
-                                          DecomposeArgs args) {
-        int p= getExtraDataIndex(norm32);
-        args.length=extraData[p++];
-
-        if((norm32&qcMask&QC_NFKD)!=0 && args.length>=0x100) {
-            /* use compatibility decomposition, skip canonical data */
-            p+=((args.length>>7)&1)+(args.length&DECOMP_LENGTH_MASK);
-            args.length>>=8;
-        }
-
-        if((args.length&DECOMP_FLAG_LENGTH_HAS_CC)>0) {
-            /* get the lead and trail cc's */
-            char bothCCs=extraData[p++];
-            args.cc=(UNSIGNED_BYTE_MASK) & (bothCCs>>8);
-            args.trailCC=(UNSIGNED_BYTE_MASK) & bothCCs;
+        if(doCompose) {
+            compose(s, src, limit, onlyContiguous, true, buffer);
         } else {
-            /* lead and trail cc's are both 0 */
-            args.cc=args.trailCC=0;
-        }
-
-        args.length&=DECOMP_LENGTH_MASK;
-        return p;
-    }
-
-
-    /**
-     * get the canonical decomposition for one character
-     * @return index into the extraData array
-     */
-    private static int decompose(long/*unsigned*/ norm32,
-                                 DecomposeArgs args) {
-
-        int p= getExtraDataIndex(norm32);
-        args.length=extraData[p++];
-
-        if((args.length&DECOMP_FLAG_LENGTH_HAS_CC)>0) {
-            /* get the lead and trail cc's */
-            char bothCCs=extraData[p++];
-            args.cc=(UNSIGNED_BYTE_MASK) & (bothCCs>>8);
-            args.trailCC=(UNSIGNED_BYTE_MASK) & bothCCs;
-        } else {
-            /* lead and trail cc's are both 0 */
-            args.cc=args.trailCC=0;
-        }
-
-        args.length&=DECOMP_LENGTH_MASK;
-        return p;
-    }
-
-
-    private static final class NextCCArgs{
-        char[] source;
-        int next;
-        int limit;
-        char c;
-        char c2;
-    }
-
-    /*
-     * get the combining class of (c, c2)= args.source[args.next++]
-     * before: args.next<args.limit  after: args.next<=args.limit
-     * if only one code unit is used, then c2==0
-     */
-    private static int /*unsigned byte*/ getNextCC(NextCCArgs args) {
-        long /*unsigned*/ norm32;
-
-        args.c=args.source[args.next++];
-
-        norm32= getNorm32(args.c);
-        if((norm32 & CC_MASK)==0) {
-            args.c2=0;
-            return 0;
-        } else {
-            if(!isNorm32LeadSurrogate(norm32)) {
-                args.c2=0;
-            } else {
-                /* c is a lead surrogate, get the real norm32 */
-                if(args.next!=args.limit &&
-                        UTF16.isTrailSurrogate(args.c2=args.source[args.next])){
-                    ++args.next;
-                    norm32=getNorm32FromSurrogatePair(norm32, args.c2);
-                } else {
-                    args.c2=0;
-                    return 0;
-                }
-            }
-
-            return (int)((UNSIGNED_BYTE_MASK) & (norm32>>CC_SHIFT));
+            buffer.append(s, src, limit);
         }
     }
 
-    private static final class PrevArgs{
-        char[] src;
-        int start;
-        int current;
-        char c;
-        char c2;
+    // Dual functionality:
+    // buffer!=NULL: normalize
+    // buffer==NULL: isNormalized/quickCheck/spanQuickCheckYes
+    public int makeFCD(CharSequence s, int src, int limit, ReorderingBuffer buffer) {
+        // Note: In this function we use buffer->appendZeroCC() because we track
+        // the lead and trail combining classes here, rather than leaving it to
+        // the ReorderingBuffer.
+        // The exception is the call to decomposeShort() which uses the buffer
+        // in the normal way.
+
+        // Tracks the last FCD-safe boundary, before lccc=0 or after properly-ordered tccc<=1.
+        // Similar to the prevBoundary in the compose() implementation.
+        int prevBoundary=src;
+        int prevSrc;
+        int c=0;
+        int prevFCD16=0;
+        int fcd16=0;
+
+        for(;;) {
+            // count code units with lccc==0
+            for(prevSrc=src; src!=limit;) {
+                if((c=s.charAt(src))<MIN_CCC_LCCC_CP) {
+                    prevFCD16=~c;
+                    ++src;
+                } else if(!singleLeadMightHaveNonZeroFCD16(c)) {
+                    prevFCD16=0;
+                    ++src;
+                } else {
+                    if(UTF16.isSurrogate((char)c)) {
+                        char c2;
+                        if(UTF16Plus.isSurrogateLead(c)) {
+                            if((src+1)!=limit && Character.isLowSurrogate(c2=s.charAt(src+1))) {
+                                c=Character.toCodePoint((char)c, c2);
+                            }
+                        } else /* trail surrogate */ {
+                            if(prevSrc<src && Character.isHighSurrogate(c2=s.charAt(src-1))) {
+                                --src;
+                                c=Character.toCodePoint(c2, (char)c);
+                            }
+                        }
+                    }
+                    if((fcd16=getFCD16FromNormData(c))<=0xff) {
+                        prevFCD16=fcd16;
+                        src+=Character.charCount(c);
+                    } else {
+                        break;
+                    }
+              }
+            }
+            // copy these code units all at once
+            if(src!=prevSrc) {
+                if(src==limit) {
+                    if(buffer!=null) {
+                        buffer.flushAndAppendZeroCC(s, prevSrc, src);
+                    }
+                    break;
+                }
+                prevBoundary=src;
+                // We know that the previous character's lccc==0.
+                if(prevFCD16<0) {
+                    // Fetching the fcd16 value was deferred for this below-U+0300 code point.
+                    int prev=~prevFCD16;
+                    prevFCD16= prev<0x180 ? tccc180[prev] : getFCD16FromNormData(prev);
+                    if(prevFCD16>1) {
+                        --prevBoundary;
+                    }
+                } else {
+                    int p=src-1;
+                    if( Character.isLowSurrogate(s.charAt(p)) && prevSrc<p &&
+                        Character.isHighSurrogate(s.charAt(p-1))
+                    ) {
+                        --p;
+                        // Need to fetch the previous character's FCD value because
+                        // prevFCD16 was just for the trail surrogate code point.
+                        prevFCD16=getFCD16FromNormData(Character.toCodePoint(s.charAt(p), s.charAt(p+1)));
+                        // Still known to have lccc==0 because its lead surrogate unit had lccc==0.
+                    }
+                    if(prevFCD16>1) {
+                        prevBoundary=p;
+                    }
+                }
+                if(buffer!=null) {
+                    // The last lccc==0 character is excluded from the
+                    // flush-and-append call in case it needs to be modified.
+                    buffer.flushAndAppendZeroCC(s, prevSrc, prevBoundary);
+                    buffer.append(s, prevBoundary, src);
+                }
+                // The start of the current character (c).
+                prevSrc=src;
+            } else if(src==limit) {
+                break;
+            }
+
+            src+=Character.charCount(c);
+            // The current character (c) at [prevSrc..src[ has a non-zero lead combining class.
+            // Check for proper order, and decompose locally if necessary.
+            if((prevFCD16&0xff)<=(fcd16>>8)) {
+                // proper order: prev tccc <= current lccc
+                if((fcd16&0xff)<=1) {
+                    prevBoundary=src;
+                }
+                if(buffer!=null) {
+                    buffer.appendZeroCC(c);
+                }
+                prevFCD16=fcd16;
+                continue;
+            } else if(buffer==null) {
+                return prevBoundary;  // quick check "no"
+            } else {
+                /*
+                 * Back out the part of the source that we copied or appended
+                 * already but is now going to be decomposed.
+                 * prevSrc is set to after what was copied/appended.
+                 */
+                buffer.removeSuffix(prevSrc-prevBoundary);
+                /*
+                 * Find the part of the source that needs to be decomposed,
+                 * up to the next safe boundary.
+                 */
+                src=findNextFCDBoundary(s, src, limit);
+                /*
+                 * The source text does not fulfill the conditions for FCD.
+                 * Decompose and reorder a limited piece of the text.
+                 */
+                decomposeShort(s, prevBoundary, src, buffer);
+                prevBoundary=src;
+                prevFCD16=0;
+            }
+        }
+        return src;
     }
 
-    /*
-     * read backwards and get norm32
-     * return 0 if the character is <minC
-     * if c2!=0 then (c2, c) is a surrogate pair (reversed - c2 is first
-     * surrogate but read second!)
-     */
-    private static long /*unsigned*/ getPrevNorm32(PrevArgs args,
-                                                      int/*unsigned*/ minC,
-                                                      int/*unsigned*/ mask) {
-        long/*unsigned*/ norm32;
+    // Note: hasDecompBoundary() could be implemented as aliases to
+    // hasFCDBoundaryBefore() and hasFCDBoundaryAfter()
+    // at the cost of building the FCD trie for a decomposition normalizer.
+    public boolean hasDecompBoundary(int c, boolean before) {
+        for(;;) {
+            if(c<minDecompNoCP) {
+                return true;
+            }
+            int norm16=getNorm16(c);
+            if(isHangul(norm16) || isDecompYesAndZeroCC(norm16)) {
+                return true;
+            } else if(norm16>MIN_NORMAL_MAYBE_YES) {
+                return false;  // ccc!=0
+            } else if(isDecompNoAlgorithmic(norm16)) {
+                c=mapAlgorithmic(c, norm16);
+            } else {
+                // c decomposes, get everything from the variable-length extra data
+                int firstUnit=extraData.charAt(norm16);
+                if((firstUnit&MAPPING_LENGTH_MASK)==0) {
+                    return false;
+                }
+                if(!before) {
+                    // decomp after-boundary: same as hasFCDBoundaryAfter(),
+                    // fcd16<=1 || trailCC==0
+                    if(firstUnit>0x1ff) {
+                        return false;  // trailCC>1
+                    }
+                    if(firstUnit<=0xff) {
+                        return true;  // trailCC==0
+                    }
+                    // if(trailCC==1) test leadCC==0, same as checking for before-boundary
+                }
+                // true if leadCC==0 (hasFCDBoundaryBefore())
+                return (firstUnit&MAPPING_HAS_CCC_LCCC_WORD)==0 || (extraData.charAt(norm16-1)&0xff00)==0;
+            }
+        }
+    }
 
-        args.c=args.src[--args.current];
-        args.c2=0;
+    public boolean hasCompBoundaryBefore(int c) {
+        return c<minCompNoMaybeCP || hasCompBoundaryBefore(c, getNorm16(c));
+    }
 
-        /* check for a surrogate before getting norm32 to see if we need to
-         * predecrement further
-         */
-        if(args.c<minC) {
-            return 0;
-        } else if(!UTF16.isSurrogate(args.c)) {
-            return getNorm32(args.c);
-        } else if(UTF16.isLeadSurrogate(args.c)) {
-            /* unpaired first surrogate */
-            return 0;
-        } else if(args.current!=args.start &&
-                    UTF16.isLeadSurrogate(args.c2=args.src[args.current-1])) {
-            --args.current;
-            norm32=getNorm32(args.c2);
+    private boolean isMaybe(int norm16) { return minMaybeYes<=norm16 && norm16<=JAMO_VT; }
+    private boolean isMaybeOrNonZeroCC(int norm16) { return norm16>=minMaybeYes; }
+    private static boolean isJamoVT(int norm16) { return norm16==JAMO_VT; }
+    private boolean isHangul(int norm16) { return norm16==minYesNo; }
+    private boolean isCompYesAndZeroCC(int norm16) { return norm16<minNoNo; }
+
+    // UBool isCompYes(uint16_t norm16) const {
+    //     return norm16>=MIN_YES_YES_WITH_CC || norm16<minNoNo;
+    // }
+    // UBool isCompYesOrMaybe(uint16_t norm16) const {
+    //     return norm16<minNoNo || minMaybeYes<=norm16;
+    // }
+    // private boolean hasZeroCCFromDecompYes(int norm16) {
+    //     return norm16<=MIN_NORMAL_MAYBE_YES || norm16==JAMO_VT;
+    // }
+    private boolean isDecompYesAndZeroCC(int norm16) {
+        return norm16<minYesNo ||
+               norm16==JAMO_VT ||
+               (minMaybeYes<=norm16 && norm16<=MIN_NORMAL_MAYBE_YES);
+    }
 
-            if((norm32&mask)==0) {
-                /* all surrogate pairs with this lead surrogate have
-                 * only irrelevant data
-                 */
-                return 0;
-            } else {
-                /* norm32 must be a surrogate special */
-                return getNorm32FromSurrogatePair(norm32, args.c);
-            }
+    /**
+     * A little faster and simpler than isDecompYesAndZeroCC() but does not include
+     * the MaybeYes which combine-forward and have ccc=0.
+     * (Standard Unicode 5.2 normalization does not have such characters.)
+     */
+    private boolean isMostDecompYesAndZeroCC(int norm16) {
+        return norm16<minYesNo || norm16==MIN_NORMAL_MAYBE_YES || norm16==JAMO_VT;
+    }
+
+    private boolean isDecompNoAlgorithmic(int norm16) { return norm16>=limitNoNo; }
+
+    // For use with isCompYes().
+    // Perhaps the compiler can combine the two tests for MIN_YES_YES_WITH_CC.
+    // static uint8_t getCCFromYes(uint16_t norm16) {
+    //     return norm16>=MIN_YES_YES_WITH_CC ? (uint8_t)norm16 : 0;
+    // }
+    private int getCCFromNoNo(int norm16) {
+        if((extraData.charAt(norm16)&MAPPING_HAS_CCC_LCCC_WORD)!=0) {
+            return extraData.charAt(norm16-1)&0xff;
         } else {
-            /* unpaired second surrogate */
-            args.c2=0;
             return 0;
         }
     }
 
-    /*
-     * get the combining class of (c, c2)=*--p
-     * before: start<p  after: start<=p
+    // requires that the [cpStart..cpLimit[ character passes isCompYesAndZeroCC()
+    int getTrailCCFromCompYesAndZeroCC(CharSequence s, int cpStart, int cpLimit) {
+        int c;
+        if(cpStart==(cpLimit-1)) {
+            c=s.charAt(cpStart);
+        } else {
+            c=Character.codePointAt(s, cpStart);
+        }
+        int prevNorm16=getNorm16(c);
+        if(prevNorm16<=minYesNo) {
+            return 0;  // yesYes and Hangul LV/LVT have ccc=tccc=0
+        } else {
+            return extraData.charAt(prevNorm16)>>8;  // tccc from yesNo
+        }
+    }
+
+    // Requires algorithmic-NoNo.
+    private int mapAlgorithmic(int c, int norm16) {
+        return c+norm16-(minMaybeYes-MAX_DELTA-1);
+    }
+
+    // Requires minYesNo<norm16<limitNoNo.
+    // private int getMapping(int norm16) { return /*extraData+*/norm16; }
+
+    /**
+     * @return index into maybeYesCompositions, or -1
      */
-    private static int /*unsigned byte*/ getPrevCC(PrevArgs args) {
-
-        return (int)((UNSIGNED_BYTE_MASK)&(getPrevNorm32(args, MIN_WITH_LEAD_CC,
-                                                         CC_MASK)>>CC_SHIFT));
+    private int getCompositionsListForDecompYes(int norm16) {
+        if(norm16==0 || MIN_NORMAL_MAYBE_YES<=norm16) {
+            return -1;
+        } else {
+            if((norm16-=minMaybeYes)<0) {
+                // norm16<minMaybeYes: index into extraData which is a substring at
+                //     maybeYesCompositions[MIN_NORMAL_MAYBE_YES-minMaybeYes]
+                // same as (MIN_NORMAL_MAYBE_YES-minMaybeYes)+norm16
+                norm16+=MIN_NORMAL_MAYBE_YES;  // for yesYes; if Jamo L: harmless empty list
+            }
+            return norm16;
+        }
     }
 
-    /*
-     * is this a safe boundary character for NF*D?
-     * (lead cc==0)
+    /**
+     * @return index into maybeYesCompositions
      */
-    public static boolean isNFDSafe(long/*unsigned*/ norm32,
-                                     int/*unsigned*/ccOrQCMask,
-                                     int/*unsigned*/ decompQCMask) {
-        if((norm32&ccOrQCMask)==0) {
-            return true; /* cc==0 and no decomposition: this is NF*D safe */
+    private int getCompositionsListForComposite(int norm16) {
+        // composite has both mapping & compositions list
+        int firstUnit=extraData.charAt(norm16);
+        return (MIN_NORMAL_MAYBE_YES-minMaybeYes)+norm16+  // mapping in maybeYesCompositions
+            1+  // +1 to skip the first unit with the mapping lenth
+            (firstUnit&MAPPING_LENGTH_MASK);  // + mapping length
+    }
+
+    // Decompose a short piece of text which is likely to contain characters that
+    // fail the quick check loop and/or where the quick check loop's overhead
+    // is unlikely to be amortized.
+    // Called by the compose() and makeFCD() implementations.
+    // Public in Java for collation implementation code.
+    public void decomposeShort(CharSequence s, int src, int limit,
+                               ReorderingBuffer buffer) {
+        while(src<limit) {
+            int c=Character.codePointAt(s, src);
+            src+=Character.charCount(c);
+            decompose(c, getNorm16(c), buffer);
         }
+    }
 
-        /* inspect its decomposition - maybe a Hangul but not a surrogate here*/
-        if(isNorm32Regular(norm32) && (norm32&decompQCMask)!=0) {
-            DecomposeArgs args=new DecomposeArgs();
-            /* decomposes, get everything from the variable-length extra data */
-            decompose(norm32, decompQCMask, args);
-            return args.cc==0;
-        } else {
-            /* no decomposition (or Hangul), test the cc directly */
-            return (norm32&CC_MASK)==0;
+    private void decompose(int c, int norm16,
+                           ReorderingBuffer buffer) {
+        // Only loops for 1:1 algorithmic mappings.
+        for(;;) {
+            // get the decomposition and the lead and trail cc's
+            if(isDecompYes(norm16)) {
+                // c does not decompose
+                buffer.append(c, getCCFromYesOrMaybe(norm16));
+            } else if(isHangul(norm16)) {
+                // Hangul syllable: decompose algorithmically
+                Hangul.decompose(c, buffer);
+            } else if(isDecompNoAlgorithmic(norm16)) {
+                c=mapAlgorithmic(c, norm16);
+                norm16=getNorm16(c);
+                continue;
+            } else {
+                // c decomposes, get everything from the variable-length extra data
+                int firstUnit=extraData.charAt(norm16);
+                int length=firstUnit&MAPPING_LENGTH_MASK;
+                int leadCC, trailCC;
+                trailCC=firstUnit>>8;
+                if((firstUnit&MAPPING_HAS_CCC_LCCC_WORD)!=0) {
+                    leadCC=extraData.charAt(norm16-1)>>8;
+                } else {
+                    leadCC=0;
+                }
+                ++norm16;  // skip over the firstUnit
+                buffer.append(extraData, norm16, norm16+length, leadCC, trailCC);
+            }
+            return;
         }
     }
 
-    /*
-     * is this (or does its decomposition begin with) a "true starter"?
-     * (cc==0 and NF*C_YES)
+    /**
+     * Finds the recomposition result for
+     * a forward-combining "lead" character,
+     * specified with a pointer to its compositions list,
+     * and a backward-combining "trail" character.
+     *
+     * <p>If the lead and trail characters combine, then this function returns
+     * the following "compositeAndFwd" value:
+     * <pre>
+     * Bits 21..1  composite character
+     * Bit      0  set if the composite is a forward-combining starter
+     * </pre>
+     * otherwise it returns -1.
+     *
+     * <p>The compositions list has (trail, compositeAndFwd) pair entries,
+     * encoded as either pairs or triples of 16-bit units.
+     * The last entry has the high bit of its first unit set.
+     *
+     * <p>The list is sorted by ascending trail characters (there are no duplicates).
+     * A linear search is used.
+     *
+     * <p>See normalizer2impl.h for a more detailed description
+     * of the compositions list format.
      */
-    public static boolean isTrueStarter(long/*unsigned*/ norm32,
-                                          int/*unsigned*/ ccOrQCMask,
-                                          int/*unsigned*/ decompQCMask) {
-        if((norm32&ccOrQCMask)==0) {
-            return true; /* this is a true starter (could be Hangul or Jamo L)*/
-        }
-
-        /* inspect its decomposition - not a Hangul or a surrogate here */
-        if((norm32&decompQCMask)!=0) {
-            int p; /* index into extra data array */
-            DecomposeArgs args=new DecomposeArgs();
-            /* decomposes, get everything from the variable-length extra data */
-            p=decompose(norm32, decompQCMask, args);
-
-            if(args.cc==0) {
-                int/*unsigned*/ qcMask=ccOrQCMask&QC_MASK;
-
-                /* does it begin with NFC_YES? */
-                if((getNorm32(extraData,p, qcMask)&qcMask)==0) {
-                    /* yes, the decomposition begins with a true starter */
-                    return true;
+    private static int combine(String compositions, int list, int trail) {
+        int key1, firstUnit;
+        if(trail<COMP_1_TRAIL_LIMIT) {
+            // trail character is 0..33FF
+            // result entry may have 2 or 3 units
+            key1=(trail<<1);
+            while(key1>(firstUnit=compositions.charAt(list))) {
+                list+=2+(firstUnit&COMP_1_TRIPLE);
+            }
+            if(key1==(firstUnit&COMP_1_TRAIL_MASK)) {
+                if((firstUnit&COMP_1_TRIPLE)!=0) {
+                    return ((int)compositions.charAt(list+1)<<16)|compositions.charAt(list+2);
+                } else {
+                    return compositions.charAt(list+1);
+                }
+            }
+        } else {
+            // trail character is 3400..10FFFF
+            // result entry has 3 units
+            key1=COMP_1_TRAIL_LIMIT+(((trail>>COMP_1_TRAIL_SHIFT))&~COMP_1_TRIPLE);
+            int key2=(trail<<COMP_2_TRAIL_SHIFT)&0xffff;
+            int secondUnit;
+            for(;;) {
+                if(key1>(firstUnit=compositions.charAt(list))) {
+                    list+=2+(firstUnit&COMP_1_TRIPLE);
+                } else if(key1==(firstUnit&COMP_1_TRAIL_MASK)) {
+                    if(key2>(secondUnit=compositions.charAt(list+1))) {
+                        if((firstUnit&COMP_1_LAST_TUPLE)!=0) {
+                            break;
+                        } else {
+                            list+=3;
+                        }
+                    } else if(key2==(secondUnit&COMP_2_TRAIL_MASK)) {
+                        return ((secondUnit&~COMP_2_TRAIL_MASK)<<16)|compositions.charAt(list+2);
+                    } else {
+                        break;
+                    }
+                } else {
+                    break;
                 }
             }
         }
-        return false;
+        return -1;
+    }
+
+    /*
+     * Recomposes the buffer text starting at recomposeStartIndex
+     * (which is in NFD - decomposed and canonically ordered),
+     * and truncates the buffer contents.
+     *
+     * Note that recomposition never lengthens the text:
+     * Any character consists of either one or two code units;
+     * a composition may contain at most one more code unit than the original starter,
+     * while the combining mark that is removed has at least one code unit.
+     */
+    private void recompose(ReorderingBuffer buffer, int recomposeStartIndex,
+                           boolean onlyContiguous) {
+        StringBuilder sb=buffer.getStringBuilder();
+        int p=recomposeStartIndex;
+        if(p==sb.length()) {
+            return;
+        }
+
+        int starter, pRemove;
+        int compositionsList;
+        int c, compositeAndFwd;
+        int norm16;
+        int cc, prevCC;
+        boolean starterIsSupplementary;
+
+        // Some of the following variables are not used until we have a forward-combining starter
+        // and are only initialized now to avoid compiler warnings.
+        compositionsList=-1;  // used as indicator for whether we have a forward-combining starter
+        starter=-1;
+        starterIsSupplementary=false;
+        prevCC=0;
+
+        for(;;) {
+            c=sb.codePointAt(p);
+            p+=Character.charCount(c);
+            norm16=getNorm16(c);
+            cc=getCCFromYesOrMaybe(norm16);
+            if( // this character combines backward and
+                isMaybe(norm16) &&
+                // we have seen a starter that combines forward and
+                compositionsList>=0 &&
+                // the backward-combining character is not blocked
+                (prevCC<cc || prevCC==0)) {
+                if(isJamoVT(norm16)) {
+                    // c is a Jamo V/T, see if we can compose it with the previous character.
+                    if(c<Hangul.JAMO_T_BASE) {
+                        // c is a Jamo Vowel, compose with previous Jamo L and following Jamo T.
+                        char prev=(char)(sb.charAt(starter)-Hangul.JAMO_L_BASE);
+                        if(prev<Hangul.JAMO_L_COUNT) {
+                            pRemove=p-1;
+                            char syllable=(char)
+                                (Hangul.HANGUL_BASE+
+                                 (prev*Hangul.JAMO_V_COUNT+(c-Hangul.JAMO_V_BASE))*
+                                 Hangul.JAMO_T_COUNT);
+                            char t;
+                            if(p!=sb.length() && (t=(char)(sb.charAt(p)-Hangul.JAMO_T_BASE))<Hangul.JAMO_T_COUNT) {
+                                ++p;
+                                syllable+=t;  // The next character was a Jamo T.
+                            }
+                            sb.setCharAt(starter, syllable);
+                            // remove the Jamo V/T
+                            sb.delete(pRemove, p);
+                            p=pRemove;
+                        }
+                    }
+                    /*
+                     * No "else" for Jamo T:
+                     * Since the input is in NFD, there are no Hangul LV syllables that
+                     * a Jamo T could combine with.
+                     * All Jamo Ts are combined above when handling Jamo Vs.
+                     */
+                    if(p==sb.length()) {
+                        break;
+                    }
+                    compositionsList=-1;
+                    continue;
+                } else if((compositeAndFwd=combine(maybeYesCompositions, compositionsList, c))>=0) {
+                    // The starter and the combining mark (c) do combine.
+                    int composite=compositeAndFwd>>1;
+
+                    // Remove the combining mark.
+                    pRemove=p-Character.charCount(c);  // pRemove & p: start & limit of the combining mark
+                    sb.delete(pRemove, p);
+                    p=pRemove;
+                    // Replace the starter with the composite.
+                    if(starterIsSupplementary) {
+                        if(composite>0xffff) {
+                            // both are supplementary
+                            sb.setCharAt(starter, UTF16.getLeadSurrogate(composite));
+                            sb.setCharAt(starter+1, UTF16.getTrailSurrogate(composite));
+                        } else {
+                            sb.setCharAt(starter, (char)c);
+                            sb.deleteCharAt(starter+1);
+                            // The composite is shorter than the starter,
+                            // move the intermediate characters forward one.
+                            starterIsSupplementary=false;
+                            --p;
+                        }
+                    } else if(composite>0xffff) {
+                        // The composite is longer than the starter,
+                        // move the intermediate characters back one.
+                        starterIsSupplementary=true;
+                        sb.setCharAt(starter, UTF16.getLeadSurrogate(composite));
+                        sb.insert(starter+1, UTF16.getTrailSurrogate(composite));
+                        ++p;
+                    } else {
+                        // both are on the BMP
+                        sb.setCharAt(starter, (char)composite);
+                    }
+
+                    // Keep prevCC because we removed the combining mark.
+
+                    if(p==sb.length()) {
+                        break;
+                    }
+                    // Is the composite a starter that combines forward?
+                    if((compositeAndFwd&1)!=0) {
+                        compositionsList=
+                            getCompositionsListForComposite(getNorm16(composite));
+                    } else {
+                        compositionsList=-1;
+                    }
+
+                    // We combined; continue with looking for compositions.
+                    continue;
+                }
+            }
+
+            // no combination this time
+            prevCC=cc;
+            if(p==sb.length()) {
+                break;
+            }
+
+            // If c did not combine, then check if it is a starter.
+            if(cc==0) {
+                // Found a new starter.
+                if((compositionsList=getCompositionsListForDecompYes(norm16))>=0) {
+                    // It may combine with something, prepare for it.
+                    if(c<=0xffff) {
+                        starterIsSupplementary=false;
+                        starter=p-1;
+                    } else {
+                        starterIsSupplementary=true;
+                        starter=p-2;
+                    }
+                }
+            } else if(onlyContiguous) {
+                // FCC: no discontiguous compositions; any intervening character blocks.
+                compositionsList=-1;
+            }
+        }
+        buffer.flush();
+    }
+
+    /**
+     * Does c have a composition boundary before it?
+     * True if its decomposition begins with a character that has
+     * ccc=0 && NFC_QC=Yes (isCompYesAndZeroCC()).
+     * As a shortcut, this is true if c itself has ccc=0 && NFC_QC=Yes
+     * (isCompYesAndZeroCC()) so we need not decompose.
+     */
+    private boolean hasCompBoundaryBefore(int c, int norm16) {
+        for(;;) {
+            if(isCompYesAndZeroCC(norm16)) {
+                return true;
+            } else if(isMaybeOrNonZeroCC(norm16)) {
+                return false;
+            } else if(isDecompNoAlgorithmic(norm16)) {
+                c=mapAlgorithmic(c, norm16);
+                norm16=getNorm16(c);
+            } else {
+                // c decomposes, get everything from the variable-length extra data
+                int firstUnit=extraData.charAt(norm16);
+                if((firstUnit&MAPPING_LENGTH_MASK)==0) {
+                    return false;
+                }
+                if((firstUnit&MAPPING_HAS_CCC_LCCC_WORD)!=0 && (extraData.charAt(norm16-1)&0xff00)!=0) {
+                    return false;  // non-zero leadCC
+                }
+                return isCompYesAndZeroCC(getNorm16(Character.codePointAt(extraData, norm16+1)));
+            }
+        }
+    }
+
+    private int findPreviousCompBoundary(CharSequence s, int p) {
+        while(p>0) {
+            int c=Character.codePointBefore(s, p);
+            p-=Character.charCount(c);
+            if(hasCompBoundaryBefore(c)) {
+                break;
+            }
+            // We could also test hasCompBoundaryAfter() and return iter.codePointLimit,
+            // but that's probably not worth the extra cost.
+        }
+        return p;
+    }
+
+    private int findNextCompBoundary(CharSequence s, int p, int limit) {
+        while(p<limit) {
+            int c=Character.codePointAt(s, p);
+            int norm16=normTrie.get(c);
+            if(hasCompBoundaryBefore(c, norm16)) {
+                break;
+            }
+            p+=Character.charCount(c);
+        }
+        return p;
     }
 
-    /* reorder UTF-16 in-place ---------------------------------------------- */
+    private int findNextFCDBoundary(CharSequence s, int p, int limit) {
+        while(p<limit) {
+            int c=Character.codePointAt(s, p);
+            if(c<MIN_CCC_LCCC_CP || getFCD16(c)<=0xff) {
+                break;
+            }
+            p+=Character.charCount(c);
+        }
+        return p;
+    }
+
+    /**
+     * Get the canonical decomposition
+     * sherman  for ComposedCharIter
+     */
+    public static int getDecompose(int chars[], String decomps[]) {
+        Normalizer2 impl = Normalizer2.getNFDInstance();
+
+        int length=0;
+        int norm16 = 0;
+        int ch = -1;
+        int i = 0;
+
+        while (++ch < 0x2fa1e) {   //no cannoical above 0x3ffff
+            //TBD !!!! the hack code heres save us about 50ms for startup
+            //need a better solution/lookup
+            if (ch == 0x30ff)
+                ch = 0xf900;
+            else if (ch == 0x115bc)
+                ch = 0x1d15e;
+            else if (ch == 0x1d1c1)
+                ch = 0x2f800;
+
+            String s = impl.getDecomposition(ch);
+
+            if(s != null && i < chars.length) {
+                chars[i] = ch;
+                decomps[i++] = s;
+            }
+        }
+        return i;
+    }
+
+    //------------------------------------------------------
+    // special method for Collation (RBTableBuilder.build())
+    //------------------------------------------------------
+    private static boolean needSingleQuotation(char c) {
+        return (c >= 0x0009 && c <= 0x000D) ||
+               (c >= 0x0020 && c <= 0x002F) ||
+               (c >= 0x003A && c <= 0x0040) ||
+               (c >= 0x005B && c <= 0x0060) ||
+               (c >= 0x007B && c <= 0x007E);
+    }
+
+    public static String canonicalDecomposeWithSingleQuotation(String string) {
+       Normalizer2 impl = Normalizer2.getNFDInstance();
+       char[] src = string.toCharArray();
+       int    srcIndex = 0;
+       int    srcLimit = src.length;
+       char[] dest = new char[src.length * 3];  //MAX_BUF_SIZE_DECOMPOSE = 3
+       int    destIndex = 0;
+       int    destLimit = dest.length;
+
+        int prevSrc;
+        String norm;
+        int reorderStartIndex, length;
+        char c1, c2;
+        int cp;
+        int minNoMaybe = 0x00c0;
+        int cc, prevCC, trailCC;
+        char[] p;
+        int pStart;
+
+        // initialize
+        reorderStartIndex = 0;
+        prevCC = 0;
+        norm = null;
+        cp = 0;
+        pStart = 0;
+
+        cc = trailCC = -1; // initialize to bogus value
+        c1 = 0;
+        for (;;) {
+            prevSrc=srcIndex;
+            //quick check (1)less than minNoMaybe (2)no decomp (3)hangual
+            while (srcIndex != srcLimit &&
+                   ((c1 = src[srcIndex]) < minNoMaybe ||
+                    (norm = impl.getDecomposition(cp = string.codePointAt(srcIndex))) == null ||
+                    (c1 >= '\uac00' && c1 <= '\ud7a3'))) { // Hangul Syllables
+                prevCC = 0;
+                srcIndex += (cp < 0x10000) ? 1 : 2;
+            }
+
+            // copy these code units all at once
+            if (srcIndex != prevSrc) {
+                length = srcIndex - prevSrc;
+                if ((destIndex + length) <= destLimit) {
+                    System.arraycopy(src,prevSrc,dest,destIndex,length);
+                }
+
+                destIndex += length;
+                reorderStartIndex = destIndex;
+            }
+
+            // end of source reached?
+            if (srcIndex == srcLimit) {
+                break;
+            }
+
+            // cp already contains *src and norm32 is set for it, increment src
+            srcIndex += (cp < 0x10000) ? 1 : 2;
+
+            if (cp < Character.MIN_SUPPLEMENTARY_CODE_POINT) {
+                c2 = 0;
+                length = 1;
+
+                if (Character.isHighSurrogate(c1)
+                    || Character.isLowSurrogate(c1)) {
+                    norm = null;
+                }
+            } else {
+                length = 2;
+                c2 = src[srcIndex-1];
+            }
+
+          // get the decomposition and the lead and trail cc's
+          if (norm == null) {
+              // cp does not decompose
+              cc = trailCC = UCharacter.getCombiningClass(cp);
+              p = null;
+              pStart = -1;
+          } else {
+
+                pStart = 0;
+                p = norm.toCharArray();
+                length = p.length;
+                int cpNum = norm.codePointCount(0, length);
+                cc= UCharacter.getCombiningClass(norm.codePointAt(0));
+                trailCC= UCharacter.getCombiningClass(norm.codePointAt(cpNum-1));
+                if (length == 1) {
+                    // fastpath a single code unit from decomposition
+                    c1 = p[pStart];
+                    c2 = 0;
+                    p = null;
+                    pStart = -1;
+                }
+            }
+
+            if((destIndex + length * 3) >= destLimit) {  // 2 SingleQuotations
+                // buffer overflow
+                char[] tmpBuf = new char[destLimit * 2];
+                System.arraycopy(dest, 0, tmpBuf, 0, destIndex);
+                dest = tmpBuf;
+                destLimit = dest.length;
+            }
+
+            // append the decomposition to the destination buffer, assume length>0
+            {
+                int reorderSplit = destIndex;
+                if (p == null) {
+                    // fastpath: single code point
+                    if (needSingleQuotation(c1)) {
+                        //if we need single quotation, no need to consider "prevCC"
+                        //and it must NOT be a supplementary pair
+                        dest[destIndex++] = '\'';
+                        dest[destIndex++] = c1;
+                        dest[destIndex++] = '\'';
+                        trailCC = 0;
+                    } else if(cc != 0 && cc < prevCC) {
+                        // (c1, c2) is out of order with respect to the preceding
+                        //  text
+                        destIndex += length;
+                        trailCC = insertOrdered(dest, reorderStartIndex,
+                                                reorderSplit, destIndex, c1, c2, cc);
+                    } else {
+                        // just append (c1, c2)
+                        dest[destIndex++] = c1;
+                        if(c2 != 0) {
+                            dest[destIndex++] = c2;
+                        }
+                    }
+                } else {
+                    // general: multiple code points (ordered by themselves)
+                    // from decomposition
+                    if (needSingleQuotation(p[pStart])) {
+                        dest[destIndex++] = '\'';
+                        dest[destIndex++] = p[pStart++];
+                        dest[destIndex++] = '\'';
+                        length--;
+                        do {
+                            dest[destIndex++] = p[pStart++];
+                        } while(--length > 0);
+                    } else if (cc != 0 && cc < prevCC) {
+                        destIndex += length;
+                        trailCC = mergeOrdered(dest, reorderStartIndex,
+                                               reorderSplit, p, pStart,
+                                               pStart+length);
+                    } else {
+                        // just append the decomposition
+                        do {
+                            dest[destIndex++] = p[pStart++];
+                        } while (--length > 0);
+                    }
+                }
+            }
+            prevCC = trailCC;
+            if(prevCC == 0) {
+                reorderStartIndex = destIndex;
+            }
+        }
+
+        return new String(dest, 0, destIndex);
+    }
 
     /**
      * simpler, single-character version of mergeOrdered() -
@@ -649,19 +1933,23 @@
     private static int/*unsigned byte*/ insertOrdered(char[] source,
                                                       int start,
                                                       int current, int p,
-                                                         char c, char c2,
-                                                         int/*unsigned byte*/ cc) {
+                                                      char c1, char c2,
+                                                      int/*unsigned byte*/ cc) {
         int back, preBack;
         int r;
         int prevCC, trailCC=cc;
 
-        if(start<current && cc!=0) {
+        if (start<current && cc!=0) {
             // search for the insertion point where cc>=prevCC
             preBack=back=current;
+
             PrevArgs prevArgs = new PrevArgs();
             prevArgs.current  = current;
             prevArgs.start    = start;
             prevArgs.src      = source;
+            prevArgs.c1       = c1;
+            prevArgs.c2       = c2;
+
             // get the prevCC
             prevCC=getPrevCC(prevArgs);
             preBack = prevArgs.current;
@@ -679,7 +1967,6 @@
                     back=preBack;
                 }
 
-
                 // this is where we are right now with all these indicies:
                 // [start]..[pPreBack] 0..? code points that we can ignore
                 // [pPreBack]..[pBack] 0..1 code points with prevCC<=cc
@@ -690,14 +1977,14 @@
                 r=p;
                 do {
                     source[--r]=source[--current];
-                } while(back!=current);
+                } while (back!=current);
             }
         }
 
-        // insert (c, c2)
-        source[current]=c;
-        if(c2!=0) {
-            source[(current+1)]=c2;
+        // insert (c1, c2)
+        source[current] = c1;
+        if (c2!=0) {
+            source[(current+1)] = c2;
         }
 
         // we know the cc of the last code point
@@ -732,8 +2019,7 @@
                                                       int current,
                                                       char[] data,
                                                         int next,
-                                                        int limit,
-                                                        boolean isOrdered) {
+                                                        int limit) {
             int r;
             int /*unsigned byte*/ cc, trailCC=0;
             boolean adjacent;
@@ -744,7 +2030,7 @@
             ncArgs.next   = next;
             ncArgs.limit  = limit;
 
-            if(start!=current || !isOrdered) {
+            if(start!=current) {
 
                 while(ncArgs.next<ncArgs.limit) {
                     cc=getNextCC(ncArgs);
@@ -754,20 +2040,16 @@
                         if(adjacent) {
                             current=ncArgs.next;
                         } else {
-                            data[current++]=ncArgs.c;
+                            data[current++]=ncArgs.c1;
                             if(ncArgs.c2!=0) {
                                 data[current++]=ncArgs.c2;
                             }
                         }
-                        if(isOrdered) {
-                            break;
-                        } else {
-                            start=current;
-                        }
+                        break;
                     } else {
                         r=current+(ncArgs.c2==0 ? 1 : 2);
                         trailCC=insertOrdered(source,start, current, r,
-                                              ncArgs.c, ncArgs.c2, cc);
+                                              ncArgs.c1, ncArgs.c2, cc);
                         current=r;
                     }
                 }
@@ -792,1945 +2074,82 @@
             }
 
     }
-    private static int /*unsigned byte*/ mergeOrdered(char[] source,
-                                                      int start,
-                                                      int current,
-                                                      char[] data,
-                                                        final int next,
-                                                        final int limit) {
-        return mergeOrdered(source,start,current,data,next,limit,true);
+
+    private static final class PrevArgs{
+        char[] src;
+        int start;
+        int current;
+        char c1;
+        char c2;
     }
 
-    public static NormalizerBase.QuickCheckResult quickCheck(char[] src,
-                                                            int srcStart,
-                                                            int srcLimit,
-                                                            int minNoMaybe,
-                                                            int qcMask,
-                                                            int options,
-                                                            boolean allowMaybe,
-                                                            UnicodeSet nx){
-
-        int ccOrQCMask;
-        long norm32;
-        char c, c2;
-        char cc, prevCC;
-        long qcNorm32;
-        NormalizerBase.QuickCheckResult result;
-        ComposePartArgs args = new ComposePartArgs();
-        char[] buffer ;
-        int start = srcStart;
-
-        if(!isDataLoaded) {
-            return NormalizerBase.MAYBE;
-        }
-        // initialize
-        ccOrQCMask=CC_MASK|qcMask;
-        result=NormalizerBase.YES;
-        prevCC=0;
-
-        for(;;) {
-            for(;;) {
-                if(srcStart==srcLimit) {
-                    return result;
-                } else if((c=src[srcStart++])>=minNoMaybe &&
-                                  (( norm32=getNorm32(c)) & ccOrQCMask)!=0) {
-                    break;
-                }
-                prevCC=0;
-            }
-
-
-            // check one above-minimum, relevant code unit
-            if(isNorm32LeadSurrogate(norm32)) {
-                // c is a lead surrogate, get the real norm32
-                if(srcStart!=srcLimit&& UTF16.isTrailSurrogate(c2=src[srcStart])) {
-                    ++srcStart;
-                    norm32=getNorm32FromSurrogatePair(norm32,c2);
-                } else {
-                    norm32=0;
-                    c2=0;
-                }
-            }else{
-                c2=0;
-            }
-            if(nx_contains(nx, c, c2)) {
-                /* excluded: norm32==0 */
-                norm32=0;
-            }
-
-            // check the combining order
-            cc=(char)((norm32>>CC_SHIFT)&0xFF);
-            if(cc!=0 && cc<prevCC) {
-                return NormalizerBase.NO;
-            }
-            prevCC=cc;
-
-            // check for "no" or "maybe" quick check flags
-            qcNorm32 = norm32 & qcMask;
-            if((qcNorm32& QC_ANY_NO)>=1) {
-                result= NormalizerBase.NO;
-                break;
-            } else if(qcNorm32!=0) {
-                // "maybe" can only occur for NFC and NFKC
-                if(allowMaybe){
-                    result=NormalizerBase.MAYBE;
-                }else{
-                    // normalize a section around here to see if it is really
-                    // normalized or not
-                    int prevStarter;
-                    int/*unsigned*/ decompQCMask;
-
-                    decompQCMask=(qcMask<<2)&0xf; // decomposition quick check mask
-
-                    // find the previous starter
-
-                    // set prevStarter to the beginning of the current character
-                    prevStarter=srcStart-1;
-                    if(UTF16.isTrailSurrogate(src[prevStarter])) {
-                        // safe because unpaired surrogates do not result
-                        // in "maybe"
-                        --prevStarter;
-                    }
-                    prevStarter=findPreviousStarter(src, start, prevStarter,
-                                                    ccOrQCMask, decompQCMask,
-                                                    (char)minNoMaybe);
-
-                    // find the next true starter in [src..limit[ - modifies
-                    // src to point to the next starter
-                    srcStart=findNextStarter(src,srcStart, srcLimit, qcMask,
-                                             decompQCMask,(char) minNoMaybe);
-
-                    //set the args for compose part
-                    args.prevCC = prevCC;
-
-                    // decompose and recompose [prevStarter..src[
-                    buffer = composePart(args,prevStarter,src,srcStart,srcLimit,options,nx);
-
-                    // compare the normalized version with the original
-                    if(0!=strCompare(buffer,0,args.length,src,prevStarter,srcStart, false)) {
-                        result=NormalizerBase.NO; // normalization differs
-                        break;
-                    }
-
-                    // continue after the next starter
-                }
-            }
-        }
-        return result;
+    private static final class NextCCArgs{
+        char[] source;
+        int next;
+        int limit;
+        char c1;
+        char c2;
     }
 
-
-    //------------------------------------------------------
-    // make NFD & NFKD
-    //------------------------------------------------------
-
-    public static int decompose(char[] src,int srcStart,int srcLimit,
-                                char[] dest,int destStart,int destLimit,
-                                 boolean compat,int[] outTrailCC,
-                                 UnicodeSet nx) {
-
-        char[] buffer = new char[3];
-        int prevSrc;
-        long norm32;
-        int ccOrQCMask, qcMask;
-        int reorderStartIndex, length;
-        char c, c2, minNoMaybe;
-        int/*unsigned byte*/ cc, prevCC, trailCC;
-        char[] p;
-        int pStart;
-        int destIndex = destStart;
-        int srcIndex = srcStart;
-        if(!compat) {
-            minNoMaybe=(char)indexes[INDEX_MIN_NFD_NO_MAYBE];
-            qcMask=QC_NFD;
-        } else {
-            minNoMaybe=(char)indexes[INDEX_MIN_NFKD_NO_MAYBE];
-            qcMask=QC_NFKD;
-        }
-
-        /* initialize */
-        ccOrQCMask=CC_MASK|qcMask;
-        reorderStartIndex=0;
-        prevCC=0;
-        norm32=0;
-        c=0;
-        pStart=0;
-
-        cc=trailCC=-1;//initialize to bogus value
-
-        for(;;) {
-            /* count code units below the minimum or with irrelevant data for
-             * the quick check
-             */
-            prevSrc=srcIndex;
-
-            while(srcIndex!=srcLimit &&((c=src[srcIndex])<minNoMaybe ||
-                                        ((norm32=getNorm32(c))&ccOrQCMask)==0)){
-                prevCC=0;
-                ++srcIndex;
-            }
-
-            /* copy these code units all at once */
-            if(srcIndex!=prevSrc) {
-                length=srcIndex-prevSrc;
-                if((destIndex+length)<=destLimit) {
-                    System.arraycopy(src,prevSrc,dest,destIndex,length);
-                }
-
-                destIndex+=length;
-                reorderStartIndex=destIndex;
-            }
-
-            /* end of source reached? */
-            if(srcIndex==srcLimit) {
-                break;
-            }
-
-            /* c already contains *src and norm32 is set for it, increment src*/
-            ++srcIndex;
-
-            /* check one above-minimum, relevant code unit */
-            /*
-             * generally, set p and length to the decomposition string
-             * in simple cases, p==NULL and (c, c2) will hold the length code
-             * units to append in all cases, set cc to the lead and trailCC to
-             * the trail combining class
-             *
-             * the following merge-sort of the current character into the
-             * preceding, canonically ordered result text will use the
-             * optimized insertOrdered()
-             * if there is only one single code point to process;
-             * this is indicated with p==NULL, and (c, c2) is the character to
-             * insert
-             * ((c, 0) for a BMP character and (lead surrogate, trail surrogate)
-             * for a supplementary character)
-             * otherwise, p[length] is merged in with _mergeOrdered()
-             */
-            if(isNorm32HangulOrJamo(norm32)) {
-                if(nx_contains(nx, c)) {
-                    c2=0;
-                    p=null;
-                    length=1;
-                } else {
-                    // Hangul syllable: decompose algorithmically
-                    p=buffer;
-                    pStart=0;
-                    cc=trailCC=0;
-
-                    c-=HANGUL_BASE;
-
-                    c2=(char)(c%JAMO_T_COUNT);
-                    c/=JAMO_T_COUNT;
-                    if(c2>0) {
-                        buffer[2]=(char)(JAMO_T_BASE+c2);
-                        length=3;
-                    } else {
-                        length=2;
-                    }
-
-                    buffer[1]=(char)(JAMO_V_BASE+c%JAMO_V_COUNT);
-                    buffer[0]=(char)(JAMO_L_BASE+c/JAMO_V_COUNT);
-                }
-            } else {
-                if(isNorm32Regular(norm32)) {
-                    c2=0;
-                    length=1;
-                } else {
-                    // c is a lead surrogate, get the real norm32
-                    if(srcIndex!=srcLimit &&
-                                    UTF16.isTrailSurrogate(c2=src[srcIndex])) {
-                        ++srcIndex;
-                        length=2;
-                        norm32=getNorm32FromSurrogatePair(norm32, c2);
-                    } else {
-                        c2=0;
-                        length=1;
-                        norm32=0;
-                    }
-                }
-
-                /* get the decomposition and the lead and trail cc's */
-                if(nx_contains(nx, c, c2)) {
-                    /* excluded: norm32==0 */
-                    cc=trailCC=0;
-                    p=null;
-                } else if((norm32&qcMask)==0) {
-                    /* c does not decompose */
-                    cc=trailCC=(int)((UNSIGNED_BYTE_MASK) & (norm32>>CC_SHIFT));
-                    p=null;
-                    pStart=-1;
-                } else {
-                    DecomposeArgs arg = new DecomposeArgs();
-                    /* c decomposes, get everything from the variable-length
-                     * extra data
-                     */
-                    pStart=decompose(norm32, qcMask, arg);
-                    p=extraData;
-                    length=arg.length;
-                    cc=arg.cc;
-                    trailCC=arg.trailCC;
-                    if(length==1) {
-                        /* fastpath a single code unit from decomposition */
-                        c=p[pStart];
-                        c2=0;
-                        p=null;
-                        pStart=-1;
-                    }
-                }
-            }
+    private static int /*unsigned*/ getPrevCC(PrevArgs args) {
+        args.c1=args.src[--args.current];
+        args.c2=0;
 
-            /* append the decomposition to the destination buffer, assume
-             * length>0
-             */
-            if((destIndex+length)<=destLimit) {
-                int reorderSplit=destIndex;
-                if(p==null) {
-                    /* fastpath: single code point */
-                    if(cc!=0 && cc<prevCC) {
-                        /* (c, c2) is out of order with respect to the preceding
-                         *  text
-                         */
-                        destIndex+=length;
-                        trailCC=insertOrdered(dest,reorderStartIndex,
-                                            reorderSplit, destIndex, c, c2, cc);
-                    } else {
-                        /* just append (c, c2) */
-                        dest[destIndex++]=c;
-                        if(c2!=0) {
-                            dest[destIndex++]=c2;
-                        }
-                    }
-                } else {
-                    /* general: multiple code points (ordered by themselves)
-                     * from decomposition
-                     */
-                    if(cc!=0 && cc<prevCC) {
-                        /* the decomposition is out of order with respect to the
-                         *  preceding text
-                         */
-                        destIndex+=length;
-                        trailCC=mergeOrdered(dest,reorderStartIndex,
-                                          reorderSplit,p, pStart,pStart+length);
-                    } else {
-                        /* just append the decomposition */
-                        do {
-                            dest[destIndex++]=p[pStart++];
-                        } while(--length>0);
-                    }
-                }
-            } else {
-                /* buffer overflow */
-                /* keep incrementing the destIndex for preflighting */
-                destIndex+=length;
-            }
-
-            prevCC=trailCC;
-            if(prevCC==0) {
-                reorderStartIndex=destIndex;
-            }
-        }
-
-        outTrailCC[0]=prevCC;
-
-        return destIndex - destStart;
-    }
-
-    /* make NFC & NFKC ------------------------------------------------------ */
-    private static final class NextCombiningArgs{
-        char[] source;
-        int start;
-        //int limit;
-        char c;
-        char c2;
-        int/*unsigned*/ combiningIndex;
-        char /*unsigned byte*/ cc;
-    }
-
-    /* get the composition properties of the next character */
-    private static int /*unsigned*/    getNextCombining(NextCombiningArgs args,
-                                                    int limit,
-                                                    UnicodeSet nx) {
-        long/*unsigned*/ norm32;
-        int combineFlags;
-        /* get properties */
-        args.c=args.source[args.start++];
-        norm32=getNorm32(args.c);
-
-        /* preset output values for most characters */
-        args.c2=0;
-        args.combiningIndex=0;
-        args.cc=0;
-
-        if((norm32&(CC_MASK|COMBINES_ANY))==0) {
+        if (args.c1 < MIN_CCC_LCCC_CP) {
+            return 0;
+        } else if (UTF16.isLeadSurrogate(args.c1)) {
+            /* unpaired first surrogate */
             return 0;
+        } else if (!UTF16.isTrailSurrogate(args.c1)) {
+            return UCharacter.getCombiningClass(args.c1);
+        } else if (args.current!=args.start &&
+                    UTF16.isLeadSurrogate(args.c2=args.src[args.current-1])) {
+            --args.current;
+            return UCharacter.getCombiningClass(Character.toCodePoint(args.c2, args.c1));
         } else {
-            if(isNorm32Regular(norm32)) {
-                /* set cc etc. below */
-            } else if(isNorm32HangulOrJamo(norm32)) {
-                /* a compatibility decomposition contained Jamos */
-                args.combiningIndex=(int)((UNSIGNED_INT_MASK)&(0xfff0|
-                                                        (norm32>>EXTRA_SHIFT)));
-                return (int)(norm32&COMBINES_ANY);
-            } else {
-                /* c is a lead surrogate, get the real norm32 */
-                if(args.start!=limit && UTF16.isTrailSurrogate(args.c2=
-                                                     args.source[args.start])) {
-                    ++args.start;
-                    norm32=getNorm32FromSurrogatePair(norm32, args.c2);
-                } else {
-                    args.c2=0;
-                    return 0;
-                }
-            }
-
-            if(nx_contains(nx, args.c, args.c2)) {
-                return 0; /* excluded: norm32==0 */
-            }
-
-            args.cc= (char)((norm32>>CC_SHIFT)&0xff);
-
-            combineFlags=(int)(norm32&COMBINES_ANY);
-            if(combineFlags!=0) {
-                int index = getExtraDataIndex(norm32);
-                args.combiningIndex=index>0 ? extraData[(index-1)] :0;
-            }
-
-            return combineFlags;
-        }
-    }
-
-    /*
-     * given a composition-result starter (c, c2) - which means its cc==0,
-     * it combines forward, it has extra data, its norm32!=0,
-     * it is not a Hangul or Jamo,
-     * get just its combineFwdIndex
-     *
-     * norm32(c) is special if and only if c2!=0
-     */
-    private static int/*unsigned*/ getCombiningIndexFromStarter(char c,char c2){
-        long/*unsigned*/ norm32;
-
-        norm32=getNorm32(c);
-        if(c2!=0) {
-            norm32=getNorm32FromSurrogatePair(norm32, c2);
-        }
-        return extraData[(getExtraDataIndex(norm32)-1)];
-    }
-
-    /*
-     * Find the recomposition result for
-     * a forward-combining character
-     * (specified with a pointer to its part of the combiningTable[])
-     * and a backward-combining character
-     * (specified with its combineBackIndex).
-     *
-     * If these two characters combine, then set (value, value2)
-     * with the code unit(s) of the composition character.
-     *
-     * Return value:
-     * 0    do not combine
-     * 1    combine
-     * >1   combine, and the composition is a forward-combining starter
-     *
-     * See unormimp.h for a description of the composition table format.
-     */
-    private static int/*unsigned*/ combine(char[]table,int tableStart,
-                                   int/*unsinged*/ combineBackIndex,
-                                    int[] outValues) {
-        int/*unsigned*/ key;
-        int value,value2;
-
-        if(outValues.length<2){
-            throw new IllegalArgumentException();
-        }
-
-        /* search in the starter's composition table */
-        for(;;) {
-            key=table[tableStart++];
-            if(key>=combineBackIndex) {
-                break;
-            }
-            tableStart+= ((table[tableStart]&0x8000) != 0)? 2 : 1;
-        }
-
-        /* mask off bit 15, the last-entry-in-the-list flag */
-        if((key&0x7fff)==combineBackIndex) {
-            /* found! combine! */
-            value=table[tableStart];
-
-            /* is the composition a starter that combines forward? */
-            key=(int)((UNSIGNED_INT_MASK)&((value&0x2000)+1));
-
-            /* get the composition result code point from the variable-length
-             * result value
-             */
-            if((value&0x8000) != 0) {
-                if((value&0x4000) != 0) {
-                    /* surrogate pair composition result */
-                    value=(int)((UNSIGNED_INT_MASK)&((value&0x3ff)|0xd800));
-                    value2=table[tableStart+1];
-                } else {
-                    /* BMP composition result U+2000..U+ffff */
-                    value=table[tableStart+1];
-                    value2=0;
-                }
-            } else {
-                /* BMP composition result U+0000..U+1fff */
-                value&=0x1fff;
-                value2=0;
-            }
-            outValues[0]=value;
-            outValues[1]=value2;
-            return key;
-        } else {
-            /* not found */
+            /* unpaired second surrogate */
+            args.c2=0;
             return 0;
         }
     }
 
-
-    private static final class RecomposeArgs{
-        char[] source;
-        int start;
-        int limit;
-    }
-    /*
-     * recompose the characters in [p..limit[
-     * (which is in NFD - decomposed and canonically ordered),
-     * adjust limit, and return the trailing cc
-     *
-     * since for NFKC we may get Jamos in decompositions, we need to
-     * recompose those too
-     *
-     * note that recomposition never lengthens the text:
-     * any character consists of either one or two code units;
-     * a composition may contain at most one more code unit than the original
-     * starter, while the combining mark that is removed has at least one code
-     * unit
-     */
-    private static char/*unsigned byte*/ recompose(RecomposeArgs args, int options, UnicodeSet nx) {
-        int  remove, q, r;
-        int /*unsigned*/ combineFlags;
-        int /*unsigned*/ combineFwdIndex, combineBackIndex;
-        int /*unsigned*/ result, value=0, value2=0;
-        int /*unsigned byte*/  prevCC;
-        boolean starterIsSupplementary;
-        int starter;
-        int[] outValues = new int[2];
-        starter=-1;                   /* no starter */
-        combineFwdIndex=0;            /* will not be used until starter!=NULL */
-        starterIsSupplementary=false; /* will not be used until starter!=NULL */
-        prevCC=0;
-
-        NextCombiningArgs ncArg = new NextCombiningArgs();
-        ncArg.source  = args.source;
-
-        ncArg.cc      =0;
-        ncArg.c2      =0;
-
-        for(;;) {
-            ncArg.start = args.start;
-            combineFlags=getNextCombining(ncArg,args.limit,nx);
-            combineBackIndex=ncArg.combiningIndex;
-            args.start = ncArg.start;
-
-            if(((combineFlags&COMBINES_BACK)!=0) && starter!=-1) {
-                if((combineBackIndex&0x8000)!=0) {
-                    /* c is a Jamo V/T, see if we can compose it with the
-                     * previous character
-                     */
-                    /* for the PRI #29 fix, check that there is no intervening combining mark */
-                    if((options&BEFORE_PRI_29)!=0 || prevCC==0) {
-                        remove=-1; /* NULL while no Hangul composition */
-                        combineFlags=0;
-                        ncArg.c2=args.source[starter];
-                        if(combineBackIndex==0xfff2) {
-                            /* Jamo V, compose with previous Jamo L and following
-                             * Jamo T
-                             */
-                            ncArg.c2=(char)(ncArg.c2-JAMO_L_BASE);
-                            if(ncArg.c2<JAMO_L_COUNT) {
-                                remove=args.start-1;
-                                ncArg.c=(char)(HANGUL_BASE+(ncArg.c2*JAMO_V_COUNT+
-                                               (ncArg.c-JAMO_V_BASE))*JAMO_T_COUNT);
-                                if(args.start!=args.limit &&
-                                            (ncArg.c2=(char)(args.source[args.start]
-                                             -JAMO_T_BASE))<JAMO_T_COUNT) {
-                                    ++args.start;
-                                    ncArg.c+=ncArg.c2;
-                                 } else {
-                                     /* the result is an LV syllable, which is a starter (unlike LVT) */
-                                     combineFlags=COMBINES_FWD;
-                                }
-                                if(!nx_contains(nx, ncArg.c)) {
-                                    args.source[starter]=ncArg.c;
-                                   } else {
-                                    /* excluded */
-                                    if(!isHangulWithoutJamoT(ncArg.c)) {
-                                        --args.start; /* undo the ++args.start from reading the Jamo T */
-                                    }
-                                    /* c is modified but not used any more -- c=*(p-1); -- re-read the Jamo V/T */
-                                    remove=args.start;
-                                }
-                            }
-
-                        /*
-                         * Normally, the following can not occur:
-                         * Since the input is in NFD, there are no Hangul LV syllables that
-                         * a Jamo T could combine with.
-                         * All Jamo Ts are combined above when handling Jamo Vs.
-                         *
-                         * However, before the PRI #29 fix, this can occur due to
-                         * an intervening combining mark between the Hangul LV and the Jamo T.
-                         */
-                        } else {
-                            /* Jamo T, compose with previous Hangul that does not have a Jamo T */
-                            if(isHangulWithoutJamoT(ncArg.c2)) {
-                                ncArg.c2+=ncArg.c-JAMO_T_BASE;
-                                if(!nx_contains(nx, ncArg.c2)) {
-                                    remove=args.start-1;
-                                    args.source[starter]=ncArg.c2;
-                                }
-                            }
-                        }
-
-                        if(remove!=-1) {
-                            /* remove the Jamo(s) */
-                            q=remove;
-                            r=args.start;
-                            while(r<args.limit) {
-                                args.source[q++]=args.source[r++];
-                            }
-                            args.start=remove;
-                            args.limit=q;
-                        }
-
-                        ncArg.c2=0; /* c2 held *starter temporarily */
-
-                        if(combineFlags!=0) {
-                            /*
-                             * not starter=NULL because the composition is a Hangul LV syllable
-                             * and might combine once more (but only before the PRI #29 fix)
-                             */
+    private static int /*unsigned byte*/ getNextCC(NextCCArgs args) {
+        args.c1=args.source[args.next++];
+        args.c2=0;
 
-                            /* done? */
-                            if(args.start==args.limit) {
-                                return (char)prevCC;
-                            }
-
-                            /* the composition is a Hangul LV syllable which is a starter that combines forward */
-                            combineFwdIndex=0xfff0;
-
-                            /* we combined; continue with looking for compositions */
-                            continue;
-                        }
-                    }
-
-                    /*
-                     * now: cc==0 and the combining index does not include
-                     * "forward" -> the rest of the loop body will reset starter
-                     * to NULL; technically, a composed Hangul syllable is a
-                     * starter, but it does not combine forward now that we have
-                     * consumed all eligible Jamos; for Jamo V/T, combineFlags
-                     * does not contain _NORM_COMBINES_FWD
-                     */
-
-                } else if(
-                    /* the starter is not a Hangul LV or Jamo V/T and */
-                    !((combineFwdIndex&0x8000)!=0) &&
-                    /* the combining mark is not blocked and */
-                    ((options&BEFORE_PRI_29)!=0 ?
-                        (prevCC!=ncArg.cc || prevCC==0) :
-                        (prevCC<ncArg.cc || prevCC==0)) &&
-                    /* the starter and the combining mark (c, c2) do combine */
-                    0!=(result=combine(combiningTable,combineFwdIndex,
-                                       combineBackIndex, outValues)) &&
-                    /* the composition result is not excluded */
-                    !nx_contains(nx, (char)value, (char)value2)
-                ) {
-                    value=outValues[0];
-                    value2=outValues[1];
-                    /* replace the starter with the composition, remove the
-                     * combining mark
-                     */
-                    remove= ncArg.c2==0 ? args.start-1 : args.start-2; /* index to the combining mark */
-
-                    /* replace the starter with the composition */
-                    args.source[starter]=(char)value;
-                    if(starterIsSupplementary) {
-                        if(value2!=0) {
-                            /* both are supplementary */
-                            args.source[starter+1]=(char)value2;
-                        } else {
-                            /* the composition is shorter than the starter,
-                             * move the intermediate characters forward one */
-                            starterIsSupplementary=false;
-                            q=starter+1;
-                            r=q+1;
-                            while(r<remove) {
-                                args.source[q++]=args.source[r++];
-                            }
-                            --remove;
-                        }
-                    } else if(value2!=0) { // for U+1109A, U+1109C, and U+110AB
-                        starterIsSupplementary=true;
-                        args.source[starter+1]=(char)value2;
-                    /* } else { both are on the BMP, nothing more to do */
-                    }
-
-                    /* remove the combining mark by moving the following text
-                     * over it */
-                    if(remove<args.start) {
-                        q=remove;
-                        r=args.start;
-                        while(r<args.limit) {
-                            args.source[q++]=args.source[r++];
-                        }
-                        args.start=remove;
-                        args.limit=q;
-                    }
-
-                    /* keep prevCC because we removed the combining mark */
-
-                    /* done? */
-                    if(args.start==args.limit) {
-                        return (char)prevCC;
-                    }
-
-                    /* is the composition a starter that combines forward? */
-                    if(result>1) {
-                       combineFwdIndex=getCombiningIndexFromStarter((char)value,
-                                                                  (char)value2);
-                    } else {
-                       starter=-1;
-                    }
-
-                    /* we combined; continue with looking for compositions */
-                    continue;
-                }
-            }
-
-            /* no combination this time */
-            prevCC=ncArg.cc;
-            if(args.start==args.limit) {
-                return (char)prevCC;
-            }
-
-            /* if (c, c2) did not combine, then check if it is a starter */
-            if(ncArg.cc==0) {
-                /* found a new starter; combineFlags==0 if (c, c2) is excluded */
-                if((combineFlags&COMBINES_FWD)!=0) {
-                    /* it may combine with something, prepare for it */
-                    if(ncArg.c2==0) {
-                        starterIsSupplementary=false;
-                        starter=args.start-1;
-                    } else {
-                        starterIsSupplementary=false;
-                        starter=args.start-2;
-                    }
-                    combineFwdIndex=combineBackIndex;
-                } else {
-                    /* it will not combine with anything */
-                    starter=-1;
-                }
-            } else if((options&OPTIONS_COMPOSE_CONTIGUOUS)!=0) {
-                /* FCC: no discontiguous compositions; any intervening character blocks */
-                starter=-1;
-            }
+        if (UTF16.isTrailSurrogate(args.c1)) {
+            /* unpaired second surrogate */
+            return 0;
+        } else if (!UTF16.isLeadSurrogate(args.c1)) {
+            return UCharacter.getCombiningClass(args.c1);
+        } else if (args.next!=args.limit &&
+                        UTF16.isTrailSurrogate(args.c2=args.source[args.next])){
+            ++args.next;
+            return UCharacter.getCombiningClass(Character.toCodePoint(args.c1, args.c2));
+        } else {
+            /* unpaired first surrogate */
+            args.c2=0;
+            return 0;
         }
     }
 
-    // find the last true starter between src[start]....src[current] going
-    // backwards and return its index
-    private static int findPreviousStarter(char[]src, int srcStart, int current,
-                                          int/*unsigned*/ ccOrQCMask,
-                                          int/*unsigned*/ decompQCMask,
-                                          char minNoMaybe) {
-       long norm32;
-       PrevArgs args = new PrevArgs();
-       args.src = src;
-       args.start = srcStart;
-       args.current = current;
-
-       while(args.start<args.current) {
-           norm32= getPrevNorm32(args, minNoMaybe, ccOrQCMask|decompQCMask);
-           if(isTrueStarter(norm32, ccOrQCMask, decompQCMask)) {
-               break;
-           }
-       }
-       return args.current;
-    }
-
-    /* find the first true starter in [src..limit[ and return the
-     * pointer to it
-     */
-    private static int/*index*/    findNextStarter(char[] src,int start,int limit,
-                                                 int/*unsigned*/ qcMask,
-                                                 int/*unsigned*/ decompQCMask,
-                                                 char minNoMaybe) {
-        int p;
-        long/*unsigned*/ norm32;
-        int ccOrQCMask;
-        char c, c2;
-
-        ccOrQCMask=CC_MASK|qcMask;
-
-        DecomposeArgs decompArgs = new DecomposeArgs();
-
-        for(;;) {
-            if(start==limit) {
-                break; /* end of string */
-            }
-            c=src[start];
-            if(c<minNoMaybe) {
-                break; /* catches NUL terminater, too */
-            }
-
-            norm32=getNorm32(c);
-            if((norm32&ccOrQCMask)==0) {
-                break; /* true starter */
-            }
-
-            if(isNorm32LeadSurrogate(norm32)) {
-                /* c is a lead surrogate, get the real norm32 */
-                if((start+1)==limit ||
-                                   !UTF16.isTrailSurrogate(c2=(src[start+1]))){
-                    /* unmatched first surrogate: counts as a true starter */
-                    break;
-                }
-                norm32=getNorm32FromSurrogatePair(norm32, c2);
-
-                if((norm32&ccOrQCMask)==0) {
-                    break; /* true starter */
-                }
-            } else {
-                c2=0;
-            }
-
-            /* (c, c2) is not a true starter but its decomposition may be */
-            if((norm32&decompQCMask)!=0) {
-                /* (c, c2) decomposes, get everything from the variable-length
-                 *  extra data */
-                p=decompose(norm32, decompQCMask, decompArgs);
-
-                /* get the first character's norm32 to check if it is a true
-                 * starter */
-                if(decompArgs.cc==0 && (getNorm32(extraData,p, qcMask)&qcMask)==0) {
-                    break; /* true starter */
-                }
-            }
-
-            start+= c2==0 ? 1 : 2; /* not a true starter, continue */
-        }
-
-        return start;
-    }
-
-
-    private static final class ComposePartArgs{
-        int prevCC;
-        int length;   /* length of decomposed part */
-    }
-
-     /* decompose and recompose [prevStarter..src[ */
-    private static char[] composePart(ComposePartArgs args,
-                                      int prevStarter,
-                                         char[] src, int start, int limit,
-                                       int options,
-                                       UnicodeSet nx) {
-        int recomposeLimit;
-        boolean compat =((options&OPTIONS_COMPAT)!=0);
-
-        /* decompose [prevStarter..src[ */
-        int[] outTrailCC = new int[1];
-        char[] buffer = new char[(limit-prevStarter)*MAX_BUFFER_SIZE];
-
-        for(;;){
-            args.length=decompose(src,prevStarter,(start),
-                                      buffer,0,buffer.length,
-                                      compat,outTrailCC,nx);
-            if(args.length<=buffer.length){
-                break;
-            }else{
-                buffer = new char[args.length];
-            }
-        }
-
-        /* recompose the decomposition */
-        recomposeLimit=args.length;
-
-        if(args.length>=2) {
-            RecomposeArgs rcArgs = new RecomposeArgs();
-            rcArgs.source    = buffer;
-            rcArgs.start    = 0;
-            rcArgs.limit    = recomposeLimit;
-            args.prevCC=recompose(rcArgs, options, nx);
-            recomposeLimit = rcArgs.limit;
-        }
-
-        /* return with a pointer to the recomposition and its length */
-        args.length=recomposeLimit;
-        return buffer;
-    }
-
-    private static boolean composeHangul(char prev, char c,
-                                         long/*unsigned*/ norm32,
-                                         char[] src,int[] srcIndex, int limit,
-                                            boolean compat,
-                                         char[] dest,int destIndex,
-                                         UnicodeSet nx) {
-        int start=srcIndex[0];
-        if(isJamoVTNorm32JamoV(norm32)) {
-            /* c is a Jamo V, compose with previous Jamo L and
-             * following Jamo T */
-            prev=(char)(prev-JAMO_L_BASE);
-            if(prev<JAMO_L_COUNT) {
-                c=(char)(HANGUL_BASE+(prev*JAMO_V_COUNT+
-                                                 (c-JAMO_V_BASE))*JAMO_T_COUNT);
-
-                /* check if the next character is a Jamo T (normal or
-                 * compatibility) */
-                if(start!=limit) {
-                    char next, t;
-
-                    next=src[start];
-                    if((t=(char)(next-JAMO_T_BASE))<JAMO_T_COUNT) {
-                        /* normal Jamo T */
-                        ++start;
-                        c+=t;
-                    } else if(compat) {
-                        /* if NFKC, then check for compatibility Jamo T
-                         * (BMP only) */
-                        norm32=getNorm32(next);
-                        if(isNorm32Regular(norm32) && ((norm32&QC_NFKD)!=0)) {
-                            int p /*index into extra data array*/;
-                            DecomposeArgs dcArgs = new DecomposeArgs();
-                            p=decompose(norm32, QC_NFKD, dcArgs);
-                            if(dcArgs.length==1 &&
-                                   (t=(char)(extraData[p]-JAMO_T_BASE))
-                                                   <JAMO_T_COUNT) {
-                                /* compatibility Jamo T */
-                                ++start;
-                                c+=t;
-                            }
-                        }
-                    }
-                }
-                if(nx_contains(nx, c)) {
-                    if(!isHangulWithoutJamoT(c)) {
-                        --start; /* undo ++start from reading the Jamo T */
-                    }
-                    return false;
-                }
-                dest[destIndex]=c;
-                srcIndex[0]=start;
-                return true;
-            }
-        } else if(isHangulWithoutJamoT(prev)) {
-            /* c is a Jamo T, compose with previous Hangul LV that does not
-             * contain a Jamo T */
-            c=(char)(prev+(c-JAMO_T_BASE));
-            if(nx_contains(nx, c)) {
-                return false;
-            }
-            dest[destIndex]=c;
-            srcIndex[0]=start;
-            return true;
-        }
-        return false;
-    }
-    /*
-    public static int compose(char[] src, char[] dest,boolean compat, UnicodeSet nx){
-        return compose(src,0,src.length,dest,0,dest.length,compat, nx);
-    }
-    */
-
-    public static int compose(char[] src, int srcStart, int srcLimit,
-                              char[] dest,int destStart,int destLimit,
-                              int options,UnicodeSet nx) {
-
-        int prevSrc, prevStarter;
-        long/*unsigned*/ norm32;
-        int ccOrQCMask, qcMask;
-        int  reorderStartIndex, length;
-        char c, c2, minNoMaybe;
-        int/*unsigned byte*/ cc, prevCC;
-        int[] ioIndex = new int[1];
-        int destIndex = destStart;
-        int srcIndex = srcStart;
-
-        if((options&OPTIONS_COMPAT)!=0) {
-            minNoMaybe=(char)indexes[INDEX_MIN_NFKC_NO_MAYBE];
-            qcMask=QC_NFKC;
-        } else {
-            minNoMaybe=(char)indexes[INDEX_MIN_NFC_NO_MAYBE];
-            qcMask=QC_NFC;
-        }
-
-        /*
-         * prevStarter points to the last character before the current one
-         * that is a "true" starter with cc==0 and quick check "yes".
-         *
-         * prevStarter will be used instead of looking for a true starter
-         * while incrementally decomposing [prevStarter..prevSrc[
-         * in _composePart(). Having a good prevStarter allows to just decompose
-         * the entire [prevStarter..prevSrc[.
-         *
-         * When _composePart() backs out from prevSrc back to prevStarter,
-         * then it also backs out destIndex by the same amount.
-         * Therefore, at all times, the (prevSrc-prevStarter) source units
-         * must correspond 1:1 to destination units counted with destIndex,
-         * except for reordering.
-         * This is true for the qc "yes" characters copied in the fast loop,
-         * and for pure reordering.
-         * prevStarter must be set forward to src when this is not true:
-         * In _composePart() and after composing a Hangul syllable.
-         *
-         * This mechanism relies on the assumption that the decomposition of a
-         * true starter also begins with a true starter. gennorm/store.c checks
-         * for this.
-         */
-        prevStarter=srcIndex;
-
-        ccOrQCMask=CC_MASK|qcMask;
-        /*destIndex=*/reorderStartIndex=0;/* ####TODO#### check this **/
-        prevCC=0;
-
-        /* avoid compiler warnings */
-        norm32=0;
-        c=0;
-
-        for(;;) {
-            /* count code units below the minimum or with irrelevant data for
-             * the quick check */
-            prevSrc=srcIndex;
-
-            while(srcIndex!=srcLimit && ((c=src[srcIndex])<minNoMaybe ||
-                     ((norm32=getNorm32(c))&ccOrQCMask)==0)) {
-                prevCC=0;
-                ++srcIndex;
-            }
-
-
-            /* copy these code units all at once */
-            if(srcIndex!=prevSrc) {
-                length=srcIndex-prevSrc;
-                if((destIndex+length)<=destLimit) {
-                    System.arraycopy(src,prevSrc,dest,destIndex,length);
-                }
-                destIndex+=length;
-                reorderStartIndex=destIndex;
-
-                /* set prevStarter to the last character in the quick check
-                 * loop */
-                prevStarter=srcIndex-1;
-                if(UTF16.isTrailSurrogate(src[prevStarter]) &&
-                    prevSrc<prevStarter &&
-                    UTF16.isLeadSurrogate(src[(prevStarter-1)])) {
-                    --prevStarter;
-                }
-
-                prevSrc=srcIndex;
-            }
-
-            /* end of source reached? */
-            if(srcIndex==srcLimit) {
-                break;
-            }
+    private VersionInfo dataVersion;
 
-            /* c already contains *src and norm32 is set for it, increment src*/
-            ++srcIndex;
-
-            /*
-             * source buffer pointers:
-             *
-             *  all done      quick check   current char  not yet
-             *                "yes" but     (c, c2)       processed
-             *                may combine
-             *                forward
-             * [-------------[-------------[-------------[-------------[
-             * |             |             |             |             |
-             * start         prevStarter   prevSrc       src           limit
-             *
-             *
-             * destination buffer pointers and indexes:
-             *
-             *  all done      might take    not filled yet
-             *                characters for
-             *                reordering
-             * [-------------[-------------[-------------[
-             * |             |             |             |
-             * dest      reorderStartIndex destIndex     destCapacity
-             */
-
-            /* check one above-minimum, relevant code unit */
-            /*
-             * norm32 is for c=*(src-1), and the quick check flag is "no" or
-             * "maybe", and/or cc!=0
-             * check for Jamo V/T, then for surrogates and regular characters
-             * c is not a Hangul syllable or Jamo L because
-             * they are not marked with no/maybe for NFC & NFKC(and their cc==0)
-             */
-            if(isNorm32HangulOrJamo(norm32)) {
-                /*
-                 * c is a Jamo V/T:
-                 * try to compose with the previous character, Jamo V also with
-                 * a following Jamo T, and set values here right now in case we
-                 * just continue with the main loop
-                 */
-                prevCC=cc=0;
-                reorderStartIndex=destIndex;
-                ioIndex[0]=srcIndex;
-                if(
-                    destIndex>0 &&
-                    composeHangul(src[(prevSrc-1)], c, norm32,src, ioIndex,
-                                  srcLimit, (options&OPTIONS_COMPAT)!=0, dest,
-                                  destIndex<=destLimit ? destIndex-1: 0,
-                                  nx)
-                ) {
-                    srcIndex=ioIndex[0];
-                    prevStarter=srcIndex;
-                    continue;
-                }
-
-                srcIndex = ioIndex[0];
-
-                /* the Jamo V/T did not compose into a Hangul syllable, just
-                 * append to dest */
-                c2=0;
-                length=1;
-                prevStarter=prevSrc;
-            } else {
-                if(isNorm32Regular(norm32)) {
-                    c2=0;
-                    length=1;
-                } else {
-                    /* c is a lead surrogate, get the real norm32 */
-                    if(srcIndex!=srcLimit &&
-                                     UTF16.isTrailSurrogate(c2=src[srcIndex])) {
-                        ++srcIndex;
-                        length=2;
-                        norm32=getNorm32FromSurrogatePair(norm32, c2);
-                    } else {
-                        /* c is an unpaired lead surrogate, nothing to do */
-                        c2=0;
-                        length=1;
-                        norm32=0;
-                    }
-                }
-                ComposePartArgs args =new ComposePartArgs();
-
-                /* we are looking at the character (c, c2) at [prevSrc..src[ */
-                if(nx_contains(nx, c, c2)) {
-                    /* excluded: norm32==0 */
-                    cc=0;
-                } else if((norm32&qcMask)==0) {
-                    cc=(int)((UNSIGNED_BYTE_MASK)&(norm32>>CC_SHIFT));
-                } else {
-                    char[] p;
-
-                    /*
-                     * find appropriate boundaries around this character,
-                     * decompose the source text from between the boundaries,
-                     * and recompose it
-                     *
-                     * this puts the intermediate text into the side buffer because
-                     * it might be longer than the recomposition end result,
-                     * or the destination buffer may be too short or missing
-                     *
-                     * note that destIndex may be adjusted backwards to account
-                     * for source text that passed the quick check but needed to
-                     * take part in the recomposition
-                     */
-                    int decompQCMask=(qcMask<<2)&0xf; /* decomposition quick check mask */
-                    /*
-                     * find the last true starter in [prevStarter..src[
-                     * it is either the decomposition of the current character (at prevSrc),
-                     * or prevStarter
-                     */
-                    if(isTrueStarter(norm32, CC_MASK|qcMask, decompQCMask)) {
-                        prevStarter=prevSrc;
-                    } else {
-                        /* adjust destIndex: back out what had been copied with qc "yes" */
-                        destIndex-=prevSrc-prevStarter;
-                    }
-
-                    /* find the next true starter in [src..limit[ */
-                    srcIndex=findNextStarter(src, srcIndex,srcLimit, qcMask,
-                                               decompQCMask, minNoMaybe);
-                    //args.prevStarter = prevStarter;
-                    args.prevCC    = prevCC;
-                    //args.destIndex = destIndex;
-                    args.length = length;
-                    p=composePart(args,prevStarter,src,srcIndex,srcLimit,options,nx);
-
-                    if(p==null) {
-                        /* an error occurred (out of memory) */
-                        break;
-                    }
-
-                    prevCC      = args.prevCC;
-                    length      = args.length;
-
-                    /* append the recomposed buffer contents to the destination
-                     * buffer */
-                    if((destIndex+args.length)<=destLimit) {
-                        int i=0;
-                        while(i<args.length) {
-                            dest[destIndex++]=p[i++];
-                            --length;
-                        }
-                    } else {
-                        /* buffer overflow */
-                        /* keep incrementing the destIndex for preflighting */
-                        destIndex+=length;
-                    }
-
-                    prevStarter=srcIndex;
-                    continue;
-                }
-            }
-
-            /* append the single code point (c, c2) to the destination buffer */
-            if((destIndex+length)<=destLimit) {
-                if(cc!=0 && cc<prevCC) {
-                    /* (c, c2) is out of order with respect to the preceding
-                     * text */
-                    int reorderSplit= destIndex;
-                    destIndex+=length;
-                    prevCC=insertOrdered(dest,reorderStartIndex, reorderSplit,
-                                         destIndex, c, c2, cc);
-                } else {
-                    /* just append (c, c2) */
-                    dest[destIndex++]=c;
-                    if(c2!=0) {
-                        dest[destIndex++]=c2;
-                    }
-                    prevCC=cc;
-                }
-            } else {
-                /* buffer overflow */
-                /* keep incrementing the destIndex for preflighting */
-                destIndex+=length;
-                prevCC=cc;
-            }
-        }
-
-        return destIndex - destStart;
-    }
-
-    public static int getCombiningClass(int c) {
-        long norm32;
-        norm32=getNorm32(c);
-        return (int)((norm32>>CC_SHIFT)&0xFF);
-    }
-
-    public static boolean isFullCompositionExclusion(int c) {
-        if(isFormatVersion_2_1) {
-            int aux =AuxTrieImpl.auxTrie.getCodePointValue(c);
-            return (aux & AUX_COMP_EX_MASK)!=0;
-        } else {
-            return false;
-        }
-    }
-
-    public static boolean isCanonSafeStart(int c) {
-        if(isFormatVersion_2_1) {
-            int aux = AuxTrieImpl.auxTrie.getCodePointValue(c);
-            return (aux & AUX_UNSAFE_MASK)==0;
-        } else {
-            return false;
-        }
-    }
-
-    /* Is c an NF<mode>-skippable code point? See unormimp.h. */
-    public static boolean isNFSkippable(int c, NormalizerBase.Mode mode, long mask) {
-        long /*unsigned int*/ norm32;
-        mask = mask & UNSIGNED_INT_MASK;
-        char aux;
-
-        /* check conditions (a)..(e), see unormimp.h */
-        norm32 = getNorm32(c);
-
-        if((norm32&mask)!=0) {
-            return false; /* fails (a)..(e), not skippable */
-        }
-
-        if(mode == NormalizerBase.NFD || mode == NormalizerBase.NFKD || mode == NormalizerBase.NONE){
-            return true; /* NF*D, passed (a)..(c), is skippable */
-        }
-        /* check conditions (a)..(e), see unormimp.h */
-
-        /* NF*C/FCC, passed (a)..(e) */
-        if((norm32& QC_NFD)==0) {
-            return true; /* no canonical decomposition, is skippable */
-        }
-
-        /* check Hangul syllables algorithmically */
-        if(isNorm32HangulOrJamo(norm32)) {
-            /* Jamo passed (a)..(e) above, must be Hangul */
-            return !isHangulWithoutJamoT((char)c); /* LVT are skippable, LV are not */
-        }
-
-        /* if(mode<=UNORM_NFKC) { -- enable when implementing FCC */
-        /* NF*C, test (f) flag */
-        if(!isFormatVersion_2_2) {
-            return false; /* no (f) data, say not skippable to be safe */
-        }
-
-
-        aux = AuxTrieImpl.auxTrie.getCodePointValue(c);
-        return (aux&AUX_NFC_SKIP_F_MASK)==0; /* TRUE=skippable if the (f) flag is not set */
-
-        /* } else { FCC, test fcd<=1 instead of the above } */
-    }
-
-    public static UnicodeSet addPropertyStarts(UnicodeSet set) {
-        int c;
-
-        /* add the start code point of each same-value range of each trie */
-        //utrie_enum(&normTrie, NULL, _enumPropertyStartsRange, set);
-        TrieIterator normIter = new TrieIterator(NormTrieImpl.normTrie);
-        RangeValueIterator.Element normResult = new RangeValueIterator.Element();
-
-        while(normIter.next(normResult)){
-            set.add(normResult.start);
-        }
-
-        //utrie_enum(&fcdTrie, NULL, _enumPropertyStartsRange, set);
-        TrieIterator fcdIter  = new TrieIterator(FCDTrieImpl.fcdTrie);
-        RangeValueIterator.Element fcdResult = new RangeValueIterator.Element();
-
-        while(fcdIter.next(fcdResult)){
-            set.add(fcdResult.start);
-        }
-
-        if(isFormatVersion_2_1){
-            //utrie_enum(&auxTrie, NULL, _enumPropertyStartsRange, set);
-            TrieIterator auxIter  = new TrieIterator(AuxTrieImpl.auxTrie);
-            RangeValueIterator.Element auxResult = new RangeValueIterator.Element();
-            while(auxIter.next(auxResult)){
-                set.add(auxResult.start);
-            }
-        }
-        /* add Hangul LV syllables and LV+1 because of skippables */
-        for(c=HANGUL_BASE; c<HANGUL_BASE+HANGUL_COUNT; c+=JAMO_T_COUNT) {
-            set.add(c);
-            set.add(c+1);
-        }
-        set.add(HANGUL_BASE+HANGUL_COUNT); /* add Hangul+1 to continue with other properties */
-        return set; // for chaining
-    }
-
-    /**
-     * Internal API, used in UCharacter.getIntPropertyValue().
-     * @internal
-     * @param c code point
-     * @param modeValue numeric value compatible with Mode
-     * @return numeric value compatible with QuickCheck
-     */
-    public static final int quickCheck(int c, int modeValue) {
-        final int qcMask[/*UNORM_MODE_COUNT*/]={
-            0, 0, QC_NFD, QC_NFKD, QC_NFC, QC_NFKC
-        };
-
-        int norm32=(int)getNorm32(c)&qcMask[modeValue];
+    // Code point thresholds for quick check codes.
+    private int minDecompNoCP;
+    private int minCompNoMaybeCP;
 
-        if(norm32==0) {
-            return 1; // YES
-        } else if((norm32&QC_ANY_NO)!=0) {
-            return 0; // NO
-        } else /* _NORM_QC_ANY_MAYBE */ {
-            return 2; // MAYBE;
-        }
-    }
-
-    private static int strCompare(char[] s1, int s1Start, int s1Limit,
-                                  char[] s2, int s2Start, int s2Limit,
-                                  boolean codePointOrder) {
-
-        int start1, start2, limit1, limit2;
-
-        char c1, c2;
-
-        /* setup for fix-up */
-        start1=s1Start;
-        start2=s2Start;
-
-        int length1, length2;
-
-        length1 = s1Limit - s1Start;
-        length2 = s2Limit - s2Start;
-
-        int lengthResult;
-
-        if(length1<length2) {
-            lengthResult=-1;
-            limit1=start1+length1;
-        } else if(length1==length2) {
-            lengthResult=0;
-            limit1=start1+length1;
-        } else /* length1>length2 */ {
-            lengthResult=1;
-            limit1=start1+length2;
-        }
-
-        if(s1==s2) {
-            return lengthResult;
-        }
-
-        for(;;) {
-            /* check pseudo-limit */
-            if(s1Start==limit1) {
-                return lengthResult;
-            }
-
-            c1=s1[s1Start];
-            c2=s2[s2Start];
-            if(c1!=c2) {
-                break;
-            }
-            ++s1Start;
-            ++s2Start;
-        }
-
-        /* setup for fix-up */
-        limit1=start1+length1;
-        limit2=start2+length2;
-
-
-        /* if both values are in or above the surrogate range, fix them up */
-        if(c1>=0xd800 && c2>=0xd800 && codePointOrder) {
-            /* subtract 0x2800 from BMP code points to make them smaller than
-             *  supplementary ones */
-            if(
-                ( c1<=0xdbff && (s1Start+1)!=limit1 &&
-                  UTF16.isTrailSurrogate(s1[(s1Start+1)])
-                ) ||
-                ( UTF16.isTrailSurrogate(c1) && start1!=s1Start &&
-                  UTF16.isLeadSurrogate(s1[(s1Start-1)])
-                )
-            ) {
-                /* part of a surrogate pair, leave >=d800 */
-            } else {
-                /* BMP code point - may be surrogate code point - make <d800 */
-                c1-=0x2800;
-            }
-
-            if(
-                ( c2<=0xdbff && (s2Start+1)!=limit2 &&
-                  UTF16.isTrailSurrogate(s2[(s2Start+1)])
-                ) ||
-                ( UTF16.isTrailSurrogate(c2) && start2!=s2Start &&
-                  UTF16.isLeadSurrogate(s2[(s2Start-1)])
-                )
-            ) {
-                /* part of a surrogate pair, leave >=d800 */
-            } else {
-                /* BMP code point - may be surrogate code point - make <d800 */
-                c2-=0x2800;
-            }
-        }
-
-        /* now c1 and c2 are in UTF-32-compatible order */
-        return (int)c1-(int)c2;
-    }
-
-
-    /*
-     * Status of tailored normalization
-     *
-     * This was done initially for investigation on Unicode public review issue 7
-     * (http://www.unicode.org/review/). See Jitterbug 2481.
-     * While the UTC at meeting #94 (2003mar) did not take up the issue, this is
-     * a permanent feature in ICU 2.6 in support of IDNA which requires true
-     * Unicode 3.2 normalization.
-     * (NormalizationCorrections are rolled into IDNA mapping tables.)
-     *
-     * Tailored normalization as implemented here allows to "normalize less"
-     * than full Unicode normalization would.
-     * Based internally on a UnicodeSet of code points that are
-     * "excluded from normalization", the normalization functions leave those
-     * code points alone ("inert"). This means that tailored normalization
-     * still transforms text into a canonically equivalent form.
-     * It does not add decompositions to code points that do not have any or
-     * change decomposition results.
-     *
-     * Any function that searches for a safe boundary has not been touched,
-     * which means that these functions will be over-pessimistic when
-     * exclusions are applied.
-     * This should not matter because subsequent checks and normalizations
-     * do apply the exclusions; only a little more of the text may be processed
-     * than necessary under exclusions.
-     *
-     * Normalization exclusions have the following effect on excluded code points c:
-     * - c is not decomposed
-     * - c is not a composition target
-     * - c does not combine forward or backward for composition
-     *   except that this is not implemented for Jamo
-     * - c is treated as having a combining class of 0
-     */
-
-    /*
-     * Constants for the bit fields in the options bit set parameter.
-     * These need not be public.
-     * A user only needs to know the currently assigned values.
-     * The number and positions of reserved bits per field can remain private.
-     */
-    private static final int OPTIONS_NX_MASK=0x1f;
-    private static final int OPTIONS_UNICODE_MASK=0xe0;
-    public  static final int OPTIONS_SETS_MASK=0xff;
-//  private static final int OPTIONS_UNICODE_SHIFT=5;
-    private static final UnicodeSet[] nxCache = new UnicodeSet[OPTIONS_SETS_MASK+1];
-
-    /* Constants for options flags for normalization.*/
-
-    /**
-     * Options bit 0, do not decompose Hangul syllables.
-     * @draft ICU 2.6
-     */
-    private static final int NX_HANGUL = 1;
-    /**
-     * Options bit 1, do not decompose CJK compatibility characters.
-     * @draft ICU 2.6
-     */
-    private static final int NX_CJK_COMPAT=2;
-    /**
-     * Options bit 8, use buggy recomposition described in
-     * Unicode Public Review Issue #29
-     * at http://www.unicode.org/review/resolved-pri.html#pri29
-     *
-     * Used in IDNA implementation according to strict interpretation
-     * of IDNA definition based on Unicode 3.2 which predates PRI #29.
-     *
-     * See ICU4C unormimp.h
-     *
-     * @draft ICU 3.2
-     */
-    public static final int BEFORE_PRI_29=0x100;
-
-    /*
-     * The following options are used only in some composition functions.
-     * They use bits 12 and up to preserve lower bits for the available options
-     * space in unorm_compare() -
-     * see documentation for UNORM_COMPARE_NORM_OPTIONS_SHIFT.
-     */
-
-    /** Options bit 12, for compatibility vs. canonical decomposition. */
-    public static final int OPTIONS_COMPAT=0x1000;
-    /** Options bit 13, no discontiguous composition (FCC vs. NFC). */
-    public static final int OPTIONS_COMPOSE_CONTIGUOUS=0x2000;
-
-    /* normalization exclusion sets --------------------------------------------- */
-
-    /*
-     * Normalization exclusion UnicodeSets are used for tailored normalization;
-     * see the comment near the beginning of this file.
-     *
-     * By specifying one or several sets of code points,
-     * those code points become inert for normalization.
-     */
-    private static final synchronized UnicodeSet internalGetNXHangul() {
-        /* internal function, does not check for incoming U_FAILURE */
-
-        if(nxCache[NX_HANGUL]==null) {
-             nxCache[NX_HANGUL]=new UnicodeSet(0xac00, 0xd7a3);
-        }
-        return nxCache[NX_HANGUL];
-    }
-
-    private static final synchronized UnicodeSet internalGetNXCJKCompat() {
-        /* internal function, does not check for incoming U_FAILURE */
-
-        if(nxCache[NX_CJK_COMPAT]==null) {
-
-            /* build a set from [CJK Ideographs]&[has canonical decomposition] */
-            UnicodeSet set, hasDecomp;
-
-            set=new UnicodeSet("[:Ideographic:]");
-
-            /* start with an empty set for [has canonical decomposition] */
-            hasDecomp=new UnicodeSet();
-
-            /* iterate over all ideographs and remember which canonically decompose */
-            UnicodeSetIterator it = new UnicodeSetIterator(set);
-            int start, end;
-            long norm32;
-
-            while(it.nextRange() && (it.codepoint != UnicodeSetIterator.IS_STRING)) {
-                start=it.codepoint;
-                end=it.codepointEnd;
-                while(start<=end) {
-                    norm32 = getNorm32(start);
-                    if((norm32 & QC_NFD)>0) {
-                        hasDecomp.add(start);
-                    }
-                    ++start;
-                }
-            }
-
-            /* hasDecomp now contains all ideographs that decompose canonically */
-             nxCache[NX_CJK_COMPAT]=hasDecomp;
-
-        }
-
-        return nxCache[NX_CJK_COMPAT];
-    }
-
-    private static final synchronized UnicodeSet internalGetNXUnicode(int options) {
-        options &= OPTIONS_UNICODE_MASK;
-        if(options==0) {
-            return null;
-        }
-
-        if(nxCache[options]==null) {
-            /* build a set with all code points that were not designated by the specified Unicode version */
-            UnicodeSet set = new UnicodeSet();
-
-            switch(options) {
-            case NormalizerBase.UNICODE_3_2:
-                set.applyPattern("[:^Age=3.2:]");
-                break;
-            default:
-                return null;
-            }
-
-            nxCache[options]=set;
-        }
-
-        return nxCache[options];
-    }
-
-    /* Get a decomposition exclusion set. The data must be loaded. */
-    private static final synchronized UnicodeSet internalGetNX(int options) {
-        options&=OPTIONS_SETS_MASK;
-
-        if(nxCache[options]==null) {
-            /* return basic sets */
-            if(options==NX_HANGUL) {
-                return internalGetNXHangul();
-            }
-            if(options==NX_CJK_COMPAT) {
-                return internalGetNXCJKCompat();
-            }
-            if((options & OPTIONS_UNICODE_MASK)!=0 && (options & OPTIONS_NX_MASK)==0) {
-                return internalGetNXUnicode(options);
-            }
-
-            /* build a set from multiple subsets */
-            UnicodeSet set;
-            UnicodeSet other;
-
-            set=new UnicodeSet();
-
-
-            if((options & NX_HANGUL)!=0 && null!=(other=internalGetNXHangul())) {
-                set.addAll(other);
-            }
-            if((options&NX_CJK_COMPAT)!=0 && null!=(other=internalGetNXCJKCompat())) {
-                set.addAll(other);
-            }
-            if((options&OPTIONS_UNICODE_MASK)!=0 && null!=(other=internalGetNXUnicode(options))) {
-                set.addAll(other);
-            }
+    // Norm16 value thresholds for quick check combinations and types of extra data.
+    private int minYesNo;
+    private int minYesNoMappingsOnly;
+    private int minNoNo;
+    private int limitNoNo;
+    private int minMaybeYes;
 
-               nxCache[options]=set;
-        }
-        return nxCache[options];
-    }
-
-    public static final UnicodeSet getNX(int options) {
-        if((options&=OPTIONS_SETS_MASK)==0) {
-            /* incoming failure, or no decomposition exclusions requested */
-            return null;
-        } else {
-            return internalGetNX(options);
-        }
-    }
-
-    private static final boolean nx_contains(UnicodeSet nx, int c) {
-        return nx!=null && nx.contains(c);
-    }
-
-    private static final boolean nx_contains(UnicodeSet nx, char c, char c2) {
-        return nx!=null && nx.contains(c2==0 ? c : UCharacterProperty.getRawSupplementary(c, c2));
-    }
-
-/*****************************************************************************/
-
-    /**
-     * Get the canonical decomposition
-     * sherman  for ComposedCharIter
-     */
-
-    public static int getDecompose(int chars[], String decomps[]) {
-        DecomposeArgs args = new DecomposeArgs();
-        int length=0;
-        long norm32 = 0;
-        int ch = -1;
-        int index = 0;
-        int i = 0;
-
-        while (++ch < 0x2fa1e) {   //no cannoical above 0x3ffff
-            //TBD !!!! the hack code heres save us about 50ms for startup
-            //need a better solution/lookup
-            if (ch == 0x30ff)
-                ch = 0xf900;
-            else if (ch == 0x10000)
-                ch = 0x1d15e;
-            else if (ch == 0x1d1c1)
-                ch = 0x2f800;
-
-            norm32 = NormalizerImpl.getNorm32(ch);
-            if((norm32 & QC_NFD)!=0 && i < chars.length) {
-                chars[i] = ch;
-                index = decompose(norm32, args);
-                decomps[i++] = new String(extraData,index, args.length);
-            }
-        }
-        return i;
-    }
-
-    //------------------------------------------------------
-    // special method for Collation
-    //------------------------------------------------------
-    private static boolean needSingleQuotation(char c) {
-        return (c >= 0x0009 && c <= 0x000D) ||
-               (c >= 0x0020 && c <= 0x002F) ||
-               (c >= 0x003A && c <= 0x0040) ||
-               (c >= 0x005B && c <= 0x0060) ||
-               (c >= 0x007B && c <= 0x007E);
-    }
-
-    public static String canonicalDecomposeWithSingleQuotation(String string) {
-        char[] src = string.toCharArray();
-        int    srcIndex = 0;
-        int    srcLimit = src.length;
-        char[] dest = new char[src.length * 3];  //MAX_BUF_SIZE_DECOMPOSE = 3
-        int    destIndex = 0;
-        int    destLimit = dest.length;
-
-        char[] buffer = new char[3];
-        int prevSrc;
-        long norm32;
-        int ccOrQCMask;
-        int qcMask = QC_NFD;
-        int reorderStartIndex, length;
-        char c, c2;
-        char minNoMaybe = (char)indexes[INDEX_MIN_NFD_NO_MAYBE];
-        int cc, prevCC, trailCC;
-        char[] p;
-        int pStart;
-
-
-        // initialize
-        ccOrQCMask = CC_MASK | qcMask;
-        reorderStartIndex = 0;
-        prevCC = 0;
-        norm32 = 0;
-        c = 0;
-        pStart = 0;
-
-        cc = trailCC = -1; // initialize to bogus value
-        for(;;) {
-            prevSrc=srcIndex;
-            //quick check (1)less than minNoMaybe (2)no decomp (3)hangual
-            while (srcIndex != srcLimit &&
-                   (( c = src[srcIndex]) < minNoMaybe ||
-                    ((norm32 = getNorm32(c)) & ccOrQCMask) == 0 ||
-                    ( c >= '\uac00' && c <= '\ud7a3'))){
-
-                prevCC = 0;
-                ++srcIndex;
-            }
-
-            // copy these code units all at once
-            if (srcIndex != prevSrc) {
-                length = srcIndex - prevSrc;
-                if ((destIndex + length) <= destLimit) {
-                    System.arraycopy(src,prevSrc,dest,destIndex,length);
-                }
-
-                destIndex += length;
-                reorderStartIndex = destIndex;
-            }
-
-            // end of source reached?
-            if(srcIndex == srcLimit) {
-                break;
-            }
-            // c already contains *src and norm32 is set for it, increment src
-            ++srcIndex;
-
-            if(isNorm32Regular(norm32)) {
-                c2 = 0;
-                length = 1;
-            } else {
-                // c is a lead surrogate, get the real norm32
-                if(srcIndex != srcLimit &&
-                    Character.isLowSurrogate(c2 = src[srcIndex])) {
-                        ++srcIndex;
-                        length = 2;
-                        norm32 = getNorm32FromSurrogatePair(norm32, c2);
-                } else {
-                    c2 = 0;
-                    length = 1;
-                    norm32 = 0;
-                }
-            }
+    private Trie2_16 normTrie;
+    private String maybeYesCompositions;
+    private String extraData;  // mappings and/or compositions for yesYes, yesNo & noNo characters
+    private byte[] smallFCD;  // [0x100] one bit per 32 BMP code points, set if any FCD!=0
+    private int[] tccc180;  // [0x180] tccc values for U+0000..U+017F
 
-            // get the decomposition and the lead and trail cc's
-            if((norm32 & qcMask) == 0) {
-                // c does not decompose
-                cc = trailCC = (int)((UNSIGNED_BYTE_MASK) & (norm32 >> CC_SHIFT));
-                p = null;
-                pStart = -1;
-            } else {
-                DecomposeArgs arg = new DecomposeArgs();
-                // c decomposes, get everything from the variable-length
-                // extra data
-                pStart = decompose(norm32, qcMask, arg);
-                p = extraData;
-                length = arg.length;
-                cc = arg.cc;
-                trailCC = arg.trailCC;
-                if(length == 1) {
-                    // fastpath a single code unit from decomposition
-                    c = p[pStart];
-                    c2 = 0;
-                    p = null;
-                    pStart = -1;
-                }
-            }
-
-            if((destIndex + length * 3) >= destLimit) {  // 2 SingleQuotations
-                // buffer overflow
-                char[] tmpBuf = new char[destLimit * 2];
-                System.arraycopy(dest, 0, tmpBuf, 0, destIndex);
-                dest = tmpBuf;
-                destLimit = dest.length;
-            }
-            // append the decomposition to the destination buffer, assume length>0
-            {
-                int reorderSplit = destIndex;
-                if(p == null) {
-                    // fastpath: single code point
-                    if (needSingleQuotation(c)) {
-                        //if we need single quotation, no need to consider "prevCC"
-                        //and it must NOT be a supplementary pair
-                        dest[destIndex++] = '\'';
-                        dest[destIndex++] = c;
-                        dest[destIndex++] = '\'';
-                        trailCC = 0;
-                    } else if(cc != 0 && cc < prevCC) {
-                        // (c, c2) is out of order with respect to the preceding
-                        //  text
-                        destIndex += length;
-                        trailCC = insertOrdered(dest,reorderStartIndex,
-                                                reorderSplit, destIndex, c, c2, cc);
-                    } else {
-                        // just append (c, c2)
-                        dest[destIndex++] = c;
-                        if(c2 != 0) {
-                            dest[destIndex++] = c2;
-                        }
-                    }
-                } else {
-                    // general: multiple code points (ordered by themselves)
-                    // from decomposition
-                    if (needSingleQuotation(p[pStart])) {
-                        dest[destIndex++] = '\'';
-                        dest[destIndex++] = p[pStart++];
-                        dest[destIndex++] = '\'';
-                        length--;
-                        do {
-                            dest[destIndex++] = p[pStart++];
-                        } while(--length > 0);
-                    } else
-                    if(cc != 0 && cc < prevCC) {
-                        destIndex += length;
-                        trailCC = mergeOrdered(dest,reorderStartIndex,
-                                               reorderSplit,p, pStart,pStart+length);
-                    } else {
-                        // just append the decomposition
-                        do {
-                            dest[destIndex++] = p[pStart++];
-                        } while(--length > 0);
-                    }
-                }
-            }
-            prevCC = trailCC;
-            if(prevCC == 0) {
-                reorderStartIndex = destIndex;
-            }
-        }
-        return new String(dest, 0, destIndex);
-    }
-
-    //------------------------------------------------------
-    // mapping method for IDNA/StringPrep
-    //------------------------------------------------------
-
-    /*
-     * Normalization using NormalizerBase.UNICODE_3_2 option supports Unicode
-     * 3.2 normalization with Corrigendum 4 corrections. However, normalization
-     * without the corrections is necessary for IDNA/StringPrep support.
-     * This method is called when NormalizerBase.UNICODE_3_2_0_ORIGINAL option
-     * (= sun.text.Normalizer.UNICODE_3_2) is used and normalizes five
-     * characters in Corrigendum 4 before normalization in order to avoid
-     * incorrect normalization.
-     * For the Corrigendum 4 issue, refer
-     *   http://www.unicode.org/versions/corrigendum4.html
-     */
-
-    /*
-     * Option used in NormalizerBase.UNICODE_3_2_0_ORIGINAL.
-     */
-    public static final int WITHOUT_CORRIGENDUM4_CORRECTIONS=0x40000;
-
-    private static final char[][] corrigendum4MappingTable = {
-        {'\uD844', '\uDF6A'},  // 0x2F868
-        {'\u5F33'},            // 0x2F874
-        {'\u43AB'},            // 0x2F91F
-        {'\u7AAE'},            // 0x2F95F
-        {'\u4D57'}};           // 0x2F9BF
-
-    /*
-     * Removing Corrigendum 4 fix
-     * @return normalized text
-     */
-    public static String convert(String str) {
-        if (str == null) {
-            return null;
-        }
-
-        int ch  = UCharacterIterator.DONE;
-        StringBuffer dest = new StringBuffer();
-        UCharacterIterator iter = UCharacterIterator.getInstance(str);
-
-        while ((ch=iter.nextCodePoint())!= UCharacterIterator.DONE){
-            switch (ch) {
-            case 0x2F868:
-                dest.append(corrigendum4MappingTable[0]);
-                break;
-            case 0x2F874:
-                dest.append(corrigendum4MappingTable[1]);
-                break;
-            case 0x2F91F:
-                dest.append(corrigendum4MappingTable[2]);
-                break;
-            case 0x2F95F:
-                dest.append(corrigendum4MappingTable[3]);
-                break;
-            case 0x2F9BF:
-                dest.append(corrigendum4MappingTable[4]);
-                break;
-            default:
-                UTF16.append(dest,ch);
-                break;
-            }
-        }
-
-        return dest.toString();
-    }
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/OutputInt.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,50 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/*
+ *******************************************************************************
+ * Copyright (C) 2014, International Business Machines Corporation and
+ * others. All Rights Reserved.
+ *******************************************************************************
+ */
+package sun.text.normalizer;
+
+/**
+ * Simple struct-like class for int output parameters.
+ * Like <code>Output&lt;Integer&gt;</code> but without auto-boxing.
+ *
+ * @internal but could become public
+ * deprecated This API is ICU internal only.
+ */
+class OutputInt {
+
+    /**
+     * The value field.
+     *
+     * @internal
+     * deprecated This API is ICU internal only.
+     */
+    public int value;
+}
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/RangeValueIterator.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,141 +0,0 @@
-/*
- * Copyright (c) 2005, 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.
- */
-
-/*
- *******************************************************************************
- * (C) Copyright IBM Corp. 1996-2005 - All Rights Reserved                     *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
- *******************************************************************************
- */
-
-package sun.text.normalizer;
-
-/**
- * <p>Interface for enabling iteration over sets of
- * {@code <int index, int value>},
- * where index is the sorted integer index in ascending order and value, its
- * associated integer value.
- * <p>The result for each iteration is the consecutive range of
- * {@code <int index, int value>} with the same value. Result is represented by
- * {@code <start, limit, value>} where
- * <ul>
- * <li> start is the starting integer of the result range
- * <li> limit is 1 after the maximum integer that follows start, such that
- *      all integers between start and (limit - 1), inclusive, have the same
- *      associated integer value.
- * <li> value is the integer value that all integers from start to (limit - 1)
- *      share in common.
- * </ul>
- * <p>
- * Hence value(start) = value(start + 1) = .... = value(start + n) = .... =
- * value(limit - 1). However value(start -1) != value(start) and
- * value(limit) != value(start).
- *
- * <p>Most implementations will be created by factory methods, such as the
- * character type iterator in UCharacter.getTypeIterator. See example below.
- *
- * Example of use:<br>
- * <pre>
- * RangeValueIterator iterator = UCharacter.getTypeIterator();
- * RangeValueIterator.Element result = new RangeValueIterator.Element();
- * while (iterator.next(result)) {
- *     System.out.println("Codepoint \\u" +
- *                        Integer.toHexString(result.start) +
- *                        " to codepoint \\u" +
- *                        Integer.toHexString(result.limit - 1) +
- *                        " has the character type " + result.value);
- * }
- * </pre>
- * @author synwee
- * @stable ICU 2.6
- */
-public interface RangeValueIterator
-{
-    // public inner class ---------------------------------------------
-
-    /**
-    * Return result wrapper for com.ibm.icu.util.RangeValueIterator.
-    * Stores the start and limit of the continous result range and the
-    * common value all integers between [start, limit - 1] has.
-    * @stable ICU 2.6
-    */
-    public class Element
-    {
-        // public data member ---------------------------------------------
-
-        /**
-        * Starting integer of the continuous result range that has the same
-        * value
-        * @stable ICU 2.6
-        */
-        public int start;
-        /**
-        * (End + 1) integer of continuous result range that has the same
-        * value
-        * @stable ICU 2.6
-        */
-        public int limit;
-        /**
-        * Gets the common value of the continous result range
-        * @stable ICU 2.6
-        */
-        public int value;
-
-        // public constructor --------------------------------------------
-
-        /**
-         * Empty default constructor to make javadoc happy
-         * @stable ICU 2.4
-         */
-        public Element()
-        {
-        }
-    }
-
-    // public methods -------------------------------------------------
-
-    /**
-    * <p>Gets the next maximal result range with a common value and returns
-    * true if we are not at the end of the iteration, false otherwise.</p>
-    * <p>If the return boolean is a false, the contents of elements will not
-    * be updated.</p>
-    * @param element for storing the result range and value
-    * @return true if we are not at the end of the iteration, false otherwise.
-    * @see Element
-    * @stable ICU 2.6
-    */
-    public boolean next(Element element);
-
-    /**
-    * Resets the iterator to the beginning of the iteration.
-    * @stable ICU 2.6
-    */
-    public void reset();
-}
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/Replaceable.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/Replaceable.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -82,7 +82,7 @@
  * @author Alan Liu
  * @stable ICU 2.0
  */
-public interface Replaceable {
+interface Replaceable {
     /**
      * Returns the number of 16-bit code units in the text.
      * @return number of 16-bit code units in text
@@ -99,7 +99,6 @@
      */
     char charAt(int offset);
 
-    //// for StringPrep
     /**
      * Copies characters from this object into the destination
      * character array.  The first character to be copied is at index
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/ReplaceableString.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/ReplaceableString.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -25,13 +25,8 @@
 
 /*
  *******************************************************************************
- * (C) Copyright IBM Corp. 1996-2005 - All Rights Reserved                     *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
+ * Copyright (C) 1996-2009, International Business Machines Corporation and    *
+ * others. All Rights Reserved.                                                *
  *******************************************************************************
  */
 
@@ -51,7 +46,7 @@
  * @author Alan Liu
  * @stable ICU 2.0
  */
-public class ReplaceableString implements Replaceable {
+class ReplaceableString implements Replaceable {
 
     private StringBuffer buf;
 
@@ -64,7 +59,6 @@
         buf = new StringBuffer(str);
     }
 
-    //// for StringPrep
     /**
      * Construct a new object using <code>buf</code> for internal
      * storage.  The contents of <code>buf</code> at the time of
@@ -98,7 +92,6 @@
         return buf.charAt(offset);
     }
 
-    //// for StringPrep
     /**
      * Copies characters from this object into the destination
      * character array.  The first character to be copied is at index
@@ -118,6 +111,8 @@
      * @stable ICU 2.0
      */
     public void getChars(int srcStart, int srcLimit, char dst[], int dstStart) {
-        Utility.getChars(buf, srcStart, srcLimit, dst, dstStart);
+        if (srcStart != srcLimit) {
+            buf.getChars(srcStart, srcLimit, dst, dstStart);
+        }
     }
 }
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/ReplaceableUCharacterIterator.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/ReplaceableUCharacterIterator.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -47,7 +47,7 @@
  *
  * What are first, last, and getBeginIndex doing here?!?!?!
  */
-public class ReplaceableUCharacterIterator extends UCharacterIterator {
+class ReplaceableUCharacterIterator extends UCharacterIterator {
 
     // public constructor ------------------------------------------------------
 
@@ -63,7 +63,6 @@
         this.currentIndex = 0;
     }
 
-    //// for StringPrep
     /**
      * Public constructor
      * @param buf buffer of text on which the iterator will be based
@@ -164,7 +163,6 @@
         this.currentIndex = currentIndex;
     }
 
-    //// for StringPrep
     public int getText(char[] fillIn, int offset){
         int length = replaceable.length();
         if(offset < 0 || offset + length > fillIn.length){
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/RuleCharacterIterator.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,371 +0,0 @@
-/*
- * Copyright (c) 2005, 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.
- */
-
-/*
- *******************************************************************************
- * (C) Copyright IBM Corp. 1996-2005 - All Rights Reserved                     *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
- *******************************************************************************
- */
-
-/*
- **********************************************************************
- * Author: Alan Liu
- * Created: September 23 2003
- * Since: ICU 2.8
- **********************************************************************
- */
-
-package sun.text.normalizer;
-
-import java.text.ParsePosition;
-
-/**
- * An iterator that returns 32-bit code points.  This class is deliberately
- * <em>not</em> related to any of the JDK or ICU4J character iterator classes
- * in order to minimize complexity.
- * @author Alan Liu
- * @since ICU 2.8
- */
-@SuppressWarnings("deprecation")
-public class RuleCharacterIterator {
-
-    // TODO: Ideas for later.  (Do not implement if not needed, lest the
-    // code coverage numbers go down due to unused methods.)
-    // 1. Add a copy constructor, equals() method, clone() method.
-    // 2. Rather than return DONE, throw an exception if the end
-    // is reached -- this is an alternate usage model, probably not useful.
-    // 3. Return isEscaped from next().  If this happens,
-    // don't keep an isEscaped member variable.
-
-    /**
-     * Text being iterated.
-     */
-    private String text;
-
-    /**
-     * Position of iterator.
-     */
-    private ParsePosition pos;
-
-    /**
-     * Symbol table used to parse and dereference variables.  May be null.
-     */
-    private SymbolTable sym;
-
-    /**
-     * Current variable expansion, or null if none.
-     */
-    private char[] buf;
-
-    /**
-     * Position within buf[].  Meaningless if buf == null.
-     */
-    private int bufPos;
-
-    /**
-     * Flag indicating whether the last character was parsed from an escape.
-     */
-    private boolean isEscaped;
-
-    /**
-     * Value returned when there are no more characters to iterate.
-     */
-    public static final int DONE = -1;
-
-    /**
-     * Bitmask option to enable parsing of variable names.
-     * If {@code (options & PARSE_VARIABLES) != 0},
-     * then an embedded variable will be expanded to
-     * its value.  Variables are parsed using the SymbolTable API.
-     */
-    public static final int PARSE_VARIABLES = 1;
-
-    /**
-     * Bitmask option to enable parsing of escape sequences.
-     * If {@code (options & PARSE_ESCAPES) != 0},
-     * then an embedded escape sequence will be expanded
-     * to its value.  Escapes are parsed using Utility.unescapeAt().
-     */
-    public static final int PARSE_ESCAPES   = 2;
-
-    /**
-     * Bitmask option to enable skipping of whitespace.
-     * If {@code (options & SKIP_WHITESPACE) != 0},
-     * then whitespace characters will be silently
-     * skipped, as if they were not present in the input.  Whitespace
-     * characters are defined by UCharacterProperty.isRuleWhiteSpace().
-     */
-    public static final int SKIP_WHITESPACE = 4;
-
-    /**
-     * Constructs an iterator over the given text, starting at the given
-     * position.
-     * @param text the text to be iterated
-     * @param sym the symbol table, or null if there is none.  If sym is null,
-     * then variables will not be deferenced, even if the PARSE_VARIABLES
-     * option is set.
-     * @param pos upon input, the index of the next character to return.  If a
-     * variable has been dereferenced, then pos will <em>not</em> increment as
-     * characters of the variable value are iterated.
-     */
-    public RuleCharacterIterator(String text, SymbolTable sym,
-                                 ParsePosition pos) {
-        if (text == null || pos.getIndex() > text.length()) {
-            throw new IllegalArgumentException();
-        }
-        this.text = text;
-        this.sym = sym;
-        this.pos = pos;
-        buf = null;
-    }
-
-    /**
-     * Returns true if this iterator has no more characters to return.
-     */
-    public boolean atEnd() {
-        return buf == null && pos.getIndex() == text.length();
-    }
-
-    /**
-     * Returns the next character using the given options, or DONE if there
-     * are no more characters, and advance the position to the next
-     * character.
-     * @param options one or more of the following options, bitwise-OR-ed
-     * together: PARSE_VARIABLES, PARSE_ESCAPES, SKIP_WHITESPACE.
-     * @return the current 32-bit code point, or DONE
-     */
-    public int next(int options) {
-        int c = DONE;
-        isEscaped = false;
-
-        for (;;) {
-            c = _current();
-            _advance(UTF16.getCharCount(c));
-
-            if (c == SymbolTable.SYMBOL_REF && buf == null &&
-                (options & PARSE_VARIABLES) != 0 && sym != null) {
-                String name = sym.parseReference(text, pos, text.length());
-                // If name == null there was an isolated SYMBOL_REF;
-                // return it.  Caller must be prepared for this.
-                if (name == null) {
-                    break;
-                }
-                bufPos = 0;
-                buf = sym.lookup(name);
-                if (buf == null) {
-                    throw new IllegalArgumentException(
-                                "Undefined variable: " + name);
-                }
-                // Handle empty variable value
-                if (buf.length == 0) {
-                    buf = null;
-                }
-                continue;
-            }
-
-            if ((options & SKIP_WHITESPACE) != 0 &&
-                UCharacterProperty.isRuleWhiteSpace(c)) {
-                continue;
-            }
-
-            if (c == '\\' && (options & PARSE_ESCAPES) != 0) {
-                int offset[] = new int[] { 0 };
-                c = Utility.unescapeAt(lookahead(), offset);
-                jumpahead(offset[0]);
-                isEscaped = true;
-                if (c < 0) {
-                    throw new IllegalArgumentException("Invalid escape");
-                }
-            }
-
-            break;
-        }
-
-        return c;
-    }
-
-    /**
-     * Returns true if the last character returned by next() was
-     * escaped.  This will only be the case if the option passed in to
-     * next() included PARSE_ESCAPED and the next character was an
-     * escape sequence.
-     */
-    public boolean isEscaped() {
-        return isEscaped;
-    }
-
-    /**
-     * Returns true if this iterator is currently within a variable expansion.
-     */
-    public boolean inVariable() {
-        return buf != null;
-    }
-
-    /**
-     * Returns an object which, when later passed to setPos(), will
-     * restore this iterator's position.  Usage idiom:
-     *
-     * RuleCharacterIterator iterator = ...;
-     * Object pos = iterator.getPos(null); // allocate position object
-     * for (;;) {
-     *   pos = iterator.getPos(pos); // reuse position object
-     *   int c = iterator.next(...);
-     *   ...
-     * }
-     * iterator.setPos(pos);
-     *
-     * @param p a position object previously returned by getPos(),
-     * or null.  If not null, it will be updated and returned.  If
-     * null, a new position object will be allocated and returned.
-     * @return a position object which may be passed to setPos(),
-     * either `p,' or if `p' == null, a newly-allocated object
-     */
-    public Object getPos(Object p) {
-        if (p == null) {
-            return new Object[] {buf, new int[] {pos.getIndex(), bufPos}};
-        }
-        Object[] a = (Object[]) p;
-        a[0] = buf;
-        int[] v = (int[]) a[1];
-        v[0] = pos.getIndex();
-        v[1] = bufPos;
-        return p;
-    }
-
-    /**
-     * Restores this iterator to the position it had when getPos()
-     * returned the given object.
-     * @param p a position object previously returned by getPos()
-     */
-    public void setPos(Object p) {
-        Object[] a = (Object[]) p;
-        buf = (char[]) a[0];
-        int[] v = (int[]) a[1];
-        pos.setIndex(v[0]);
-        bufPos = v[1];
-    }
-
-    /**
-     * Skips ahead past any ignored characters, as indicated by the given
-     * options.  This is useful in conjunction with the lookahead() method.
-     *
-     * Currently, this only has an effect for SKIP_WHITESPACE.
-     * @param options one or more of the following options, bitwise-OR-ed
-     * together: PARSE_VARIABLES, PARSE_ESCAPES, SKIP_WHITESPACE.
-     */
-    public void skipIgnored(int options) {
-        if ((options & SKIP_WHITESPACE) != 0) {
-            for (;;) {
-                int a = _current();
-                if (!UCharacterProperty.isRuleWhiteSpace(a)) break;
-                _advance(UTF16.getCharCount(a));
-            }
-        }
-    }
-
-    /**
-     * Returns a string containing the remainder of the characters to be
-     * returned by this iterator, without any option processing.  If the
-     * iterator is currently within a variable expansion, this will only
-     * extend to the end of the variable expansion.  This method is provided
-     * so that iterators may interoperate with string-based APIs.  The typical
-     * sequence of calls is to call skipIgnored(), then call lookahead(), then
-     * parse the string returned by lookahead(), then call jumpahead() to
-     * resynchronize the iterator.
-     * @return a string containing the characters to be returned by future
-     * calls to next()
-     */
-    public String lookahead() {
-        if (buf != null) {
-            return new String(buf, bufPos, buf.length - bufPos);
-        } else {
-            return text.substring(pos.getIndex());
-        }
-    }
-
-    /**
-     * Advances the position by the given number of 16-bit code units.
-     * This is useful in conjunction with the lookahead() method.
-     * @param count the number of 16-bit code units to jump over
-     */
-    public void jumpahead(int count) {
-        if (count < 0) {
-            throw new IllegalArgumentException();
-        }
-        if (buf != null) {
-            bufPos += count;
-            if (bufPos > buf.length) {
-                throw new IllegalArgumentException();
-            }
-            if (bufPos == buf.length) {
-                buf = null;
-            }
-        } else {
-            int i = pos.getIndex() + count;
-            pos.setIndex(i);
-            if (i > text.length()) {
-                throw new IllegalArgumentException();
-            }
-        }
-    }
-
-    /**
-     * Returns the current 32-bit code point without parsing escapes, parsing
-     * variables, or skipping whitespace.
-     * @return the current 32-bit code point
-     */
-    private int _current() {
-        if (buf != null) {
-            return UTF16.charAt(buf, 0, buf.length, bufPos);
-        } else {
-            int i = pos.getIndex();
-            return (i < text.length()) ? UTF16.charAt(text, i) : DONE;
-        }
-    }
-
-    /**
-     * Advances the position by the given amount.
-     * @param count the number of 16-bit code units to advance past
-     */
-    private void _advance(int count) {
-        if (buf != null) {
-            bufPos += count;
-            if (bufPos == buf.length) {
-                buf = null;
-            }
-        } else {
-            pos.setIndex(pos.getIndex() + count);
-            if (pos.getIndex() > text.length()) {
-                pos.setIndex(text.length());
-            }
-        }
-    }
-}
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/SymbolTable.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,124 +0,0 @@
-/*
- * Copyright (c) 2005, 2011, 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.
- */
-
-/*
- *******************************************************************************
- * (C) Copyright IBM Corp. 1996-2005 - All Rights Reserved                     *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
- *******************************************************************************
- */
-
-package sun.text.normalizer;
-
-import java.text.ParsePosition;
-
-/**
- * An interface that defines both lookup protocol and parsing of
- * symbolic names.
- *
- * <p>A symbol table maintains two kinds of mappings.  The first is
- * between symbolic names and their values.  For example, if the
- * variable with the name "start" is set to the value "alpha"
- * (perhaps, though not necessarily, through an expression such as
- * "$start=alpha"), then the call lookup("start") will return the
- * char[] array ['a', 'l', 'p', 'h', 'a'].
- *
- * <p>The second kind of mapping is between character values and
- * UnicodeMatcher objects.  This is used by RuleBasedTransliterator,
- * which uses characters in the private use area to represent objects
- * such as UnicodeSets.  If U+E015 is mapped to the UnicodeSet [a-z],
- * then lookupMatcher(0xE015) will return the UnicodeSet [a-z].
- *
- * <p>Finally, a symbol table defines parsing behavior for symbolic
- * names.  All symbolic names start with the SYMBOL_REF character.
- * When a parser encounters this character, it calls parseReference()
- * with the position immediately following the SYMBOL_REF.  The symbol
- * table parses the name, if there is one, and returns it.
- *
- * @draft ICU 2.8
- * @deprecated This is a draft API and might change in a future release of ICU.
- */
-@Deprecated
-public interface SymbolTable {
-
-    /**
-     * The character preceding a symbol reference name.
-     * @draft ICU 2.8
-     * @deprecated This is a draft API and might change in a future release of ICU.
-     */
-    @Deprecated
-    static final char SYMBOL_REF = '$';
-
-    /**
-     * Lookup the characters associated with this string and return it.
-     * Return {@code null} if no such name exists.  The resultant
-     * array may have length zero.
-     * @param s the symbolic name to lookup
-     * @return a char array containing the name's value, or null if
-     * there is no mapping for s.
-     * @draft ICU 2.8
-     * @deprecated This is a draft API and might change in a future release of ICU.
-     */
-    @Deprecated
-    char[] lookup(String s);
-
-    /**
-     * Lookup the UnicodeMatcher associated with the given character, and
-     * return it.  Return {@code null} if not found.
-     * @param ch a 32-bit code point from 0 to 0x10FFFF inclusive.
-     * @return the UnicodeMatcher object represented by the given
-     * character, or null if there is no mapping for ch.
-     * @draft ICU 2.8
-     * @deprecated This is a draft API and might change in a future release of ICU.
-     */
-    @Deprecated
-    UnicodeMatcher lookupMatcher(int ch);
-
-    /**
-     * Parse a symbol reference name from the given string, starting
-     * at the given position.  If no valid symbol reference name is
-     * found, return null and leave pos unchanged.  That is, if the
-     * character at pos cannot start a name, or if pos is at or after
-     * text.length(), then return null.  This indicates an isolated
-     * SYMBOL_REF character.
-     * @param text the text to parse for the name
-     * @param pos on entry, the index of the first character to parse.
-     * This is the character following the SYMBOL_REF character.  On
-     * exit, the index after the last parsed character.  If the parse
-     * failed, pos is unchanged on exit.
-     * @param limit the index after the last character to be parsed.
-     * @return the parsed name, or null if there is no valid symbolic
-     * name at the given position.
-     * @draft ICU 2.8
-     * @deprecated This is a draft API and might change in a future release of ICU.
-     */
-    @Deprecated
-    String parseReference(String text, ParsePosition pos, int limit);
-}
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/Trie.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/Trie.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2009, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -22,16 +22,12 @@
  * or visit www.oracle.com if you need additional information or have any
  * questions.
  */
+
 /*
- *******************************************************************************
- * (C) Copyright IBM Corp. and others, 1996-2009 - All Rights Reserved         *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
- *******************************************************************************
+ ******************************************************************************
+ * Copyright (C) 1996-2014, International Business Machines Corporation and
+ * others. All Rights Reserved.
+ ******************************************************************************
  */
 
 package sun.text.normalizer;
@@ -135,93 +131,62 @@
         unserialize(inputStream);
     }
 
-    /**
-    * Trie constructor
-    * @param index array to be used for index
-    * @param options used by the trie
-    * @param dataManipulate object containing the information to parse the
-    *                       trie data
-    */
-    protected Trie(char index[], int options, DataManipulate dataManipulate)
-    {
-        m_options_ = options;
-        if(dataManipulate != null) {
-            m_dataManipulate_ = dataManipulate;
-        } else {
-            m_dataManipulate_ = new DefaultGetFoldingOffset();
-        }
-        m_isLatin1Linear_ = (m_options_ &
-                             HEADER_OPTIONS_LATIN1_IS_LINEAR_MASK_) != 0;
-        m_index_ = index;
-        m_dataOffset_ = m_index_.length;
-    }
-
     // protected data members ------------------------------------------
 
     /**
-    * Lead surrogate code points' index displacement in the index array.
-    * <pre>{@code
-    * 0x10000-0xd800=0x2800
-    * 0x2800 >> INDEX_STAGE_1_SHIFT_
-    * }</pre>
-    */
+     * Lead surrogate code points' index displacement in the index array.
+     * <pre>{@code
+     * 0x10000-0xd800=0x2800
+     * 0x2800 >> INDEX_STAGE_1_SHIFT_
+     * }</pre>
+     */
     protected static final int LEAD_INDEX_OFFSET_ = 0x2800 >> 5;
     /**
-    * Shift size for shifting right the input index. 1..9
-    */
+     * Shift size for shifting right the input index. 1..9
+     */
     protected static final int INDEX_STAGE_1_SHIFT_ = 5;
     /**
-    * Shift size for shifting left the index array values.
-    * Increases possible data size with 16-bit index values at the cost
-    * of compactability.
-    * This requires blocks of stage 2 data to be aligned by
-    * DATA_GRANULARITY.
-    * 0..INDEX_STAGE_1_SHIFT
-    */
+     * Shift size for shifting left the index array values.
+     * Increases possible data size with 16-bit index values at the cost
+     * of compactability.
+     * This requires blocks of stage 2 data to be aligned by
+     * DATA_GRANULARITY.
+     * 0..INDEX_STAGE_1_SHIFT
+     */
     protected static final int INDEX_STAGE_2_SHIFT_ = 2;
     /**
      * Number of data values in a stage 2 (data array) block.
      */
     protected static final int DATA_BLOCK_LENGTH=1<<INDEX_STAGE_1_SHIFT_;
     /**
-    * Mask for getting the lower bits from the input index.
-    * DATA_BLOCK_LENGTH - 1.
-    */
+     * Mask for getting the lower bits from the input index.
+     * DATA_BLOCK_LENGTH - 1.
+     */
     protected static final int INDEX_STAGE_3_MASK_ = DATA_BLOCK_LENGTH - 1;
-    /** Number of bits of a trail surrogate that are used in index table lookups. */
-    protected static final int SURROGATE_BLOCK_BITS=10-INDEX_STAGE_1_SHIFT_;
     /**
-     * Number of index (stage 1) entries per lead surrogate.
-     * Same as number of index entries for 1024 trail surrogates,
-     * {@code ==0x400>>INDEX_STAGE_1_SHIFT_}
+     * Surrogate mask to use when shifting offset to retrieve supplementary
+     * values
      */
-    protected static final int SURROGATE_BLOCK_COUNT=(1<<SURROGATE_BLOCK_BITS);
-    /** Length of the BMP portion of the index (stage 1) array. */
-    protected static final int BMP_INDEX_LENGTH=0x10000>>INDEX_STAGE_1_SHIFT_;
-    /**
-    * Surrogate mask to use when shifting offset to retrieve supplementary
-    * values
-    */
     protected static final int SURROGATE_MASK_ = 0x3FF;
     /**
-    * Index or UTF16 characters
-    */
+     * Index or UTF16 characters
+     */
     protected char m_index_[];
     /**
-    * Internal TrieValue which handles the parsing of the data value.
-    * This class is to be implemented by the user
-    */
+     * Internal TrieValue which handles the parsing of the data value.
+     * This class is to be implemented by the user
+     */
     protected DataManipulate m_dataManipulate_;
     /**
-    * Start index of the data portion of the trie. CharTrie combines
-    * index and data into a char array, so this is used to indicate the
-    * initial offset to the data portion.
-    * Note this index always points to the initial value.
-    */
+     * Start index of the data portion of the trie. CharTrie combines
+     * index and data into a char array, so this is used to indicate the
+     * initial offset to the data portion.
+     * Note this index always points to the initial value.
+     */
     protected int m_dataOffset_;
     /**
-    * Length of the data array
-    */
+     * Length of the data array
+     */
     protected int m_dataLength_;
 
     // protected methods -----------------------------------------------
@@ -235,19 +200,6 @@
     protected abstract int getSurrogateOffset(char lead, char trail);
 
     /**
-    * Gets the value at the argument index
-    * @param index value at index will be retrieved
-    * @return 32 bit value
-    */
-    protected abstract int getValue(int index);
-
-    /**
-    * Gets the default initial value
-    * @return 32 bit value
-    */
-    protected abstract int getInitialValue();
-
-    /**
     * Gets the offset to the data which the index ch after variable offset
     * points to.
     * Note for locating a non-supplementary character data offset, calling
@@ -297,13 +249,13 @@
     }
 
     /**
-    * Internal trie getter from a code point.
-    * Could be faster(?) but longer with
-    * {@code if((c32)<=0xd7ff) { (result)=_TRIE_GET_RAW(trie, data, 0, c32); }}
-    * Gets the offset to data which the codepoint points to
-    * @param ch codepoint
-    * @return offset to data
-    */
+     * Internal trie getter from a code point.
+     * Could be faster(?) but longer with
+     * {@code if((c32)<=0xd7ff) { (result)=_TRIE_GET_RAW(trie, data, 0, c32); }}
+     * Gets the offset to data which the codepoint points to
+     * @param ch codepoint
+     * @return offset to data
+     */
     protected final int getCodePointOffset(int ch)
     {
         // if ((ch >> 16) == 0) slower
@@ -321,7 +273,7 @@
             return getSurrogateOffset(UTF16.getLeadSurrogate(ch),
                                       (char)(ch & SURROGATE_MASK_));
         } else {
-            // return -1 // if there is an error, in this case we return
+            // return -1 if there is an error, in this case we return
             return -1;
         }
     }
@@ -343,15 +295,6 @@
     }
 
     /**
-    * Determines if this is a 32 bit trie
-    * @return true if options specifies this is a 32 bit trie
-    */
-    protected final boolean isIntTrie()
-    {
-        return (m_options_ & HEADER_OPTIONS_DATA_IS_32_BIT_) != 0;
-    }
-
-    /**
     * Determines if this is a 16 bit trie
     * @return true if this is a 16 bit trie
     */
@@ -363,8 +306,8 @@
     // private data members --------------------------------------------
 
     /**
-    * Latin 1 option mask
-    */
+     * Latin 1 option mask
+     */
     protected static final int HEADER_OPTIONS_LATIN1_IS_LINEAR_MASK_ = 0x200;
     /**
     * Constant number to authenticate the byte block
@@ -378,28 +321,28 @@
     protected static final int HEADER_OPTIONS_DATA_IS_32_BIT_ = 0x100;
 
     /**
-    * Flag indicator for Latin quick access data block
-    */
+     * Flag indicator for Latin quick access data block
+     */
     private boolean m_isLatin1Linear_;
 
     /**
-    * <p>Trie options field.</p>
-    * <p>options bit field:<br>
-    * 9  1 = Latin-1 data is stored linearly at data + DATA_BLOCK_LENGTH<br>
-    * 8  0 = 16-bit data, 1=32-bit data<br>
-    * 7..4  INDEX_STAGE_1_SHIFT   // 0..INDEX_STAGE_2_SHIFT<br>
-    * 3..0  INDEX_STAGE_2_SHIFT   // 1..9<br>
-    */
+     * <p>Trie options field.</p>
+     * <p>options bit field:<br>
+     * 9  1 = Latin-1 data is stored linearly at data + DATA_BLOCK_LENGTH<br>
+     * 8  0 = 16-bit data, 1=32-bit data<br>
+     * 7..4  INDEX_STAGE_1_SHIFT   // 0..INDEX_STAGE_2_SHIFT<br>
+     * 3..0  INDEX_STAGE_2_SHIFT   // 1..9<br>
+     */
     private int m_options_;
 
     // private methods ---------------------------------------------------
 
     /**
-    * Authenticates raw data header.
-    * Checking the header information, signature and options.
-    * @param signature This contains the options and type of a Trie
-    * @return true if the header is authenticated valid
-    */
+     * Authenticates raw data header.
+     * Checking the header information, signature and options.
+     * @param signature This contains the options and type of a Trie
+     * @return true if the header is authenticated valid
+     */
     private final boolean checkHeader(int signature)
     {
         // check the signature
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/Trie2.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,655 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/*
+ *******************************************************************************
+ * Copyright (C) 2009-2014, International Business Machines Corporation and
+ * others. All Rights Reserved.
+ *******************************************************************************
+ */
+
+package sun.text.normalizer;
+
+import java.io.IOException;
+import java.nio.ByteBuffer;
+import java.nio.ByteOrder;
+import java.util.Iterator;
+import java.util.NoSuchElementException;
+
+
+/**
+ * This is the interface and common implementation of a Unicode Trie2.
+ * It is a kind of compressed table that maps from Unicode code points (0..0x10ffff)
+ * to 16- or 32-bit integer values.  It works best when there are ranges of
+ * characters with the same value, which is generally the case with Unicode
+ * character properties.
+ *
+ * This is the second common version of a Unicode trie (hence the name Trie2).
+ *
+ */
+abstract class Trie2 implements Iterable<Trie2.Range> {
+
+    /**
+     * Create a Trie2 from its serialized form.  Inverse of utrie2_serialize().
+     *
+     * Reads from the current position and leaves the buffer after the end of the trie.
+     *
+     * The serialized format is identical between ICU4C and ICU4J, so this function
+     * will work with serialized Trie2s from either.
+     *
+     * The actual type of the returned Trie2 will be either Trie2_16 or Trie2_32, depending
+     * on the width of the data.
+     *
+     * To obtain the width of the Trie2, check the actual class type of the returned Trie2.
+     * Or use the createFromSerialized() function of Trie2_16 or Trie2_32, which will
+     * return only Tries of their specific type/size.
+     *
+     * The serialized Trie2 on the stream may be in either little or big endian byte order.
+     * This allows using serialized Tries from ICU4C without needing to consider the
+     * byte order of the system that created them.
+     *
+     * @param bytes a byte buffer to the serialized form of a UTrie2.
+     * @return An unserialized Trie2, ready for use.
+     * @throws IllegalArgumentException if the stream does not contain a serialized Trie2.
+     * @throws IOException if a read error occurs in the buffer.
+     *
+     */
+    public static Trie2 createFromSerialized(ByteBuffer bytes) throws IOException {
+         //    From ICU4C utrie2_impl.h
+         //    * Trie2 data structure in serialized form:
+         //     *
+         //     * UTrie2Header header;
+         //     * uint16_t index[header.index2Length];
+         //     * uint16_t data[header.shiftedDataLength<<2];  -- or uint32_t data[...]
+         //     * @internal
+         //     */
+         //    typedef struct UTrie2Header {
+         //        /** "Tri2" in big-endian US-ASCII (0x54726932) */
+         //        uint32_t signature;
+
+         //       /**
+         //         * options bit field:
+         //         * 15.. 4   reserved (0)
+         //         *  3.. 0   UTrie2ValueBits valueBits
+         //         */
+         //        uint16_t options;
+         //
+         //        /** UTRIE2_INDEX_1_OFFSET..UTRIE2_MAX_INDEX_LENGTH */
+         //        uint16_t indexLength;
+         //
+         //        /** (UTRIE2_DATA_START_OFFSET..UTRIE2_MAX_DATA_LENGTH)>>UTRIE2_INDEX_SHIFT */
+         //        uint16_t shiftedDataLength;
+         //
+         //        /** Null index and data blocks, not shifted. */
+         //        uint16_t index2NullOffset, dataNullOffset;
+         //
+         //        /**
+         //         * First code point of the single-value range ending with U+10ffff,
+         //         * rounded up and then shifted right by UTRIE2_SHIFT_1.
+         //         */
+         //        uint16_t shiftedHighStart;
+         //    } UTrie2Header;
+
+        ByteOrder outerByteOrder = bytes.order();
+        try {
+            UTrie2Header header = new UTrie2Header();
+
+            /* check the signature */
+            header.signature = bytes.getInt();
+            switch (header.signature) {
+            case 0x54726932:
+                // The buffer is already set to the trie data byte order.
+                break;
+            case 0x32697254:
+                // Temporarily reverse the byte order.
+                boolean isBigEndian = outerByteOrder == ByteOrder.BIG_ENDIAN;
+                bytes.order(isBigEndian ? ByteOrder.LITTLE_ENDIAN : ByteOrder.BIG_ENDIAN);
+                header.signature = 0x54726932;
+                break;
+            default:
+                throw new IllegalArgumentException("Buffer does not contain a serialized UTrie2");
+            }
+
+            header.options = bytes.getChar();
+            header.indexLength = bytes.getChar();
+            header.shiftedDataLength = bytes.getChar();
+            header.index2NullOffset = bytes.getChar();
+            header.dataNullOffset   = bytes.getChar();
+            header.shiftedHighStart = bytes.getChar();
+
+            if ((header.options & UTRIE2_OPTIONS_VALUE_BITS_MASK) != 0) {
+                throw new IllegalArgumentException("UTrie2 serialized format error.");
+            }
+
+            Trie2 This;
+            This = new Trie2_16();
+            This.header = header;
+
+            /* get the length values and offsets */
+            This.indexLength      = header.indexLength;
+            This.dataLength       = header.shiftedDataLength << UTRIE2_INDEX_SHIFT;
+            This.index2NullOffset = header.index2NullOffset;
+            This.dataNullOffset   = header.dataNullOffset;
+            This.highStart        = header.shiftedHighStart << UTRIE2_SHIFT_1;
+            This.highValueIndex   = This.dataLength - UTRIE2_DATA_GRANULARITY;
+            This.highValueIndex += This.indexLength;
+
+            // Allocate the Trie2 index array. If the data width is 16 bits, the array also
+            // includes the space for the data.
+
+            int indexArraySize = This.indexLength;
+            indexArraySize += This.dataLength;
+            This.index = new char[indexArraySize];
+
+            /* Read in the index */
+            int i;
+            for (i=0; i<This.indexLength; i++) {
+                This.index[i] = bytes.getChar();
+            }
+
+            /* Read in the data. 16 bit data goes in the same array as the index.
+             * 32 bit data goes in its own separate data array.
+             */
+            This.data16 = This.indexLength;
+            for (i=0; i<This.dataLength; i++) {
+                This.index[This.data16 + i] = bytes.getChar();
+            }
+
+            This.data32 = null;
+            This.initialValue = This.index[This.dataNullOffset];
+            This.errorValue   = This.index[This.data16+UTRIE2_BAD_UTF8_DATA_OFFSET];
+
+            return This;
+        } finally {
+            bytes.order(outerByteOrder);
+        }
+    }
+
+    /**
+     * Get the value for a code point as stored in the Trie2.
+     *
+     * @param codePoint the code point
+     * @return the value
+     */
+    abstract public int get(int codePoint);
+
+    /**
+     * Get the trie value for a UTF-16 code unit.
+     *
+     * A Trie2 stores two distinct values for input in the lead surrogate
+     * range, one for lead surrogates, which is the value that will be
+     * returned by this function, and a second value that is returned
+     * by Trie2.get().
+     *
+     * For code units outside of the lead surrogate range, this function
+     * returns the same result as Trie2.get().
+     *
+     * This function, together with the alternate value for lead surrogates,
+     * makes possible very efficient processing of UTF-16 strings without
+     * first converting surrogate pairs to their corresponding 32 bit code point
+     * values.
+     *
+     * At build-time, enumerate the contents of the Trie2 to see if there
+     * is non-trivial (non-initialValue) data for any of the supplementary
+     * code points associated with a lead surrogate.
+     * If so, then set a special (application-specific) value for the
+     * lead surrogate code _unit_, with Trie2Writable.setForLeadSurrogateCodeUnit().
+     *
+     * At runtime, use Trie2.getFromU16SingleLead(). If there is non-trivial
+     * data and the code unit is a lead surrogate, then check if a trail surrogate
+     * follows. If so, assemble the supplementary code point and look up its value
+     * with Trie2.get(); otherwise reset the lead
+     * surrogate's value or do a code point lookup for it.
+     *
+     * If there is only trivial data for lead and trail surrogates, then processing
+     * can often skip them. For example, in normalization or case mapping
+     * all characters that do not have any mappings are simply copied as is.
+     *
+     * @param c the code point or lead surrogate value.
+     * @return the value
+     */
+    abstract public int getFromU16SingleLead(char c);
+
+    /**
+     * When iterating over the contents of a Trie2, Elements of this type are produced.
+     * The iterator will return one item for each contiguous range of codepoints  having the same value.
+     *
+     * When iterating, the same Trie2EnumRange object will be reused and returned for each range.
+     * If you need to retain complete iteration results, clone each returned Trie2EnumRange,
+     * or save the range in some other way, before advancing to the next iteration step.
+     */
+    public static class Range {
+        public int     startCodePoint;
+        public int     endCodePoint;     // Inclusive.
+        public int     value;
+        public boolean leadSurrogate;
+
+        public boolean equals(Object other) {
+            if (other == null || !(other.getClass().equals(getClass()))) {
+                return false;
+            }
+            Range tother = (Range)other;
+            return this.startCodePoint == tother.startCodePoint &&
+                   this.endCodePoint   == tother.endCodePoint   &&
+                   this.value          == tother.value          &&
+                   this.leadSurrogate  == tother.leadSurrogate;
+        }
+
+        public int hashCode() {
+            int h = initHash();
+            h = hashUChar32(h, startCodePoint);
+            h = hashUChar32(h, endCodePoint);
+            h = hashInt(h, value);
+            h = hashByte(h, leadSurrogate? 1: 0);
+            return h;
+        }
+    }
+
+    /**
+     *  Create an iterator over the value ranges in this Trie2.
+     *  Values from the Trie2 are not remapped or filtered, but are returned as they
+     *  are stored in the Trie2.
+     *
+     * @return an Iterator
+     */
+    public Iterator<Range> iterator() {
+        return iterator(defaultValueMapper);
+    }
+
+    private static ValueMapper defaultValueMapper = new ValueMapper() {
+        public int map(int in) {
+            return in;
+        }
+    };
+
+    /**
+     * Create an iterator over the value ranges from this Trie2.
+     * Values from the Trie2 are passed through a caller-supplied remapping function,
+     * and it is the remapped values that determine the ranges that
+     * will be produced by the iterator.
+     *
+     *
+     * @param mapper provides a function to remap values obtained from the Trie2.
+     * @return an Iterator
+     */
+    public Iterator<Range> iterator(ValueMapper mapper) {
+        return new Trie2Iterator(mapper);
+    }
+
+    /**
+     * When iterating over the contents of a Trie2, an instance of TrieValueMapper may
+     * be used to remap the values from the Trie2.  The remapped values will be used
+     * both in determining the ranges of codepoints and as the value to be returned
+     * for each range.
+     *
+     * Example of use, with an anonymous subclass of TrieValueMapper:
+     *
+     *
+     * ValueMapper m = new ValueMapper() {
+     *    int map(int in) {return in & 0x1f;};
+     * }
+     * for (Iterator<Trie2EnumRange> iter = trie.iterator(m); i.hasNext(); ) {
+     *     Trie2EnumRange r = i.next();
+     *     ...  // Do something with the range r.
+     * }
+     *
+     */
+    public interface ValueMapper {
+        public int  map(int originalVal);
+    }
+
+    //--------------------------------------------------------------------------------
+    //
+    // Below this point are internal implementation items.  No further public API.
+    //
+    //--------------------------------------------------------------------------------
+
+     /**
+     * Trie2 data structure in serialized form:
+     *
+     * UTrie2Header header;
+     * uint16_t index[header.index2Length];
+     * uint16_t data[header.shiftedDataLength<<2];  -- or uint32_t data[...]
+     *
+     * For Java, this is read from the stream into an instance of UTrie2Header.
+     * (The C version just places a struct over the raw serialized data.)
+     *
+     * @internal
+     */
+    static class UTrie2Header {
+        /** "Tri2" in big-endian US-ASCII (0x54726932) */
+        int signature;
+
+        /**
+         * options bit field (uint16_t):
+         * 15.. 4   reserved (0)
+         *  3.. 0   UTrie2ValueBits valueBits
+         */
+        int  options;
+
+        /** UTRIE2_INDEX_1_OFFSET..UTRIE2_MAX_INDEX_LENGTH  (uint16_t) */
+        int  indexLength;
+
+        /** (UTRIE2_DATA_START_OFFSET..UTRIE2_MAX_DATA_LENGTH)>>UTRIE2_INDEX_SHIFT  (uint16_t) */
+        int  shiftedDataLength;
+
+        /** Null index and data blocks, not shifted.  (uint16_t) */
+        int  index2NullOffset, dataNullOffset;
+
+        /**
+         * First code point of the single-value range ending with U+10ffff,
+         * rounded up and then shifted right by UTRIE2_SHIFT_1.  (uint16_t)
+         */
+        int shiftedHighStart;
+    }
+
+    //
+    //  Data members of UTrie2.
+    //
+    UTrie2Header  header;
+    char          index[];           // Index array.  Includes data for 16 bit Tries.
+    int           data16;            // Offset to data portion of the index array, if 16 bit data.
+                                     //    zero if 32 bit data.
+    int           data32[];          // NULL if 16b data is used via index
+
+    int           indexLength;
+    int           dataLength;
+    int           index2NullOffset;  // 0xffff if there is no dedicated index-2 null block
+    int           initialValue;
+
+    /** Value returned for out-of-range code points and illegal UTF-8. */
+    int           errorValue;
+
+    /* Start of the last range which ends at U+10ffff, and its value. */
+    int           highStart;
+    int           highValueIndex;
+
+    int           dataNullOffset;
+
+    /**
+     * Trie2 constants, defining shift widths, index array lengths, etc.
+     *
+     * These are needed for the runtime macros but users can treat these as
+     * implementation details and skip to the actual public API further below.
+     */
+
+    static final int UTRIE2_OPTIONS_VALUE_BITS_MASK=0x000f;
+
+
+    /** Shift size for getting the index-1 table offset. */
+    static final int UTRIE2_SHIFT_1=6+5;
+
+    /** Shift size for getting the index-2 table offset. */
+    static final int UTRIE2_SHIFT_2=5;
+
+    /**
+     * Difference between the two shift sizes,
+     * for getting an index-1 offset from an index-2 offset. 6=11-5
+     */
+    static final int UTRIE2_SHIFT_1_2=UTRIE2_SHIFT_1-UTRIE2_SHIFT_2;
+
+    /**
+     * Number of index-1 entries for the BMP. 32=0x20
+     * This part of the index-1 table is omitted from the serialized form.
+     */
+    static final int UTRIE2_OMITTED_BMP_INDEX_1_LENGTH=0x10000>>UTRIE2_SHIFT_1;
+
+    /** Number of entries in an index-2 block. 64=0x40 */
+    static final int UTRIE2_INDEX_2_BLOCK_LENGTH=1<<UTRIE2_SHIFT_1_2;
+
+    /** Mask for getting the lower bits for the in-index-2-block offset. */
+    static final int UTRIE2_INDEX_2_MASK=UTRIE2_INDEX_2_BLOCK_LENGTH-1;
+
+    /** Number of entries in a data block. 32=0x20 */
+    static final int UTRIE2_DATA_BLOCK_LENGTH=1<<UTRIE2_SHIFT_2;
+
+    /** Mask for getting the lower bits for the in-data-block offset. */
+    static final int UTRIE2_DATA_MASK=UTRIE2_DATA_BLOCK_LENGTH-1;
+
+    /**
+     * Shift size for shifting left the index array values.
+     * Increases possible data size with 16-bit index values at the cost
+     * of compactability.
+     * This requires data blocks to be aligned by UTRIE2_DATA_GRANULARITY.
+     */
+    static final int UTRIE2_INDEX_SHIFT=2;
+
+    /** The alignment size of a data block. Also the granularity for compaction. */
+    static final int UTRIE2_DATA_GRANULARITY=1<<UTRIE2_INDEX_SHIFT;
+
+    /**
+     * The part of the index-2 table for U+D800..U+DBFF stores values for
+     * lead surrogate code _units_ not code _points_.
+     * Values for lead surrogate code _points_ are indexed with this portion of the table.
+     * Length=32=0x20=0x400>>UTRIE2_SHIFT_2. (There are 1024=0x400 lead surrogates.)
+     */
+    static final int UTRIE2_LSCP_INDEX_2_OFFSET=0x10000>>UTRIE2_SHIFT_2;
+    static final int UTRIE2_LSCP_INDEX_2_LENGTH=0x400>>UTRIE2_SHIFT_2;
+
+    /** Count the lengths of both BMP pieces. 2080=0x820 */
+    static final int UTRIE2_INDEX_2_BMP_LENGTH=UTRIE2_LSCP_INDEX_2_OFFSET+UTRIE2_LSCP_INDEX_2_LENGTH;
+
+    /**
+     * The 2-byte UTF-8 version of the index-2 table follows at offset 2080=0x820.
+     * Length 32=0x20 for lead bytes C0..DF, regardless of UTRIE2_SHIFT_2.
+     */
+    static final int UTRIE2_UTF8_2B_INDEX_2_OFFSET=UTRIE2_INDEX_2_BMP_LENGTH;
+    static final int UTRIE2_UTF8_2B_INDEX_2_LENGTH=0x800>>6;  /* U+0800 is the first code point after 2-byte UTF-8 */
+
+    /**
+     * The index-1 table, only used for supplementary code points, at offset 2112=0x840.
+     * Variable length, for code points up to highStart, where the last single-value range starts.
+     * Maximum length 512=0x200=0x100000>>UTRIE2_SHIFT_1.
+     * (For 0x100000 supplementary code points U+10000..U+10ffff.)
+     *
+     * The part of the index-2 table for supplementary code points starts
+     * after this index-1 table.
+     *
+     * Both the index-1 table and the following part of the index-2 table
+     * are omitted completely if there is only BMP data.
+     */
+    static final int UTRIE2_INDEX_1_OFFSET=UTRIE2_UTF8_2B_INDEX_2_OFFSET+UTRIE2_UTF8_2B_INDEX_2_LENGTH;
+
+    /**
+     * The illegal-UTF-8 data block follows the ASCII block, at offset 128=0x80.
+     * Used with linear access for single bytes 0..0xbf for simple error handling.
+     * Length 64=0x40, not UTRIE2_DATA_BLOCK_LENGTH.
+     */
+    static final int UTRIE2_BAD_UTF8_DATA_OFFSET=0x80;
+
+    /**
+     * Implementation class for an iterator over a Trie2.
+     *
+     *   Iteration over a Trie2 first returns all of the ranges that are indexed by code points,
+     *   then returns the special alternate values for the lead surrogates
+     *
+     * @internal
+     */
+    class Trie2Iterator implements Iterator<Range> {
+
+        // The normal constructor that configures the iterator to cover the complete
+        //   contents of the Trie2
+        Trie2Iterator(ValueMapper vm) {
+            mapper    = vm;
+            nextStart = 0;
+            limitCP   = 0x110000;
+            doLeadSurrogates = true;
+        }
+
+        /**
+         *  The main next() function for Trie2 iterators
+         *
+         */
+        public Range next() {
+            if (!hasNext()) {
+                throw new NoSuchElementException();
+            }
+            if (nextStart >= limitCP) {
+                // Switch over from iterating normal code point values to
+                //   doing the alternate lead-surrogate values.
+                doingCodePoints = false;
+                nextStart = 0xd800;
+            }
+            int   endOfRange = 0;
+            int   val = 0;
+            int   mappedVal = 0;
+
+            if (doingCodePoints) {
+                // Iteration over code point values.
+                val = get(nextStart);
+                mappedVal = mapper.map(val);
+                endOfRange = rangeEnd(nextStart, limitCP, val);
+                // Loop once for each range in the Trie2 with the same raw (unmapped) value.
+                // Loop continues so long as the mapped values are the same.
+                for (;;) {
+                    if (endOfRange >= limitCP-1) {
+                        break;
+                    }
+                    val = get(endOfRange+1);
+                    if (mapper.map(val) != mappedVal) {
+                        break;
+                    }
+                    endOfRange = rangeEnd(endOfRange+1, limitCP, val);
+                }
+            } else {
+                // Iteration over the alternate lead surrogate values.
+                val = getFromU16SingleLead((char)nextStart);
+                mappedVal = mapper.map(val);
+                endOfRange = rangeEndLS((char)nextStart);
+                // Loop once for each range in the Trie2 with the same raw (unmapped) value.
+                // Loop continues so long as the mapped values are the same.
+                for (;;) {
+                    if (endOfRange >= 0xdbff) {
+                        break;
+                    }
+                    val = getFromU16SingleLead((char)(endOfRange+1));
+                    if (mapper.map(val) != mappedVal) {
+                        break;
+                    }
+                    endOfRange = rangeEndLS((char)(endOfRange+1));
+                }
+            }
+            returnValue.startCodePoint = nextStart;
+            returnValue.endCodePoint   = endOfRange;
+            returnValue.value          = mappedVal;
+            returnValue.leadSurrogate  = !doingCodePoints;
+            nextStart                  = endOfRange+1;
+            return returnValue;
+        }
+
+        /**
+         *
+         */
+        public boolean hasNext() {
+            return doingCodePoints && (doLeadSurrogates || nextStart < limitCP) || nextStart < 0xdc00;
+        }
+
+        private int rangeEndLS(char startingLS) {
+            if (startingLS >= 0xdbff) {
+                return 0xdbff;
+            }
+
+            int c;
+            int val = getFromU16SingleLead(startingLS);
+            for (c = startingLS+1; c <= 0x0dbff; c++) {
+                if (getFromU16SingleLead((char)c) != val) {
+                    break;
+                }
+            }
+            return c-1;
+        }
+
+        //
+        //   Iteration State Variables
+        //
+        private ValueMapper    mapper;
+        private Range          returnValue = new Range();
+        // The starting code point for the next range to be returned.
+        private int            nextStart;
+        // The upper limit for the last normal range to be returned.  Normally 0x110000, but
+        //   may be lower when iterating over the code points for a single lead surrogate.
+        private int            limitCP;
+
+        // True while iterating over the the Trie2 values for code points.
+        // False while iterating over the alternate values for lead surrogates.
+        private boolean        doingCodePoints = true;
+
+        // True if the iterator should iterate the special values for lead surrogates in
+        //   addition to the normal values for code points.
+        private boolean        doLeadSurrogates = true;
+    }
+
+    /**
+     * Find the last character in a contiguous range of characters with the
+     * same Trie2 value as the input character.
+     *
+     * @param c  The character to begin with.
+     * @return   The last contiguous character with the same value.
+     */
+    int rangeEnd(int start, int limitp, int val) {
+        int c;
+        int limit = Math.min(highStart, limitp);
+
+        for (c = start+1; c < limit; c++) {
+            if (get(c) != val) {
+                break;
+            }
+        }
+        if (c >= highStart) {
+            c = limitp;
+        }
+        return c - 1;
+    }
+
+
+    //
+    //  Hashing implementation functions.  FNV hash.  Respected public domain algorithm.
+    //
+    private static int initHash() {
+        return 0x811c9DC5;  // unsigned 2166136261
+    }
+
+    private static int hashByte(int h, int b) {
+        h = h * 16777619;
+        h = h ^ b;
+        return h;
+    }
+
+    private static int hashUChar32(int h, int c) {
+        h = Trie2.hashByte(h, c & 255);
+        h = Trie2.hashByte(h, (c>>8) & 255);
+        h = Trie2.hashByte(h, c>>16);
+        return h;
+    }
+
+    private static int hashInt(int h, int i) {
+        h = Trie2.hashByte(h, i & 255);
+        h = Trie2.hashByte(h, (i>>8) & 255);
+        h = Trie2.hashByte(h, (i>>16) & 255);
+        h = Trie2.hashByte(h, (i>>24) & 255);
+        return h;
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/Trie2_16.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,167 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/*
+ *******************************************************************************
+ * Copyright (C) 2009-2014, International Business Machines Corporation and
+ * others. All Rights Reserved.
+ *******************************************************************************
+ */
+
+package sun.text.normalizer;
+
+import java.io.IOException;
+import java.nio.ByteBuffer;
+
+
+/**
+ * @author aheninger
+ *
+ * A read-only Trie2, holding 16 bit data values.
+ *
+ * A Trie2 is a highly optimized data structure for mapping from Unicode
+ * code points (values ranging from 0 to 0x10ffff) to a 16 or 32 bit value.
+ *
+ * See class Trie2 for descriptions of the API for accessing the contents of a trie.
+ *
+ * The fundamental data access methods are declared final in this class, with
+ * the intent that applications might gain a little extra performance, when compared
+ * with calling the same methods via the abstract UTrie2 base class.
+ */
+public final class Trie2_16 extends Trie2 {
+
+    /**
+     *  Internal constructor, not for general use.
+     */
+    Trie2_16() {
+    }
+
+
+    /**
+     * Create a Trie2 from its serialized form.  Inverse of utrie2_serialize().
+     * The serialized format is identical between ICU4C and ICU4J, so this function
+     * will work with serialized Trie2s from either.
+     *
+     * The serialized Trie2 in the bytes may be in either little or big endian byte order.
+     * This allows using serialized Tries from ICU4C without needing to consider the
+     * byte order of the system that created them.
+     *
+     * @param bytes a byte buffer to the serialized form of a UTrie2.
+     * @return An unserialized Trie2_16, ready for use.
+     * @throws IllegalArgumentException if the buffer does not contain a serialized Trie2.
+     * @throws IOException if a read error occurs in the buffer.
+     * @throws ClassCastException if the bytes contain a serialized Trie2_32
+     */
+    public static Trie2_16  createFromSerialized(ByteBuffer bytes) throws IOException {
+        return (Trie2_16) Trie2.createFromSerialized(bytes);
+    }
+
+    /**
+     * Get the value for a code point as stored in the Trie2.
+     *
+     * @param codePoint the code point
+     * @return the value
+     */
+    @Override
+    public final int get(int codePoint) {
+        int value;
+        int ix;
+
+        if (codePoint >= 0) {
+            if (codePoint < 0x0d800 || (codePoint > 0x0dbff && codePoint <= 0x0ffff)) {
+                // Ordinary BMP code point, excluding leading surrogates.
+                // BMP uses a single level lookup.  BMP index starts at offset 0 in the Trie2 index.
+                // 16 bit data is stored in the index array itself.
+                ix = index[codePoint >> UTRIE2_SHIFT_2];
+                ix = (ix << UTRIE2_INDEX_SHIFT) + (codePoint & UTRIE2_DATA_MASK);
+                value = index[ix];
+                return value;
+            }
+            if (codePoint <= 0xffff) {
+                // Lead Surrogate Code Point.  A Separate index section is stored for
+                // lead surrogate code units and code points.
+                //   The main index has the code unit data.
+                //   For this function, we need the code point data.
+                // Note: this expression could be refactored for slightly improved efficiency, but
+                //       surrogate code points will be so rare in practice that it's not worth it.
+                ix = index[UTRIE2_LSCP_INDEX_2_OFFSET + ((codePoint - 0xd800) >> UTRIE2_SHIFT_2)];
+                ix = (ix << UTRIE2_INDEX_SHIFT) + (codePoint & UTRIE2_DATA_MASK);
+                value = index[ix];
+                return value;
+            }
+            if (codePoint < highStart) {
+                // Supplemental code point, use two-level lookup.
+                ix = (UTRIE2_INDEX_1_OFFSET - UTRIE2_OMITTED_BMP_INDEX_1_LENGTH) + (codePoint >> UTRIE2_SHIFT_1);
+                ix = index[ix];
+                ix += (codePoint >> UTRIE2_SHIFT_2) & UTRIE2_INDEX_2_MASK;
+                ix = index[ix];
+                ix = (ix << UTRIE2_INDEX_SHIFT) + (codePoint & UTRIE2_DATA_MASK);
+                value = index[ix];
+                return value;
+            }
+            if (codePoint <= 0x10ffff) {
+                value = index[highValueIndex];
+                return value;
+            }
+        }
+
+        // Fall through.  The code point is outside of the legal range of 0..0x10ffff.
+        return errorValue;
+    }
+
+
+    /**
+     * Get a Trie2 value for a UTF-16 code unit.
+     *
+     * This function returns the same value as get() if the input
+     * character is outside of the lead surrogate range
+     *
+     * There are two values stored in a Trie2 for inputs in the lead
+     * surrogate range.  This function returns the alternate value,
+     * while Trie2.get() returns the main value.
+     *
+     * @param codeUnit a 16 bit code unit or lead surrogate value.
+     * @return the value
+     */
+    @Override
+    public int getFromU16SingleLead(char codeUnit) {
+        int value;
+        int ix;
+
+        // Because the input is a 16 bit char, we can skip the tests for it being in
+        // the BMP range.  It is.
+        ix = index[codeUnit >> UTRIE2_SHIFT_2];
+        ix = (ix << UTRIE2_INDEX_SHIFT) + (codeUnit & UTRIE2_DATA_MASK);
+        value = index[ix];
+        return value;
+    }
+
+    /**
+     * @return the number of bytes of the serialized trie
+     */
+    public int getSerializedLength() {
+        return 16+(header.indexLength+dataLength)*2;
+    }
+}
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/TrieIterator.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,547 +0,0 @@
-/*
- * Copyright (c) 2005, 2009, 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.
- */
-/*
- *******************************************************************************
- * (C) Copyright IBM Corp. and others, 1996-2009 - All Rights Reserved         *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
- *******************************************************************************
- */
-
-package sun.text.normalizer;
-
-/**
- * Class enabling iteration of the values in a Trie.
- * <p>Result of each iteration contains the interval of codepoints that have
- * the same value type and the value type itself.
- * <p>The comparison of each codepoint value is done via extract(), which the
- * default implementation is to return the value as it is.
- * <p>Method extract() can be overwritten to perform manipulations on
- * codepoint values in order to perform specialized comparison.
- * <p>TrieIterator is designed to be a generic iterator for the CharTrie
- * and the IntTrie, hence to accommodate both types of data, the return
- * result will be in terms of int (32 bit) values.
- * <p>See com.ibm.icu.text.UCharacterTypeIterator for examples of use.
- * <p>Notes for porting utrie_enum from icu4c to icu4j:<br>
- * Internally, icu4c's utrie_enum performs all iterations in its body. In Java
- * sense, the caller will have to pass a object with a callback function
- * UTrieEnumRange(const void *context, UChar32 start, UChar32 limit,
- * uint32_t value) into utrie_enum. utrie_enum will then find ranges of
- * codepoints with the same value as determined by
- * UTrieEnumValue(const void *context, uint32_t value). for each range,
- * utrie_enum calls the callback function to perform a task. In this way,
- * icu4c performs the iteration within utrie_enum.
- * To follow the JDK model, icu4j is slightly different from icu4c.
- * Instead of requesting the caller to implement an object for a callback.
- * The caller will have to implement a subclass of TrieIterator, fleshing out
- * the method extract(int) (equivalent to UTrieEnumValue). Independent of icu4j,
- * the caller will have to code his own iteration and flesh out the task
- * (equivalent to UTrieEnumRange) to be performed in the iteration loop.
- *
- * <p>There are basically 3 usage scenarios for porting:
- * <p>1) UTrieEnumValue is the only implemented callback then just implement a
- * subclass of TrieIterator and override the extract(int) method. The
- * extract(int) method is analogus to UTrieEnumValue callback.
- *
- * <p>2) UTrieEnumValue and UTrieEnumRange both are implemented then implement
- * a subclass of TrieIterator, override the extract method and iterate, e.g.<br>
- * {@code utrie_enum(&normTrie, _enumPropertyStartsValue, _enumPropertyStartsRange,
- *               set);}<br>
- * In Java:<br>
- * <pre>
- * class TrieIteratorImpl extends TrieIterator{
- *     public TrieIteratorImpl(Trie data){
- *         super(data);
- *     }
- *     public int extract(int value){
- *         // port the implementation of _enumPropertyStartsValue here
- *     }
- * }
- * ....
- * TrieIterator fcdIter  = new TrieIteratorImpl(fcdTrieImpl.fcdTrie);
- * while(fcdIter.next(result)) {
- *     // port the implementation of _enumPropertyStartsRange
- * }
- * </pre>
- *
- * <p>3) UTrieEnumRange is the only implemented callback then just implement
- * the while loop, when utrie_enum is called
- * <pre>{@code
- * // utrie_enum(&fcdTrie, NULL, _enumPropertyStartsRange, set);
- * TrieIterator fcdIter  = new TrieIterator(fcdTrieImpl.fcdTrie);
- * while(fcdIter.next(result)){
- *     set.add(result.start);
- * }
- * }</pre>
- *
- * @author synwee
- * @see com.ibm.icu.impl.Trie
- * @see com.ibm.icu.lang.UCharacterTypeIterator
- * @since release 2.1, Jan 17 2002
- */
-public class TrieIterator implements RangeValueIterator
-{
-
-    // public constructor ---------------------------------------------
-
-    /**
-    * TrieEnumeration constructor
-    * @param trie to be used
-    * @exception IllegalArgumentException throw when argument is null.
-    */
-    public TrieIterator(Trie trie)
-    {
-        if (trie == null) {
-            throw new IllegalArgumentException(
-                                          "Argument trie cannot be null");
-        }
-        m_trie_             = trie;
-        // synwee: check that extract belongs to the child class
-        m_initialValue_     = extract(m_trie_.getInitialValue());
-        reset();
-    }
-
-    // public methods -------------------------------------------------
-
-    /**
-    * <p>Returns true if we are not at the end of the iteration, false
-    * otherwise.</p>
-    * <p>The next set of codepoints with the same value type will be
-    * calculated during this call and returned in the arguement element.</p>
-    * @param element return result
-    * @return true if we are not at the end of the iteration, false otherwise.
-    * @exception NoSuchElementException - if no more elements exist.
-    * @see com.ibm.icu.util.RangeValueIterator.Element
-    */
-    public final boolean next(Element element)
-    {
-        if (m_nextCodepoint_ > UCharacter.MAX_VALUE) {
-            return false;
-        }
-        if (m_nextCodepoint_ < UCharacter.SUPPLEMENTARY_MIN_VALUE &&
-            calculateNextBMPElement(element)) {
-            return true;
-        }
-        calculateNextSupplementaryElement(element);
-        return true;
-    }
-
-    /**
-    * Resets the iterator to the beginning of the iteration
-    */
-    public final void reset()
-    {
-        m_currentCodepoint_ = 0;
-        m_nextCodepoint_    = 0;
-        m_nextIndex_        = 0;
-        m_nextBlock_ = m_trie_.m_index_[0] << Trie.INDEX_STAGE_2_SHIFT_;
-        if (m_nextBlock_ == 0) {
-            m_nextValue_ = m_initialValue_;
-        }
-        else {
-            m_nextValue_ = extract(m_trie_.getValue(m_nextBlock_));
-        }
-        m_nextBlockIndex_ = 0;
-        m_nextTrailIndexOffset_ = TRAIL_SURROGATE_INDEX_BLOCK_LENGTH_;
-    }
-
-    // protected methods ----------------------------------------------
-
-    /**
-    * Called by next() to extracts a 32 bit value from a trie value
-    * used for comparison.
-    * This method is to be overwritten if special manipulation is to be done
-    * to retrieve a relevant comparison.
-    * The default function is to return the value as it is.
-    * @param value a value from the trie
-    * @return extracted value
-    */
-    protected int extract(int value)
-    {
-        return value;
-    }
-
-    // private methods ------------------------------------------------
-
-    /**
-    * Set the result values
-    * @param element return result object
-    * @param start codepoint of range
-    * @param limit (end + 1) codepoint of range
-    * @param value common value of range
-    */
-    private final void setResult(Element element, int start, int limit,
-                                 int value)
-    {
-        element.start = start;
-        element.limit = limit;
-        element.value = value;
-    }
-
-    /**
-    * Finding the next element.
-    * This method is called just before returning the result of
-    * next().
-    * We always store the next element before it is requested.
-    * In the case that we have to continue calculations into the
-    * supplementary planes, a false will be returned.
-    * @param element return result object
-    * @return true if the next range is found, false if we have to proceed to
-    *         the supplementary range.
-    */
-    private final boolean calculateNextBMPElement(Element element)
-    {
-        int currentBlock    = m_nextBlock_;
-        int currentValue    = m_nextValue_;
-        m_currentCodepoint_ = m_nextCodepoint_;
-        m_nextCodepoint_ ++;
-        m_nextBlockIndex_ ++;
-        if (!checkBlockDetail(currentValue)) {
-            setResult(element, m_currentCodepoint_, m_nextCodepoint_,
-                      currentValue);
-            return true;
-        }
-        // synwee check that next block index == 0 here
-        // enumerate BMP - the main loop enumerates data blocks
-        while (m_nextCodepoint_ < UCharacter.SUPPLEMENTARY_MIN_VALUE) {
-            m_nextIndex_ ++;
-            // because of the way the character is split to form the index
-            // the lead surrogate and trail surrogate can not be in the
-            // mid of a block
-            if (m_nextCodepoint_ == LEAD_SURROGATE_MIN_VALUE_) {
-                // skip lead surrogate code units,
-                // go to lead surrogate codepoints
-                m_nextIndex_ = BMP_INDEX_LENGTH_;
-            }
-            else if (m_nextCodepoint_ == TRAIL_SURROGATE_MIN_VALUE_) {
-                // go back to regular BMP code points
-                m_nextIndex_ = m_nextCodepoint_ >> Trie.INDEX_STAGE_1_SHIFT_;
-            }
-
-            m_nextBlockIndex_ = 0;
-            if (!checkBlock(currentBlock, currentValue)) {
-                setResult(element, m_currentCodepoint_, m_nextCodepoint_,
-                          currentValue);
-                return true;
-            }
-        }
-        m_nextCodepoint_ --;   // step one back since this value has not been
-        m_nextBlockIndex_ --;  // retrieved yet.
-        return false;
-    }
-
-    /**
-    * Finds the next supplementary element.
-    * For each entry in the trie, the value to be delivered is passed through
-    * extract().
-    * We always store the next element before it is requested.
-    * Called after calculateNextBMP() completes its round of BMP characters.
-    * There is a slight difference in the usage of m_currentCodepoint_
-    * here as compared to calculateNextBMP(). Though both represents the
-    * lower bound of the next element, in calculateNextBMP() it gets set
-    * at the start of any loop, where-else, in calculateNextSupplementary()
-    * since m_currentCodepoint_ already contains the lower bound of the
-    * next element (passed down from calculateNextBMP()), we keep it till
-    * the end before resetting it to the new value.
-    * Note, if there are no more iterations, it will never get to here.
-    * Blocked out by next().
-    * @param element return result object
-    */
-    private final void calculateNextSupplementaryElement(Element element)
-    {
-        int currentValue = m_nextValue_;
-        int currentBlock = m_nextBlock_;
-        m_nextCodepoint_ ++;
-        m_nextBlockIndex_ ++;
-
-        if (UTF16.getTrailSurrogate(m_nextCodepoint_)
-                                        != UTF16.TRAIL_SURROGATE_MIN_VALUE) {
-            // this piece is only called when we are in the middle of a lead
-            // surrogate block
-            if (!checkNullNextTrailIndex() && !checkBlockDetail(currentValue)) {
-                setResult(element, m_currentCodepoint_, m_nextCodepoint_,
-                          currentValue);
-                m_currentCodepoint_ = m_nextCodepoint_;
-                return;
-            }
-            // we have cleared one block
-            m_nextIndex_ ++;
-            m_nextTrailIndexOffset_ ++;
-            if (!checkTrailBlock(currentBlock, currentValue)) {
-                setResult(element, m_currentCodepoint_, m_nextCodepoint_,
-                          currentValue);
-                m_currentCodepoint_ = m_nextCodepoint_;
-                return;
-            }
-        }
-        int nextLead  = UTF16.getLeadSurrogate(m_nextCodepoint_);
-        // enumerate supplementary code points
-        while (nextLead < TRAIL_SURROGATE_MIN_VALUE_) {
-            // lead surrogate access
-            int leadBlock =
-                   m_trie_.m_index_[nextLead >> Trie.INDEX_STAGE_1_SHIFT_] <<
-                                                   Trie.INDEX_STAGE_2_SHIFT_;
-            if (leadBlock == m_trie_.m_dataOffset_) {
-                // no entries for a whole block of lead surrogates
-                if (currentValue != m_initialValue_) {
-                    m_nextValue_      = m_initialValue_;
-                    m_nextBlock_      = 0;
-                    m_nextBlockIndex_ = 0;
-                    setResult(element, m_currentCodepoint_, m_nextCodepoint_,
-                              currentValue);
-                    m_currentCodepoint_ = m_nextCodepoint_;
-                    return;
-                }
-
-                nextLead += DATA_BLOCK_LENGTH_;
-                // number of total affected supplementary codepoints in one
-                // block
-                // this is not a simple addition of
-                // DATA_BLOCK_SUPPLEMENTARY_LENGTH since we need to consider
-                // that we might have moved some of the codepoints
-                m_nextCodepoint_ = UCharacterProperty.getRawSupplementary(
-                                     (char)nextLead,
-                                     (char)UTF16.TRAIL_SURROGATE_MIN_VALUE);
-                continue;
-            }
-            if (m_trie_.m_dataManipulate_ == null) {
-                throw new NullPointerException(
-                            "The field DataManipulate in this Trie is null");
-            }
-            // enumerate trail surrogates for this lead surrogate
-            m_nextIndex_ = m_trie_.m_dataManipulate_.getFoldingOffset(
-                               m_trie_.getValue(leadBlock +
-                                   (nextLead & Trie.INDEX_STAGE_3_MASK_)));
-            if (m_nextIndex_ <= 0) {
-                // no data for this lead surrogate
-                if (currentValue != m_initialValue_) {
-                    m_nextValue_      = m_initialValue_;
-                    m_nextBlock_      = 0;
-                    m_nextBlockIndex_ = 0;
-                    setResult(element, m_currentCodepoint_, m_nextCodepoint_,
-                              currentValue);
-                    m_currentCodepoint_ = m_nextCodepoint_;
-                    return;
-                }
-                m_nextCodepoint_ += TRAIL_SURROGATE_COUNT_;
-            } else {
-                m_nextTrailIndexOffset_ = 0;
-                if (!checkTrailBlock(currentBlock, currentValue)) {
-                    setResult(element, m_currentCodepoint_, m_nextCodepoint_,
-                              currentValue);
-                    m_currentCodepoint_ = m_nextCodepoint_;
-                    return;
-                }
-            }
-            nextLead ++;
-         }
-
-         // deliver last range
-         setResult(element, m_currentCodepoint_, UCharacter.MAX_VALUE + 1,
-                   currentValue);
-    }
-
-    /**
-    * Internal block value calculations
-    * Performs calculations on a data block to find codepoints in m_nextBlock_
-    * after the index m_nextBlockIndex_ that has the same value.
-    * Note m_*_ variables at this point is the next codepoint whose value
-    * has not been calculated.
-    * But when returned with false, it will be the last codepoint whose
-    * value has been calculated.
-    * @param currentValue the value which other codepoints are tested against
-    * @return true if the whole block has the same value as currentValue or if
-    *              the whole block has been calculated, false otherwise.
-    */
-    private final boolean checkBlockDetail(int currentValue)
-    {
-        while (m_nextBlockIndex_ < DATA_BLOCK_LENGTH_) {
-            m_nextValue_ = extract(m_trie_.getValue(m_nextBlock_ +
-                                                    m_nextBlockIndex_));
-            if (m_nextValue_ != currentValue) {
-                return false;
-            }
-            ++ m_nextBlockIndex_;
-            ++ m_nextCodepoint_;
-        }
-        return true;
-    }
-
-    /**
-    * Internal block value calculations
-    * Performs calculations on a data block to find codepoints in m_nextBlock_
-    * that has the same value.
-    * Will call checkBlockDetail() if highlevel check fails.
-    * Note m_*_ variables at this point is the next codepoint whose value
-    * has not been calculated.
-    * @param currentBlock the initial block containing all currentValue
-    * @param currentValue the value which other codepoints are tested against
-    * @return true if the whole block has the same value as currentValue or if
-    *              the whole block has been calculated, false otherwise.
-    */
-    private final boolean checkBlock(int currentBlock, int currentValue)
-    {
-        m_nextBlock_ = m_trie_.m_index_[m_nextIndex_] <<
-                                                  Trie.INDEX_STAGE_2_SHIFT_;
-        if (m_nextBlock_ == currentBlock &&
-            (m_nextCodepoint_ - m_currentCodepoint_) >= DATA_BLOCK_LENGTH_) {
-            // the block is the same as the previous one, filled with
-            // currentValue
-            m_nextCodepoint_ += DATA_BLOCK_LENGTH_;
-        }
-        else if (m_nextBlock_ == 0) {
-            // this is the all-initial-value block
-            if (currentValue != m_initialValue_) {
-                m_nextValue_      = m_initialValue_;
-                m_nextBlockIndex_ = 0;
-                return false;
-            }
-            m_nextCodepoint_ += DATA_BLOCK_LENGTH_;
-        }
-        else {
-            if (!checkBlockDetail(currentValue)) {
-                return false;
-            }
-        }
-        return true;
-    }
-
-    /**
-    * Internal block value calculations
-    * Performs calculations on multiple data blocks for a set of trail
-    * surrogates to find codepoints in m_nextBlock_ that has the same value.
-    * Will call checkBlock() for internal block checks.
-    * Note m_*_ variables at this point is the next codepoint whose value
-    * has not been calculated.
-    * @param currentBlock the initial block containing all currentValue
-    * @param currentValue the value which other codepoints are tested against
-    * @return true if the whole block has the same value as currentValue or if
-    *              the whole block has been calculated, false otherwise.
-    */
-    private final boolean checkTrailBlock(int currentBlock,
-                                          int currentValue)
-    {
-        // enumerate code points for this lead surrogate
-        while (m_nextTrailIndexOffset_ < TRAIL_SURROGATE_INDEX_BLOCK_LENGTH_)
-        {
-            // if we ever reach here, we are at the start of a new block
-            m_nextBlockIndex_ = 0;
-            // copy of most of the body of the BMP loop
-            if (!checkBlock(currentBlock, currentValue)) {
-                return false;
-            }
-            m_nextTrailIndexOffset_ ++;
-            m_nextIndex_ ++;
-        }
-        return true;
-    }
-
-    /**
-    * Checks if we are beginning at the start of a initial block.
-    * If we are then the rest of the codepoints in this initial block
-    * has the same values.
-    * We increment m_nextCodepoint_ and relevant data members if so.
-    * This is used only in for the supplementary codepoints because
-    * the offset to the trail indexes could be 0.
-    * @return true if we are at the start of a initial block.
-    */
-    private final boolean checkNullNextTrailIndex()
-    {
-        if (m_nextIndex_ <= 0) {
-            m_nextCodepoint_ += TRAIL_SURROGATE_COUNT_ - 1;
-            int nextLead  = UTF16.getLeadSurrogate(m_nextCodepoint_);
-            int leadBlock =
-                   m_trie_.m_index_[nextLead >> Trie.INDEX_STAGE_1_SHIFT_] <<
-                                                   Trie.INDEX_STAGE_2_SHIFT_;
-            if (m_trie_.m_dataManipulate_ == null) {
-                throw new NullPointerException(
-                            "The field DataManipulate in this Trie is null");
-            }
-            m_nextIndex_ = m_trie_.m_dataManipulate_.getFoldingOffset(
-                               m_trie_.getValue(leadBlock +
-                                   (nextLead & Trie.INDEX_STAGE_3_MASK_)));
-            m_nextIndex_ --;
-            m_nextBlockIndex_ =  DATA_BLOCK_LENGTH_;
-            return true;
-        }
-        return false;
-    }
-
-    // private data members --------------------------------------------
-
-    /**
-    * Size of the stage 1 BMP indexes
-    */
-    private static final int BMP_INDEX_LENGTH_ =
-                                        0x10000 >> Trie.INDEX_STAGE_1_SHIFT_;
-    /**
-    * Lead surrogate minimum value
-    */
-    private static final int LEAD_SURROGATE_MIN_VALUE_ = 0xD800;
-    /**
-    * Trail surrogate minimum value
-    */
-    private static final int TRAIL_SURROGATE_MIN_VALUE_ = 0xDC00;
-    /**
-    * Number of trail surrogate
-    */
-    private static final int TRAIL_SURROGATE_COUNT_ = 0x400;
-    /**
-    * Number of stage 1 indexes for supplementary calculations that maps to
-    * each lead surrogate character.
-    * See second pass into getRawOffset for the trail surrogate character.
-    * 10 for significant number of bits for trail surrogates, 5 for what we
-    * discard during shifting.
-    */
-    private static final int TRAIL_SURROGATE_INDEX_BLOCK_LENGTH_ =
-                                    1 << (10 - Trie.INDEX_STAGE_1_SHIFT_);
-    /**
-    * Number of data values in a stage 2 (data array) block.
-    */
-    private static final int DATA_BLOCK_LENGTH_ =
-                                              1 << Trie.INDEX_STAGE_1_SHIFT_;
-    /**
-    * Trie instance
-    */
-    private Trie m_trie_;
-    /**
-    * Initial value for trie values
-    */
-    private int m_initialValue_;
-    /**
-    * Next element results and data.
-    */
-    private int m_currentCodepoint_;
-    private int m_nextCodepoint_;
-    private int m_nextValue_;
-    private int m_nextIndex_;
-    private int m_nextBlock_;
-    private int m_nextBlockIndex_;
-    private int m_nextTrailIndexOffset_;
-}
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/UBiDiProps.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/UBiDiProps.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2009, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -24,74 +24,71 @@
  */
 /*
  *******************************************************************************
- * (C) Copyright IBM Corp. and others, 1996-2009 - All Rights Reserved         *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
+ *
+ *   Copyright (C) 2004-2014, International Business Machines
+ *   Corporation and others.  All Rights Reserved.
+ *
  *******************************************************************************
-*   file name:  UBiDiProps.java
-*   encoding:   US-ASCII
-*   tab size:   8 (not used)
-*   indentation:4
-*
-*   created on: 2005jan16
-*   created by: Markus W. Scherer
-*
-*   Low-level Unicode bidi/shaping properties access.
-*   Java port of ubidi_props.h/.c.
-*/
+ *   file name:  UBiDiProps.java
+ *   encoding:   US-ASCII
+ *   tab size:   8 (not used)
+ *   indentation:4
+ *
+ *   created on: 2005jan16
+ *   created by: Markus W. Scherer
+ *
+ *   Low-level Unicode bidi/shaping properties access.
+ *   Java port of ubidi_props.h/.c.
+ */
 
 package sun.text.normalizer;
 
-import java.io.BufferedInputStream;
-import java.io.DataInputStream;
-import java.io.InputStream;
 import java.io.IOException;
+import java.nio.ByteBuffer;
+import java.util.MissingResourceException;
 
 public final class UBiDiProps {
     // constructors etc. --------------------------------------------------- ***
 
     // port of ubidi_openProps()
-    public UBiDiProps() throws IOException{
-        InputStream is=ICUData.getStream(DATA_FILE_NAME);
-        BufferedInputStream b=new BufferedInputStream(is, 4096 /* data buffer size */);
-        readData(b);
-        b.close();
-        is.close();
-
+    private UBiDiProps() throws IOException{
+        ByteBuffer bytes=ICUBinary.getRequiredData(DATA_FILE_NAME);
+        readData(bytes);
     }
 
-    private void readData(InputStream is) throws IOException {
-        DataInputStream inputStream=new DataInputStream(is);
-
+    private void readData(ByteBuffer bytes) throws IOException {
         // read the header
-        ICUBinary.readHeader(inputStream, FMT, new IsAcceptable());
+        ICUBinary.readHeader(bytes, FMT, new IsAcceptable());
 
         // read indexes[]
         int i, count;
-        count=inputStream.readInt();
-        if(count<IX_INDEX_TOP) {
+        count=bytes.getInt();
+        if(count<IX_TOP) {
             throw new IOException("indexes[0] too small in "+DATA_FILE_NAME);
         }
         indexes=new int[count];
 
         indexes[0]=count;
         for(i=1; i<count; ++i) {
-            indexes[i]=inputStream.readInt();
+            indexes[i]=bytes.getInt();
         }
 
         // read the trie
-        trie=new CharTrie(inputStream, null);
+        trie=Trie2_16.createFromSerialized(bytes);
+        int expectedTrieLength=indexes[IX_TRIE_SIZE];
+        int trieLength=trie.getSerializedLength();
+        if(trieLength>expectedTrieLength) {
+            throw new IOException(DATA_FILE_NAME+": not enough bytes for the trie");
+        }
+        // skip padding after trie bytes
+        ICUBinary.skipBytes(bytes, expectedTrieLength-trieLength);
 
         // read mirrors[]
         count=indexes[IX_MIRROR_LENGTH];
         if(count>0) {
             mirrors=new int[count];
             for(i=0; i<count; ++i) {
-                mirrors[i]=inputStream.readInt();
+                mirrors[i]=bytes.getInt();
             }
         }
 
@@ -99,81 +96,172 @@
         count=indexes[IX_JG_LIMIT]-indexes[IX_JG_START];
         jgArray=new byte[count];
         for(i=0; i<count; ++i) {
-            jgArray[i]=inputStream.readByte();
+            jgArray[i]=bytes.get();
+        }
+
+        // read jgArray2[]
+        count=indexes[IX_JG_LIMIT2]-indexes[IX_JG_START2];
+        jgArray2=new byte[count];
+        for(i=0; i<count; ++i) {
+            jgArray2[i]=bytes.get();
         }
     }
 
     // implement ICUBinary.Authenticate
-    private final class IsAcceptable implements ICUBinary.Authenticate {
+    private final static class IsAcceptable implements ICUBinary.Authenticate {
         public boolean isDataVersionAcceptable(byte version[]) {
-            return version[0]==1 &&
-                   version[2]==Trie.INDEX_STAGE_1_SHIFT_ && version[3]==Trie.INDEX_STAGE_2_SHIFT_;
+            return version[0]==2;
         }
     }
 
-    // UBiDiProps singleton
-    private static UBiDiProps gBdp=null;
+    // property access functions ------------------------------------------- ***
+
+    public final int getClass(int c) {
+        return getClassFromProps(trie.get(c));
+    }
+
+    private final int getMirror(int c, int props) {
+        int delta=getMirrorDeltaFromProps(props);
+        if(delta!=ESC_MIRROR_DELTA) {
+            return c+delta;
+        } else {
+            /* look for mirror code point in the mirrors[] table */
+            int m;
+            int i, length;
+            int c2;
 
-    // port of ubidi_getSingleton()
-    public static final synchronized UBiDiProps getSingleton() throws IOException {
-        if(gBdp==null) {
-            gBdp=new UBiDiProps();
+            length=indexes[IX_MIRROR_LENGTH];
+
+            /* linear search */
+            for(i=0; i<length; ++i) {
+                m=mirrors[i];
+                c2=getMirrorCodePoint(m);
+                if(c==c2) {
+                    /* found c, return its mirror code point using the index in m */
+                    return getMirrorCodePoint(mirrors[getMirrorIndex(m)]);
+                } else if(c<c2) {
+                    break;
+                }
+            }
+
+            /* c not found, return it itself */
+            return c;
         }
-        return gBdp;
     }
 
-    // UBiDiProps dummy singleton
-    private static UBiDiProps gBdpDummy=null;
+    public final int getMirror(int c) {
+        int props=trie.get(c);
+        return getMirror(c, props);
+    }
 
-    private UBiDiProps(boolean makeDummy) { // ignore makeDummy, only creates a unique signature
-        indexes=new int[IX_TOP];
-        indexes[0]=IX_TOP;
-        trie=new CharTrie(0, 0, null); // dummy trie, always returns 0
+    public final int getJoiningType(int c) {
+        return (trie.get(c)&JT_MASK)>>JT_SHIFT;
     }
 
-    /**
-     * Get a singleton dummy object, one that works with no real data.
-     * This can be used when the real data is not available.
-     * Using the dummy can reduce checks for available data after an initial failure.
-     * Port of ucase_getDummy().
-     */
-    public static final synchronized UBiDiProps getDummy() {
-        if(gBdpDummy==null) {
-            gBdpDummy=new UBiDiProps(true);
+    public final int getJoiningGroup(int c) {
+        int start, limit;
+
+        start=indexes[IX_JG_START];
+        limit=indexes[IX_JG_LIMIT];
+        if(start<=c && c<limit) {
+            return (int)jgArray[c-start]&0xff;
         }
-        return gBdpDummy;
+        start=indexes[IX_JG_START2];
+        limit=indexes[IX_JG_LIMIT2];
+        if(start<=c && c<limit) {
+            return (int)jgArray2[c-start]&0xff;
+        }
+        return UCharacter.JoiningGroup.NO_JOINING_GROUP;
     }
 
-    public final int getClass(int c) {
-        return getClassFromProps(trie.getCodePointValue(c));
+    public final int getPairedBracketType(int c) {
+        return (trie.get(c)&BPT_MASK)>>BPT_SHIFT;
+    }
+
+    public final int getPairedBracket(int c) {
+        int props=trie.get(c);
+        if((props&BPT_MASK)==0) {
+            return c;
+        } else {
+            return getMirror(c, props);
+        }
     }
 
     // data members -------------------------------------------------------- ***
     private int indexes[];
     private int mirrors[];
     private byte jgArray[];
+    private byte jgArray2[];
 
-    private CharTrie trie;
+    private Trie2_16 trie;
 
     // data format constants ----------------------------------------------- ***
     private static final String DATA_FILE_NAME = "/sun/text/resources/ubidi.icu";
 
     /* format "BiDi" */
-    private static final byte FMT[]={ 0x42, 0x69, 0x44, 0x69 };
+    private static final int FMT=0x42694469;
 
     /* indexes into indexes[] */
-    private static final int IX_INDEX_TOP=0;
+    private static final int IX_TRIE_SIZE=2;
     private static final int IX_MIRROR_LENGTH=3;
 
     private static final int IX_JG_START=4;
     private static final int IX_JG_LIMIT=5;
+    private static final int IX_JG_START2=6;  /* new in format version 2.2, ICU 54 */
+    private static final int IX_JG_LIMIT2=7;
 
     private static final int IX_TOP=16;
 
+    // definitions for 16-bit bidi/shaping properties word ----------------- ***
+
+                          /* CLASS_SHIFT=0, */     /* bidi class: 5 bits (4..0) */
+    private static final int JT_SHIFT=5;           /* joining type: 3 bits (7..5) */
+
+    private static final int BPT_SHIFT=8;          /* Bidi_Paired_Bracket_Type(bpt): 2 bits (9..8) */
+
+    private static final int MIRROR_DELTA_SHIFT=13;        /* bidi mirroring delta: 3 bits (15..13) */
+
     private static final int CLASS_MASK=    0x0000001f;
+    private static final int JT_MASK=       0x000000e0;
+    private static final int BPT_MASK=      0x00000300;
 
     private static final int getClassFromProps(int props) {
         return props&CLASS_MASK;
     }
+    private static final boolean getFlagFromProps(int props, int shift) {
+        return ((props>>shift)&1)!=0;
+    }
+    private static final int getMirrorDeltaFromProps(int props) {
+        return (short)props>>MIRROR_DELTA_SHIFT;
+    }
 
+    private static final int ESC_MIRROR_DELTA=-4;
+
+    // definitions for 32-bit mirror table entry --------------------------- ***
+
+    /* the source Unicode code point takes 21 bits (20..0) */
+    private static final int MIRROR_INDEX_SHIFT=21;
+
+    private static final int getMirrorCodePoint(int m) {
+        return m&0x1fffff;
+    }
+    private static final int getMirrorIndex(int m) {
+        return m>>>MIRROR_INDEX_SHIFT;
+    }
+
+
+    /*
+     * public singleton instance
+     */
+    public static final UBiDiProps INSTANCE;
+
+    // This static initializer block must be placed after
+    // other static member initialization
+    static {
+        try {
+            INSTANCE = new UBiDiProps();
+        } catch (IOException e) {
+            throw new MissingResourceException(e.getMessage(),DATA_FILE_NAME,"");
+        }
+    }
 }
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/UCharacter.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/UCharacter.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2009, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2009, 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
@@ -22,40 +22,30 @@
  * or visit www.oracle.com if you need additional information or have any
  * questions.
  */
-/*
- *******************************************************************************
- * (C) Copyright IBM Corp. and others, 1996-2009 - All Rights Reserved         *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
- *******************************************************************************
- */
+
+/**
+*******************************************************************************
+* Copyright (C) 1996-2014, International Business Machines Corporation and
+* others. All Rights Reserved.
+*******************************************************************************
+*/
 
 package sun.text.normalizer;
 
-import java.io.IOException;
-import java.util.MissingResourceException;
-
 /**
- * <p>
- * The UCharacter class provides extensions to the
- * <a href="http://docs.oracle.com/javase/1.5.0/docs/api/java/lang/Character.html">
+ * <p>The UCharacter class provides extensions to the
+ * <a href="http://java.sun.com/j2se/1.5/docs/api/java/lang/Character.html">
  * java.lang.Character</a> class. These extensions provide support for
  * more Unicode properties and together with the <a href=../text/UTF16.html>UTF16</a>
  * class, provide support for supplementary characters (those with code
  * points above U+FFFF).
  * Each ICU release supports the latest version of Unicode available at that time.
- * </p>
- * <p>
- * Code points are represented in these API using ints. While it would be
+ *
+ * <p>Code points are represented in these API using ints. While it would be
  * more convenient in Java to have a separate primitive datatype for them,
  * ints suffice in the meantime.
- * </p>
- * <p>
- * To use this class please add the jar file name icu4j.jar to the
+ *
+ * <p>To use this class please add the jar file name icu4j.jar to the
  * class path, since it contains data files which supply the information used
  * by this file.<br>
  * E.g. In Windows <br>
@@ -64,9 +54,8 @@
  * unames.icu from the icu4j source subdirectory
  * <i>$ICU4J_SRC/src/com.ibm.icu.impl.data</i> to your class directory
  * <i>$ICU4J_CLASS/com.ibm.icu.impl.data</i>.
- * </p>
- * <p>
- * Aside from the additions for UTF-16 support, and the updated Unicode
+ *
+ * <p>Aside from the additions for UTF-16 support, and the updated Unicode
  * properties, the main differences between UCharacter and Character are:
  * <ul>
  * <li> UCharacter is not designed to be a char wrapper and does not have
@@ -87,8 +76,9 @@
  *      as having numeric values.  This is a semantic change from ICU4J 1.3.1.
  * </ul>
  * <p>
- * Further detail differences can be determined from the program
- *        <a href="http://source.icu-project.org/repos/icu/icu4j/trunk/src/com/ibm/icu/dev/test/lang/UCharacterCompare.java">
+ * Further detail on differences can be determined using the program
+ *        <a href=
+ * "http://source.icu-project.org/repos/icu/icu4j/trunk/src/com/ibm/icu/dev/test/lang/UCharacterCompare.java">
  *        com.ibm.icu.dev.test.lang.UCharacterCompare</a>
  * </p>
  * <p>
@@ -103,8 +93,11 @@
  * </p>
  * <p>
  * For more information see
- * "About the Unicode Character Database" (http://www.unicode.org/ucd/)
- * and the ICU User Guide chapter on Properties (http://www.icu-project.org/userguide/properties.html).
+ * <a href="http://www.unicode/org/ucd/">"About the Unicode Character Database"</a>
+ * (http://www.unicode.org/ucd/)
+ * and the <a href="http://www.icu-project.org/userguide/properties.html">ICU
+ * User Guide chapter on Properties</a>
+ * (http://www.icu-project.org/userguide/properties.html).
  * </p>
  * <p>
  * There are also functions that provide easy migration from C/POSIX functions
@@ -128,12 +121,15 @@
  * Annex C: Compatibility Properties of UTS #18 Unicode Regular Expressions
  * (http://www.unicode.org/reports/tr18/#Compatibility_Properties).
  * </p>
+ * <p>
+ * API access for C/POSIX character classes is as follows:
  * <pre>{@code
- * API access for C/POSIX character classes is as follows:
  * - alpha:     isUAlphabetic(c) or hasBinaryProperty(c, UProperty.ALPHABETIC)
  * - lower:     isULowercase(c) or hasBinaryProperty(c, UProperty.LOWERCASE)
  * - upper:     isUUppercase(c) or hasBinaryProperty(c, UProperty.UPPERCASE)
- * - punct:     ((1<<getType(c)) & ((1<<DASH_PUNCTUATION)|(1<<START_PUNCTUATION)|(1<<END_PUNCTUATION)|(1<<CONNECTOR_PUNCTUATION)|(1<<OTHER_PUNCTUATION)|(1<<INITIAL_PUNCTUATION)|(1<<FINAL_PUNCTUATION)))!=0
+ * - punct:     ((1<<getType(c)) & ((1<<DASH_PUNCTUATION)|(1<<START_PUNCTUATION)|
+ *               (1<<END_PUNCTUATION)|(1<<CONNECTOR_PUNCTUATION)|(1<<OTHER_PUNCTUATION)|
+ *               (1<<INITIAL_PUNCTUATION)|(1<<FINAL_PUNCTUATION)))!=0
  * - digit:     isDigit(c) or getType(c)==DECIMAL_DIGIT_NUMBER
  * - xdigit:    hasBinaryProperty(c, UProperty.POSIX_XDIGIT)
  * - alnum:     hasBinaryProperty(c, UProperty.POSIX_ALNUM)
@@ -143,21 +139,22 @@
  * - graph:     hasBinaryProperty(c, UProperty.POSIX_GRAPH)
  * - print:     hasBinaryProperty(c, UProperty.POSIX_PRINT)
  * }</pre>
+ * </p>
  * <p>
  * The C/POSIX character classes are also available in UnicodeSet patterns,
  * using patterns like [:graph:] or \p{graph}.
  * </p>
- * <p>
- * Note: There are several ICU (and Java) whitespace functions.
- * Comparison:
- * - isUWhiteSpace=UCHAR_WHITE_SPACE: Unicode White_Space property;
+ *
+ * There are several ICU (and Java) whitespace functions.
+ * Comparison:<ul>
+ * <li> isUWhiteSpace=UCHAR_WHITE_SPACE: Unicode White_Space property;
  *       most of general categories "Z" (separators) + most whitespace ISO controls
  *       (including no-break spaces, but excluding IS1..IS4 and ZWSP)
- * - isWhitespace: Java isWhitespace; Z + whitespace ISO controls but excluding no-break spaces
- * - isSpaceChar: just Z (including no-break spaces)
+ * <li> isWhitespace: Java isWhitespace; Z + whitespace ISO controls but excluding no-break spaces
+ * <li> isSpaceChar: just Z (including no-break spaces)</ul>
  * </p>
  * <p>
- * This class is not subclassable
+ * This class is not subclassable.
  * </p>
  * @author Syn Wee Quek
  * @stable ICU 2.1
@@ -168,6 +165,19 @@
 {
 
     /**
+     * Joining Group constants.
+     * @see UProperty#JOINING_GROUP
+     * @stable ICU 2.4
+     */
+    public static interface JoiningGroup
+    {
+        /**
+         * @stable ICU 2.4
+         */
+        public static final int NO_JOINING_GROUP = 0;
+    }
+
+    /**
      * Numeric Type constants.
      * @see UProperty#NUMERIC_TYPE
      * @stable ICU 2.4
@@ -177,7 +187,61 @@
         /**
          * @stable ICU 2.4
          */
+        public static final int NONE = 0;
+        /**
+         * @stable ICU 2.4
+         */
         public static final int DECIMAL = 1;
+        /**
+         * @stable ICU 2.4
+         */
+        public static final int DIGIT = 2;
+        /**
+         * @stable ICU 2.4
+         */
+        public static final int NUMERIC = 3;
+        /**
+         * @stable ICU 2.4
+         */
+        public static final int COUNT = 4;
+    }
+
+    /**
+     * Hangul Syllable Type constants.
+     *
+     * @see UProperty#HANGUL_SYLLABLE_TYPE
+     * @stable ICU 2.6
+     */
+    public static interface HangulSyllableType
+    {
+        /**
+         * @stable ICU 2.6
+         */
+        public static final int NOT_APPLICABLE      = 0;   /*[NA]*/ /*See note !!*/
+        /**
+         * @stable ICU 2.6
+         */
+        public static final int LEADING_JAMO        = 1;   /*[L]*/
+        /**
+         * @stable ICU 2.6
+         */
+        public static final int VOWEL_JAMO          = 2;   /*[V]*/
+        /**
+         * @stable ICU 2.6
+         */
+        public static final int TRAILING_JAMO       = 3;   /*[T]*/
+        /**
+         * @stable ICU 2.6
+         */
+        public static final int LV_SYLLABLE         = 4;   /*[LV]*/
+        /**
+         * @stable ICU 2.6
+         */
+        public static final int LVT_SYLLABLE        = 5;   /*[LVT]*/
+        /**
+         * @stable ICU 2.6
+         */
+        public static final int COUNT               = 6;
     }
 
     // public data members -----------------------------------------------
@@ -192,22 +256,15 @@
      * The highest Unicode code point value (scalar value) according to the
      * Unicode Standard.
      * This is a 21-bit value (21 bits, rounded up).<br>
-     * Up-to-date Unicode implementation of java.lang.Character.MIN_VALUE
+     * Up-to-date Unicode implementation of java.lang.Character.MAX_VALUE
      * @stable ICU 2.1
      */
     public static final int MAX_VALUE = UTF16.CODEPOINT_MAX_VALUE;
 
-    /**
-     * The minimum value for Supplementary code points
-     * @stable ICU 2.1
-     */
-    public static final int SUPPLEMENTARY_MIN_VALUE =
-        UTF16.SUPPLEMENTARY_MIN_VALUE;
-
     // public methods ----------------------------------------------------
 
     /**
-     * Retrieves the numeric value of a decimal digit code point.
+     * Returns the numeric value of a decimal digit code point.
      * <br>This method observes the semantics of
      * <code>java.lang.Character.digit()</code>.  Note that this
      * will return positive values for code points for which isDigit
@@ -231,15 +288,54 @@
      */
     public static int digit(int ch, int radix)
     {
-        // when ch is out of bounds getProperty == 0
-        int props = getProperty(ch);
-        int value;
-        if (getNumericType(props) == NumericType.DECIMAL) {
-            value = UCharacterProperty.getUnsignedValue(props);
+        if (2 <= radix && radix <= 36) {
+            int value = digit(ch);
+            if (value < 0) {
+                // ch is not a decimal digit, try latin letters
+                value = UCharacterProperty.getEuropeanDigit(ch);
+            }
+            return (value < radix) ? value : -1;
         } else {
-            value = getEuropeanDigit(ch);
+            return -1;  // invalid radix
         }
-        return (0 <= value && value < radix) ? value : -1;
+    }
+
+    /**
+     * Returns the numeric value of a decimal digit code point.
+     * <br>This is a convenience overload of <code>digit(int, int)</code>
+     * that provides a decimal radix.
+     * <br><em>Semantic Change:</em> In release 1.3.1 and prior, this
+     * treated numeric letters and other numbers as digits.  This has
+     * been changed to conform to the java semantics.
+     * @param ch the code point to query
+     * @return the numeric value represented by the code point,
+     * or -1 if the code point is not a decimal digit or if its
+     * value is too large for a decimal radix
+     * @stable ICU 2.1
+     */
+    public static int digit(int ch)
+    {
+        return UCharacterProperty.INSTANCE.digit(ch);
+    }
+
+    /**
+     * Returns a value indicating a code point's Unicode category.
+     * Up-to-date Unicode implementation of java.lang.Character.getType()
+     * except for the above mentioned code points that had their category
+     * changed.<br>
+     * Return results are constants from the interface
+     * <a href=UCharacterCategory.html>UCharacterCategory</a><br>
+     * <em>NOTE:</em> the UCharacterCategory values are <em>not</em> compatible with
+     * those returned by java.lang.Character.getType.  UCharacterCategory values
+     * match the ones used in ICU4C, while java.lang.Character type
+     * values, though similar, skip the value 17.</p>
+     * @param ch code point whose type is to be determined
+     * @return category which is a value of UCharacterCategory
+     * @stable ICU 2.1
+     */
+    public static int getType(int ch)
+    {
+        return UCharacterProperty.INSTANCE.getType(ch);
     }
 
     /**
@@ -254,7 +350,67 @@
      */
     public static int getDirection(int ch)
     {
-        return gBdp.getClass(ch);
+        return UBiDiProps.INSTANCE.getClass(ch);
+    }
+
+    /**
+     * Maps the specified code point to a "mirror-image" code point.
+     * For code points with the "mirrored" property, implementations sometimes
+     * need a "poor man's" mapping to another code point such that the default
+     * glyph may serve as the mirror-image of the default glyph of the
+     * specified code point.<br>
+     * This is useful for text conversion to and from codepages with visual
+     * order, and for displays without glyph selection capabilities.
+     * @param ch code point whose mirror is to be retrieved
+     * @return another code point that may serve as a mirror-image substitute,
+     *         or ch itself if there is no such mapping or ch does not have the
+     *         "mirrored" property
+     * @stable ICU 2.1
+     */
+    public static int getMirror(int ch)
+    {
+        return UBiDiProps.INSTANCE.getMirror(ch);
+    }
+
+    /**
+     * Maps the specified character to its paired bracket character.
+     * For Bidi_Paired_Bracket_Type!=None, this is the same as getMirror(int).
+     * Otherwise c itself is returned.
+     * See http://www.unicode.org/reports/tr9/
+     *
+     * @param c the code point to be mapped
+     * @return the paired bracket code point,
+     *         or c itself if there is no such mapping
+     *         (Bidi_Paired_Bracket_Type=None)
+     *
+     * @see UProperty#BIDI_PAIRED_BRACKET
+     * @see UProperty#BIDI_PAIRED_BRACKET_TYPE
+     * @see #getMirror(int)
+     * @stable ICU 52
+     */
+    public static int getBidiPairedBracket(int c) {
+        return UBiDiProps.INSTANCE.getPairedBracket(c);
+    }
+
+    /**
+     * Returns the combining class of the argument codepoint
+     * @param ch code point whose combining is to be retrieved
+     * @return the combining class of the codepoint
+     * @stable ICU 2.1
+     */
+    public static int getCombiningClass(int ch)
+    {
+        return Normalizer2.getNFDInstance().getCombiningClass(ch);
+    }
+
+    /**
+     * Returns the version of Unicode data used.
+     * @return the unicode version number used
+     * @stable ICU 2.1
+     */
+    public static VersionInfo getUnicodeVersion()
+    {
+        return UCharacterProperty.INSTANCE.m_unicodeVersion_;
     }
 
     /**
@@ -275,7 +431,7 @@
     }
 
     /**
-     * <p>Get the "age" of the code point.</p>
+     * Returns the "age" of the code point.</p>
      * <p>The "age" is the Unicode version when the code point was first
      * designated (as a non-character or for Private Use) or assigned a
      * character.
@@ -289,143 +445,95 @@
     public static VersionInfo getAge(int ch)
     {
         if (ch < MIN_VALUE || ch > MAX_VALUE) {
-        throw new IllegalArgumentException("Codepoint out of bounds");
+            throw new IllegalArgumentException("Codepoint out of bounds");
         }
-        return PROPERTY_.getAge(ch);
-    }
-
-    // private variables -------------------------------------------------
-
-    /**
-     * Database storing the sets of character property
-     */
-    private static final UCharacterProperty PROPERTY_;
-    /**
-     * For optimization
-     */
-    private static final char[] PROPERTY_TRIE_INDEX_;
-    private static final char[] PROPERTY_TRIE_DATA_;
-    private static final int PROPERTY_INITIAL_VALUE_;
-
-    private static final UBiDiProps gBdp;
-
-    // block to initialise character property database
-    static
-    {
-        try
-        {
-            PROPERTY_ = UCharacterProperty.getInstance();
-            PROPERTY_TRIE_INDEX_ = PROPERTY_.m_trieIndex_;
-            PROPERTY_TRIE_DATA_ = PROPERTY_.m_trieData_;
-            PROPERTY_INITIAL_VALUE_ = PROPERTY_.m_trieInitialValue_;
-        }
-        catch (Exception e)
-        {
-            throw new MissingResourceException(e.getMessage(),"","");
-        }
-
-        UBiDiProps bdp;
-        try {
-            bdp=UBiDiProps.getSingleton();
-        } catch(IOException e) {
-            bdp=UBiDiProps.getDummy();
-        }
-        gBdp=bdp;
+        return UCharacterProperty.INSTANCE.getAge(ch);
     }
 
     /**
-     * Shift to get numeric type
-     */
-    private static final int NUMERIC_TYPE_SHIFT_ = 5;
-    /**
-     * Mask to get numeric type
+     * Returns the property value for an Unicode property type of a code point.
+     * Also returns binary and mask property values.</p>
+     * <p>Unicode, especially in version 3.2, defines many more properties than
+     * the original set in UnicodeData.txt.</p>
+     * <p>The properties APIs are intended to reflect Unicode properties as
+     * defined in the Unicode Character Database (UCD) and Unicode Technical
+     * Reports (UTR). For details about the properties see
+     * http://www.unicode.org/.</p>
+     * <p>For names of Unicode properties see the UCD file PropertyAliases.txt.
+     * </p>
+     * <pre>
+     * Sample usage:
+     * int ea = UCharacter.getIntPropertyValue(c, UProperty.EAST_ASIAN_WIDTH);
+     * int ideo = UCharacter.getIntPropertyValue(c, UProperty.IDEOGRAPHIC);
+     * boolean b = (ideo == 1) ? true : false;
+     * </pre>
+     * @param ch code point to test.
+     * @param type UProperty selector constant, identifies which binary
+     *        property to check. Must be
+     *        UProperty.BINARY_START &lt;= type &lt; UProperty.BINARY_LIMIT or
+     *        UProperty.INT_START &lt;= type &lt; UProperty.INT_LIMIT or
+     *        UProperty.MASK_START &lt;= type &lt; UProperty.MASK_LIMIT.
+     * @return numeric value that is directly the property value or,
+     *         for enumerated properties, corresponds to the numeric value of
+     *         the enumerated constant of the respective property value
+     *         enumeration type (cast to enum type if necessary).
+     *         Returns 0 or 1 (for false / true) for binary Unicode properties.
+     *         Returns a bit-mask for mask properties.
+     *         Returns 0 if 'type' is out of bounds or if the Unicode version
+     *         does not have data for the property at all, or not for this code
+     *         point.
+     * @see UProperty
+     * @see #hasBinaryProperty
+     * @see #getIntPropertyMinValue
+     * @see #getIntPropertyMaxValue
+     * @see #getUnicodeVersion
+     * @stable ICU 2.4
      */
-    private static final int NUMERIC_TYPE_MASK_ = 0x7 << NUMERIC_TYPE_SHIFT_;
-
-    // private methods ---------------------------------------------------
-
-    /**
-     * Getting the digit values of characters like 'A' - 'Z', normal,
-     * half-width and full-width. This method assumes that the other digit
-     * characters are checked by the calling method.
-     * @param ch character to test
-     * @return -1 if ch is not a character of the form 'A' - 'Z', otherwise
-     *         its corresponding digit will be returned.
-     */
-    private static int getEuropeanDigit(int ch) {
-        if ((ch > 0x7a && ch < 0xff21)
-            || ch < 0x41 || (ch > 0x5a && ch < 0x61)
-            || ch > 0xff5a || (ch > 0xff3a && ch < 0xff41)) {
-            return -1;
-        }
-        if (ch <= 0x7a) {
-            // ch >= 0x41 or ch < 0x61
-            return ch + 10 - ((ch <= 0x5a) ? 0x41 : 0x61);
-        }
-        // ch >= 0xff21
-        if (ch <= 0xff3a) {
-            return ch + 10 - 0xff21;
-        }
-        // ch >= 0xff41 && ch <= 0xff5a
-        return ch + 10 - 0xff41;
+     // for BiDiBase.java
+    public static int getIntPropertyValue(int ch, int type) {
+        return UCharacterProperty.INSTANCE.getIntPropertyValue(ch, type);
     }
 
-    /**
-     * Gets the numeric type of the property argument
-     * @param props 32 bit property
-     * @return the numeric type
-     */
-    private static int getNumericType(int props)
-    {
-        return (props & NUMERIC_TYPE_MASK_) >> NUMERIC_TYPE_SHIFT_;
-    }
+    // private constructor -----------------------------------------------
 
     /**
-     * Gets the property value at the index.
-     * This is optimized.
-     * Note this is alittle different from CharTrie the index m_trieData_
-     * is never negative.
-     * This is a duplicate of UCharacterProperty.getProperty. For optimization
-     * purposes, this method calls the trie data directly instead of through
-     * UCharacterProperty.getProperty.
-     * @param ch code point whose property value is to be retrieved
-     * @return property value of code point
-     * @stable ICU 2.6
+     * Private constructor to prevent instantiation
      */
-    private static final int getProperty(int ch)
-    {
-        if (ch < UTF16.LEAD_SURROGATE_MIN_VALUE
-            || (ch > UTF16.LEAD_SURROGATE_MAX_VALUE
-                && ch < UTF16.SUPPLEMENTARY_MIN_VALUE)) {
-            // BMP codepoint 0000..D7FF or DC00..FFFF
-            try { // using try for ch < 0 is faster than using an if statement
-                return PROPERTY_TRIE_DATA_[
-                              (PROPERTY_TRIE_INDEX_[ch >> 5] << 2)
-                              + (ch & 0x1f)];
-            } catch (ArrayIndexOutOfBoundsException e) {
-                return PROPERTY_INITIAL_VALUE_;
-            }
-        }
-        if (ch <= UTF16.LEAD_SURROGATE_MAX_VALUE) {
-            // lead surrogate D800..DBFF
-            return PROPERTY_TRIE_DATA_[
-                              (PROPERTY_TRIE_INDEX_[(0x2800 >> 5) + (ch >> 5)] << 2)
-                              + (ch & 0x1f)];
-        }
-        // for optimization
-        if (ch <= UTF16.CODEPOINT_MAX_VALUE) {
-            // supplementary code point 10000..10FFFF
-            // look at the construction of supplementary characters
-            // trail forms the ends of it.
-            return PROPERTY_.m_trie_.getSurrogateValue(
-                                      UTF16.getLeadSurrogate(ch),
-                                      (char)(ch & 0x3ff));
-        }
-        // return m_dataOffset_ if there is an error, in this case we return
-        // the default value: m_initialValue_
-        // we cannot assume that m_initialValue_ is at offset 0
-        // this is for optimization.
-        return PROPERTY_INITIAL_VALUE_;
-    }
+    private UCharacter() { }
+
+      /*
+       * Copied from UCharacterEnums.java
+       */
 
+        /**
+         * Character type Mn
+         * @stable ICU 2.1
+         */
+        public static final byte NON_SPACING_MARK        = 6;
+        /**
+         * Character type Me
+         * @stable ICU 2.1
+         */
+        public static final byte ENCLOSING_MARK          = 7;
+        /**
+         * Character type Mc
+         * @stable ICU 2.1
+         */
+        public static final byte COMBINING_SPACING_MARK  = 8;
+        /**
+         * Character type count
+         * @stable ICU 2.1
+         */
+        public static final byte CHAR_CATEGORY_COUNT     = 30;
+
+        /**
+         * Directional type R
+         * @stable ICU 2.1
+         */
+        public static final int RIGHT_TO_LEFT              = 1;
+        /**
+         * Directional type AL
+         * @stable ICU 2.1
+         */
+        public static final int RIGHT_TO_LEFT_ARABIC       = 13;
 }
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/UCharacterIterator.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/UCharacterIterator.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2006, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 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
@@ -25,13 +25,8 @@
 
 /*
  *******************************************************************************
- * (C) Copyright IBM Corp. 1996-2005 - All Rights Reserved                     *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
+ * Copyright (C) 1996-2014, International Business Machines Corporation and    *
+ * others. All Rights Reserved.                                                *
  *******************************************************************************
  */
 
@@ -84,7 +79,6 @@
         return new ReplaceableUCharacterIterator(source);
     }
 
-    //// for StringPrep
     /**
      * Returns a <code>UCharacterIterator</code> object given a
      * source StringBuffer.
@@ -97,7 +91,7 @@
         return new ReplaceableUCharacterIterator(source);
     }
 
-    /**
+   /**
      * Returns a <code>UCharacterIterator</code> object given a
      * CharacterIterator.
      * @param source a valid CharacterIterator object.
@@ -112,21 +106,12 @@
     // public methods ----------------------------------------------------------
 
     /**
-     * Returns the code unit at the current index.  If index is out
-     * of range, returns DONE.  Index is not changed.
-     * @return current code unit
-     * @stable ICU 2.4
-     */
-    public abstract int current();
-
-    /**
      * Returns the length of the text
      * @return length of the text
      * @stable ICU 2.4
      */
     public abstract int getLength();
 
-
     /**
      * Gets the current index in text.
      * @return current index in text.
@@ -134,7 +119,6 @@
      */
     public abstract int getIndex();
 
-
     /**
      * Returns the UTF16 code unit at index, and increments to the next
      * code unit (post-increment semantics).  If index is out of
@@ -183,6 +167,33 @@
      */
     public abstract int previous();
 
+
+    /**
+     * Retreat to the start of the previous code point in the text,
+     * and return it (pre-decrement semantics).  If the index is not
+     * preceeded by a valid surrogate pair, the behavior is the same
+     * as <code>previous()</code>.  Otherwise the iterator is
+     * decremented to the start of the surrogate pair, and the code
+     * point represented by the pair is returned.
+     * @return the previous code point in the text, or DONE if the new
+     *         index is before the start of the text.
+     * @stable ICU 2.4
+     */
+    public int previousCodePoint(){
+        int ch1 = previous();
+        if(UTF16.isTrailSurrogate((char)ch1)){
+            int ch2 = previous();
+            if(UTF16.isLeadSurrogate((char)ch2)){
+                return UCharacterProperty.getRawSupplementary((char)ch2,
+                                                              (char)ch1);
+            }else if (ch2 != DONE) {
+                //unmatched trail surrogate so back out
+                next();
+            }
+        }
+        return ch1;
+    }
+
     /**
      * Sets the index to the specified index in the text.
      * @param index the index within the text.
@@ -192,7 +203,14 @@
      */
     public abstract void setIndex(int index);
 
-    //// for StringPrep
+    /**
+     * Sets the current index to the start.
+     * @stable ICU 2.4
+     */
+    public void setToStart() {
+        setIndex(0);
+    }
+
     /**
      * Fills the buffer with the underlying text storage of the iterator
      * If the buffer capacity is not enough a exception is thrown. The capacity
@@ -222,20 +240,19 @@
      *         units.
      * @param offset the position within the array to start putting the data.
      * @return the number of code units added to fillIn, as a convenience
-     * @exception IndexOutOfBounds exception if there is not enough
-     *            room after offset in the array, or if offset {@literal <} 0.
+     * @exception IndexOutOfBoundsException exception if there is not enough
+     *            room after offset in the array, or if offset < 0.
      * @stable ICU 2.4
      */
     public abstract int getText(char[] fillIn, int offset);
 
-    //// for StringPrep
     /**
      * Convenience override for <code>getText(char[], int)</code> that provides
      * an offset of 0.
      * @param fillIn an array of chars to fill with the underlying UTF-16 code
      *         units.
      * @return the number of code units added to fillIn, as a convenience
-     * @exception IndexOutOfBounds exception if there is not enough
+     * @exception IndexOutOfBoundsException exception if there is not enough
      *            room in the array.
      * @stable ICU 2.4
      */
@@ -243,7 +260,6 @@
         return getText(fillIn, 0);
     }
 
-    //// for StringPrep
     /**
      * Convenience method for returning the underlying text storage as a string
      * @return the underlying text storage in the iterator as a string
@@ -256,25 +272,32 @@
     }
 
     /**
-     * Moves the current position by the number of code units
-     * specified, either forward or backward depending on the sign
-     * of delta (positive or negative respectively).  If the resulting
-     * index would be less than zero, the index is set to zero, and if
-     * the resulting index would be greater than limit, the index is
-     * set to limit.
-     *
-     * @param delta the number of code units to move the current
-     *              index.
-     * @return the new index.
-     * @exception IndexOutOfBoundsException is thrown if an invalid index is
+     * Moves the current position by the number of code points
+     * specified, either forward or backward depending on the sign of
+     * delta (positive or negative respectively). If the current index
+     * is at a trail surrogate then the first adjustment is by code
+     * unit, and the remaining adjustments are by code points.  If the
+     * resulting index would be less than zero, the index is set to
+     * zero, and if the resulting index would be greater than limit,
+     * the index is set to limit.
+     * @param delta the number of code units to move the current index.
+     * @return the new index
+     * @exception IndexOutOfBoundsException is thrown if an invalid delta is
      *            supplied
      * @stable ICU 2.4
      *
      */
-    public int moveIndex(int delta) {
-        int x = Math.max(0, Math.min(getIndex() + delta, getLength()));
-        setIndex(x);
-        return x;
+    public int moveCodePointIndex(int delta){
+        if(delta>0){
+            while(delta>0 && nextCodePoint() != DONE){delta--;}
+        }else{
+            while(delta<0 && previousCodePoint() != DONE){delta++;}
+        }
+        if(delta!=0){
+            throw new IndexOutOfBoundsException();
+        }
+
+        return getIndex();
     }
 
     /**
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/UCharacterProperty.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/UCharacterProperty.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2009, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -24,23 +24,21 @@
  */
 /*
  *******************************************************************************
- * (C) Copyright IBM Corp. and others, 1996-2009 - All Rights Reserved         *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
+ * Copyright (C) 1996-2014, International Business Machines Corporation and
+ * others. All Rights Reserved.
  *******************************************************************************
  */
 
 package sun.text.normalizer;
 
-import java.io.BufferedInputStream;
-import java.io.InputStream;
 import java.io.IOException;
+import java.nio.ByteBuffer;
+import java.util.Iterator;
 import java.util.MissingResourceException;
 
+import sun.text.normalizer.UCharacter.HangulSyllableType;
+import sun.text.normalizer.UCharacter.NumericType;
+
 /**
 * <p>Internal class used for Unicode character property database.</p>
 * <p>This classes store binary data read from uprops.icu.
@@ -56,134 +54,72 @@
 * @since release 2.1, february 1st 2002
 */
 
-public final class UCharacterProperty
+final class UCharacterProperty
 {
     // public data members -----------------------------------------------
 
+    /*
+     * public singleton instance
+     */
+    public static final UCharacterProperty INSTANCE;
+
     /**
     * Trie data
     */
-    public CharTrie m_trie_;
-    /**
-     * Optimization
-     * CharTrie index array
-     */
-    public char[] m_trieIndex_;
-    /**
-     * Optimization
-     * CharTrie data array
-     */
-    public char[] m_trieData_;
-    /**
-     * Optimization
-     * CharTrie data offset
-     */
-    public int m_trieInitialValue_;
+    public Trie2_16 m_trie_;
+
     /**
     * Unicode version
     */
     public VersionInfo m_unicodeVersion_;
 
+    /**
+    * Character type mask
+    */
+    public static final int TYPE_MASK = 0x1F;
+
     // uprops.h enum UPropertySource --------------------------------------- ***
 
+    /** From uchar.c/uprops.icu main trie */
+    public static final int SRC_CHAR=1;
     /** From uchar.c/uprops.icu properties vectors trie */
     public static final int SRC_PROPSVEC=2;
-    /** One more than the highest UPropertySource (SRC_) constant. */
-    public static final int SRC_COUNT=9;
+    /** From ubidi_props.c/ubidi.icu */
+    public static final int SRC_BIDI=5;
+    /** From normalizer2impl.cpp/nfc.nrm */
+    public static final int SRC_NFC=8;
+    /** From normalizer2impl.cpp/nfkc.nrm */
+    public static final int SRC_NFKC=9;
 
     // public methods ----------------------------------------------------
 
     /**
-     * Java friends implementation
-     */
-    public void setIndexData(CharTrie.FriendAgent friendagent)
-    {
-        m_trieIndex_ = friendagent.getPrivateIndex();
-        m_trieData_ = friendagent.getPrivateData();
-        m_trieInitialValue_ = friendagent.getPrivateInitialValue();
-    }
-
-    /**
-    * Gets the property value at the index.
-    * This is optimized.
-    * Note this is alittle different from CharTrie the index m_trieData_
-    * is never negative.
+    * Gets the main property value for code point ch.
     * @param ch code point whose property value is to be retrieved
     * @return property value of code point
     */
     public final int getProperty(int ch)
     {
-        if (ch < UTF16.LEAD_SURROGATE_MIN_VALUE
-            || (ch > UTF16.LEAD_SURROGATE_MAX_VALUE
-                && ch < UTF16.SUPPLEMENTARY_MIN_VALUE)) {
-            // BMP codepoint 0000..D7FF or DC00..FFFF
-            // optimized
-            try { // using try for ch < 0 is faster than using an if statement
-                return m_trieData_[
-                    (m_trieIndex_[ch >> Trie.INDEX_STAGE_1_SHIFT_]
-                          << Trie.INDEX_STAGE_2_SHIFT_)
-                    + (ch & Trie.INDEX_STAGE_3_MASK_)];
-            } catch (ArrayIndexOutOfBoundsException e) {
-                return m_trieInitialValue_;
-            }
-        }
-        if (ch <= UTF16.LEAD_SURROGATE_MAX_VALUE) {
-            // lead surrogate D800..DBFF
-            return m_trieData_[
-                    (m_trieIndex_[Trie.LEAD_INDEX_OFFSET_
-                                  + (ch >> Trie.INDEX_STAGE_1_SHIFT_)]
-                          << Trie.INDEX_STAGE_2_SHIFT_)
-                    + (ch & Trie.INDEX_STAGE_3_MASK_)];
-        }
-        if (ch <= UTF16.CODEPOINT_MAX_VALUE) {
-            // supplementary code point 10000..10FFFF
-            // look at the construction of supplementary characters
-            // trail forms the ends of it.
-            return m_trie_.getSurrogateValue(
-                                          UTF16.getLeadSurrogate(ch),
-                                          (char)(ch & Trie.SURROGATE_MASK_));
-        }
-        // ch is out of bounds
-        // return m_dataOffset_ if there is an error, in this case we return
-        // the default value: m_initialValue_
-        // we cannot assume that m_initialValue_ is at offset 0
-        // this is for optimization.
-        return m_trieInitialValue_;
-
-        // this all is an inlined form of return m_trie_.getCodePointValue(ch);
-    }
-
-    /**
-    * Getting the unsigned numeric value of a character embedded in the property
-    * argument
-    * @param prop the character
-    * @return unsigned numberic value
-    */
-    public static int getUnsignedValue(int prop)
-    {
-        return (prop >> VALUE_SHIFT_) & UNSIGNED_VALUE_MASK_AFTER_SHIFT_;
+        return m_trie_.get(ch);
     }
 
     /**
      * Gets the unicode additional properties.
-     * C version getUnicodeProperties.
+     * Java version of C u_getUnicodeProperties().
      * @param codepoint codepoint whose additional properties is to be
      *                  retrieved
-     * @param column
+     * @param column The column index.
      * @return unicode properties
      */
-       public int getAdditional(int codepoint, int column) {
-        if (column == -1) {
-            return getProperty(codepoint);
+    public int getAdditional(int codepoint, int column) {
+        assert column >= 0;
+        if (column >= m_additionalColumnsCount_) {
+            return 0;
         }
-           if (column < 0 || column >= m_additionalColumnsCount_) {
-           return 0;
-       }
-       return m_additionalVectors_[
-                     m_additionalTrie_.getCodePointValue(codepoint) + column];
-       }
+        return m_additionalVectors_[m_additionalTrie_.get(codepoint) + column];
+    }
 
-       /**
+    /**
      * <p>Get the "age" of the code point.</p>
      * <p>The "age" is the Unicode version when the code point was first
      * designated (as a non-character or for Private Use) or assigned a
@@ -203,6 +139,91 @@
                            version & LAST_NIBBLE_MASK_, 0, 0);
     }
 
+    // int-value and enumerated properties --------------------------------- ***
+
+    public int getType(int c) {
+        return getProperty(c)&TYPE_MASK;
+    }
+
+    /*
+     * Map some of the Grapheme Cluster Break values to Hangul Syllable Types.
+     * Hangul_Syllable_Type is fully redundant with a subset of Grapheme_Cluster_Break.
+     */
+    private static final int /* UHangulSyllableType */ gcbToHst[]={
+        HangulSyllableType.NOT_APPLICABLE,   /* U_GCB_OTHER */
+        HangulSyllableType.NOT_APPLICABLE,   /* U_GCB_CONTROL */
+        HangulSyllableType.NOT_APPLICABLE,   /* U_GCB_CR */
+        HangulSyllableType.NOT_APPLICABLE,   /* U_GCB_EXTEND */
+        HangulSyllableType.LEADING_JAMO,     /* U_GCB_L */
+        HangulSyllableType.NOT_APPLICABLE,   /* U_GCB_LF */
+        HangulSyllableType.LV_SYLLABLE,      /* U_GCB_LV */
+        HangulSyllableType.LVT_SYLLABLE,     /* U_GCB_LVT */
+        HangulSyllableType.TRAILING_JAMO,    /* U_GCB_T */
+        HangulSyllableType.VOWEL_JAMO        /* U_GCB_V */
+        /*
+         * Omit GCB values beyond what we need for hst.
+         * The code below checks for the array length.
+         */
+    };
+
+    private class IntProperty {
+        int column;  // SRC_PROPSVEC column, or "source" if mask==0
+        int mask;
+        int shift;
+
+        IntProperty(int column, int mask, int shift) {
+            this.column=column;
+            this.mask=mask;
+            this.shift=shift;
+        }
+
+        IntProperty(int source) {
+            this.column=source;
+            this.mask=0;
+        }
+
+        int getValue(int c) {
+            // systematic, directly stored properties
+            return (getAdditional(c, column)&mask)>>>shift;
+        }
+    }
+
+    private class BiDiIntProperty extends IntProperty {
+        BiDiIntProperty() {
+            super(SRC_BIDI);
+        }
+    }
+
+    private class CombiningClassIntProperty extends IntProperty {
+        CombiningClassIntProperty(int source) {
+            super(source);
+        }
+    }
+
+    private class NormQuickCheckIntProperty extends IntProperty {  // UCHAR_NF*_QUICK_CHECK properties
+        int which;
+        int max;
+
+        NormQuickCheckIntProperty(int source, int which, int max) {
+            super(source);
+            this.which=which;
+            this.max=max;
+        }
+    }
+
+    private IntProperty intProp =  new BiDiIntProperty() {  // BIDI_PAIRED_BRACKET_TYPE
+        int getValue(int c) {
+            return UBiDiProps.INSTANCE.getPairedBracketType(c);
+        }
+    };
+
+    public int getIntPropertyValue(int c, int which) {
+        if (which == BIDI_PAIRED_BRACKET_TYPE) {
+            return intProp.getValue(c);
+        }
+        return 0; // undefined
+    }
+
     /**
     * Forms a supplementary code point from the argument character<br>
     * Note this is for internal use hence no checks for the validity of the
@@ -217,42 +238,48 @@
     }
 
     /**
-    * Loads the property data and initialize the UCharacterProperty instance.
-    * @throws MissingResourceException when data is missing or data has been corrupted
-    */
-    public static UCharacterProperty getInstance()
+     * Gets the type mask
+     * @param type character type
+     * @return mask
+     */
+    public static final int getMask(int type)
     {
-        if(INSTANCE_ == null) {
-            try {
-                INSTANCE_ = new UCharacterProperty();
-            }
-            catch (Exception e) {
-                throw new MissingResourceException(e.getMessage(),"","");
-            }
-        }
-        return INSTANCE_;
+        return 1 << type;
     }
 
     /**
-     * Checks if the argument c is to be treated as a white space in ICU
-     * rules. Usually ICU rule white spaces are ignored unless quoted.
-     * Equivalent to test for Pattern_White_Space Unicode property.
-     * Stable set of characters, won't change.
-     * See UAX #31 Identifier and Pattern Syntax: http://www.unicode.org/reports/tr31/
-     * @param c codepoint to check
-     * @return true if c is a ICU white space
+     * Returns the digit values of characters like 'A' - 'Z', normal,
+     * half-width and full-width. This method assumes that the other digit
+     * characters are checked by the calling method.
+     * @param ch character to test
+     * @return -1 if ch is not a character of the form 'A' - 'Z', otherwise
+     *         its corresponding digit will be returned.
      */
-    public static boolean isRuleWhiteSpace(int c)
-    {
-        /* "white space" in the sense of ICU rule parsers
-           This is a FIXED LIST that is NOT DEPENDENT ON UNICODE PROPERTIES.
-           See UAX #31 Identifier and Pattern Syntax: http://www.unicode.org/reports/tr31/
-           U+0009..U+000D, U+0020, U+0085, U+200E..U+200F, and U+2028..U+2029
-           Equivalent to test for Pattern_White_Space Unicode property.
-        */
-        return (c >= 0x0009 && c <= 0x2029 &&
-                (c <= 0x000D || c == 0x0020 || c == 0x0085 ||
-                 c == 0x200E || c == 0x200F || c >= 0x2028));
+    public static int getEuropeanDigit(int ch) {
+        if ((ch > 0x7a && ch < 0xff21)
+            || ch < 0x41 || (ch > 0x5a && ch < 0x61)
+            || ch > 0xff5a || (ch > 0xff3a && ch < 0xff41)) {
+            return -1;
+        }
+        if (ch <= 0x7a) {
+            // ch >= 0x41 or ch < 0x61
+            return ch + 10 - ((ch <= 0x5a) ? 0x41 : 0x61);
+        }
+        // ch >= 0xff21
+        if (ch <= 0xff3a) {
+            return ch + 10 - 0xff21;
+        }
+        // ch >= 0xff41 && ch <= 0xff5a
+        return ch + 10 - 0xff41;
+    }
+
+    public int digit(int c) {
+        int value = getNumericTypeValue(getProperty(c)) - NTV_DECIMAL_START_;
+        if(value<=9) {
+            return value;
+        } else {
+            return -1;
+        }
     }
 
     // protected variables -----------------------------------------------
@@ -260,7 +287,7 @@
     /**
      * Extra property trie
      */
-    CharTrie m_additionalTrie_;
+    Trie2_16 m_additionalTrie_;
     /**
      * Extra property vectors, 1st column for age and second for binary
      * properties.
@@ -280,40 +307,24 @@
      * 0
      */
      int m_maxJTGValue_;
+    /**
+     * Script_Extensions data
+     */
+    public char[] m_scriptExtensions_;
 
     // private variables -------------------------------------------------
 
-      /**
-     * UnicodeData.txt property object
-     */
-    private static UCharacterProperty INSTANCE_ = null;
-
     /**
     * Default name of the datafile
     */
     private static final String DATA_FILE_NAME_ = "/sun/text/resources/uprops.icu";
 
     /**
-    * Default buffer size of datafile
-    */
-    private static final int DATA_BUFFER_SIZE_ = 25000;
-
-    /**
-    * Numeric value shift
-    */
-    private static final int VALUE_SHIFT_ = 8;
-
-    /**
-    * Mask to be applied after shifting to obtain an unsigned numeric value
-    */
-    private static final int UNSIGNED_VALUE_MASK_AFTER_SHIFT_ = 0xFF;
-
-    /**
     * Shift value for lead surrogate to form a supplementary character.
     */
     private static final int LEAD_SURROGATE_SHIFT_ = 10;
     /**
-    * Offset to add to combined surrogate pair to avoid msking.
+    * Offset to add to combined surrogate pair to avoid masking.
     */
     private static final int SURROGATE_OFFSET_ =
                            UTF16.SUPPLEMENTARY_MIN_VALUE -
@@ -321,7 +332,153 @@
                            LEAD_SURROGATE_SHIFT_) -
                            UTF16.TRAIL_SURROGATE_MIN_VALUE;
 
-    // additional properties ----------------------------------------------
+
+    // property data constants -------------------------------------------------
+
+    /**
+     * Numeric types and values in the main properties words.
+     */
+    private static final int NUMERIC_TYPE_VALUE_SHIFT_ = 6;
+    private static final int getNumericTypeValue(int props) {
+        return props >> NUMERIC_TYPE_VALUE_SHIFT_;
+    }
+
+    /* constants for the storage form of numeric types and values */
+    /** No numeric value. */
+    private static final int NTV_NONE_ = 0;
+    /** Decimal digits: nv=0..9 */
+    private static final int NTV_DECIMAL_START_ = 1;
+    /** Other digits: nv=0..9 */
+    private static final int NTV_DIGIT_START_ = 11;
+    /** Small integers: nv=0..154 */
+    private static final int NTV_NUMERIC_START_ = 21;
+
+    private static final int ntvGetType(int ntv) {
+        return
+            (ntv==NTV_NONE_) ? NumericType.NONE :
+            (ntv<NTV_DIGIT_START_) ?  NumericType.DECIMAL :
+            (ntv<NTV_NUMERIC_START_) ? NumericType.DIGIT :
+            NumericType.NUMERIC;
+    }
+
+    /*
+     * Properties in vector word 0
+     * Bits
+     * 31..24   DerivedAge version major/minor one nibble each
+     * 23..22   3..1: Bits 7..0 = Script_Extensions index
+     *             3: Script value from Script_Extensions
+     *             2: Script=Inherited
+     *             1: Script=Common
+     *             0: Script=bits 7..0
+     * 21..20   reserved
+     * 19..17   East Asian Width
+     * 16.. 8   UBlockCode
+     *  7.. 0   UScriptCode
+     */
+    /**
+     * Script_Extensions: mask includes Script
+     */
+    public static final int SCRIPT_X_MASK = 0x00c000ff;
+    //private static final int SCRIPT_X_SHIFT = 22;
+    /**
+     * Integer properties mask and shift values for East Asian cell width.
+     * Equivalent to icu4c UPROPS_EA_MASK
+     */
+    private static final int EAST_ASIAN_MASK_ = 0x000e0000;
+    /**
+     * Integer properties mask and shift values for East Asian cell width.
+     * Equivalent to icu4c UPROPS_EA_SHIFT
+     */
+    private static final int EAST_ASIAN_SHIFT_ = 17;
+    /**
+     * Integer properties mask and shift values for blocks.
+     * Equivalent to icu4c UPROPS_BLOCK_MASK
+     */
+    private static final int BLOCK_MASK_ = 0x0001ff00;
+    /**
+     * Integer properties mask and shift values for blocks.
+     * Equivalent to icu4c UPROPS_BLOCK_SHIFT
+     */
+    private static final int BLOCK_SHIFT_ = 8;
+    /**
+     * Integer properties mask and shift values for scripts.
+     * Equivalent to icu4c UPROPS_SHIFT_MASK
+     */
+    public static final int SCRIPT_MASK_ = 0x000000ff;
+
+    /**
+     * Additional properties used in internal trie data
+     */
+    /*
+     * Properties in vector word 1
+     * Each bit encodes one binary property.
+     * The following constants represent the bit number, use 1<<UPROPS_XYZ.
+     * UPROPS_BINARY_1_TOP<=32!
+     *
+     * Keep this list of property enums in sync with
+     * propListNames[] in icu/source/tools/genprops/props2.c!
+     *
+     * ICU 2.6/uprops format version 3.2 stores full properties instead of "Other_".
+     */
+    private static final int WHITE_SPACE_PROPERTY_ = 0;
+    private static final int DASH_PROPERTY_ = 1;
+    private static final int HYPHEN_PROPERTY_ = 2;
+    private static final int QUOTATION_MARK_PROPERTY_ = 3;
+    private static final int TERMINAL_PUNCTUATION_PROPERTY_ = 4;
+    private static final int MATH_PROPERTY_ = 5;
+    private static final int HEX_DIGIT_PROPERTY_ = 6;
+    private static final int ASCII_HEX_DIGIT_PROPERTY_ = 7;
+    private static final int ALPHABETIC_PROPERTY_ = 8;
+    private static final int IDEOGRAPHIC_PROPERTY_ = 9;
+    private static final int DIACRITIC_PROPERTY_ = 10;
+    private static final int EXTENDER_PROPERTY_ = 11;
+    private static final int NONCHARACTER_CODE_POINT_PROPERTY_ = 12;
+    private static final int GRAPHEME_EXTEND_PROPERTY_ = 13;
+    private static final int GRAPHEME_LINK_PROPERTY_ = 14;
+    private static final int IDS_BINARY_OPERATOR_PROPERTY_ = 15;
+    private static final int IDS_TRINARY_OPERATOR_PROPERTY_ = 16;
+    private static final int RADICAL_PROPERTY_ = 17;
+    private static final int UNIFIED_IDEOGRAPH_PROPERTY_ = 18;
+    private static final int DEFAULT_IGNORABLE_CODE_POINT_PROPERTY_ = 19;
+    private static final int DEPRECATED_PROPERTY_ = 20;
+    private static final int LOGICAL_ORDER_EXCEPTION_PROPERTY_ = 21;
+    private static final int XID_START_PROPERTY_ = 22;
+    private static final int XID_CONTINUE_PROPERTY_ = 23;
+    private static final int ID_START_PROPERTY_    = 24;
+    private static final int ID_CONTINUE_PROPERTY_ = 25;
+    private static final int GRAPHEME_BASE_PROPERTY_ = 26;
+    private static final int S_TERM_PROPERTY_ = 27;
+    private static final int VARIATION_SELECTOR_PROPERTY_ = 28;
+    private static final int PATTERN_SYNTAX = 29;                   /* new in ICU 3.4 and Unicode 4.1 */
+    private static final int PATTERN_WHITE_SPACE = 30;
+
+    /*
+     * Properties in vector word 2
+     * Bits
+     * 31..26   reserved
+     * 25..20   Line Break
+     * 19..15   Sentence Break
+     * 14..10   Word Break
+     *  9.. 5   Grapheme Cluster Break
+     *  4.. 0   Decomposition Type
+     */
+    private static final int LB_MASK          = 0x03f00000;
+    private static final int LB_SHIFT         = 20;
+
+    private static final int SB_MASK          = 0x000f8000;
+    private static final int SB_SHIFT         = 15;
+
+    private static final int WB_MASK          = 0x00007c00;
+    private static final int WB_SHIFT         = 10;
+
+    private static final int GCB_MASK         = 0x000003e0;
+    private static final int GCB_SHIFT        = 5;
+
+    /**
+     * Integer properties mask for decomposition type.
+     * Equivalent to icu4c UPROPS_DT_MASK.
+     */
+    private static final int DECOMPOSITION_TYPE_MASK_ = 0x0000001f;
 
     /**
      * First nibble shift
@@ -339,31 +496,112 @@
     // private constructors --------------------------------------------------
 
     /**
-    * Constructor
-    * @exception IOException thrown when data reading fails or data corrupted
-    */
+     * Constructor
+     * @exception IOException thrown when data reading fails or data corrupted
+     */
     private UCharacterProperty() throws IOException
     {
         // jar access
-        InputStream is = ICUData.getRequiredStream(DATA_FILE_NAME_);
-        BufferedInputStream b = new BufferedInputStream(is, DATA_BUFFER_SIZE_);
-        UCharacterPropertyReader reader = new UCharacterPropertyReader(b);
-        reader.read(this);
-        b.close();
+        ByteBuffer bytes=ICUBinary.getRequiredData(DATA_FILE_NAME_);
+        m_unicodeVersion_ = ICUBinary.readHeaderAndDataVersion(bytes, DATA_FORMAT, new IsAcceptable());
+        // Read or skip the 16 indexes.
+        int propertyOffset = bytes.getInt();
+        /* exceptionOffset = */ bytes.getInt();
+        /* caseOffset = */ bytes.getInt();
+        int additionalOffset = bytes.getInt();
+        int additionalVectorsOffset = bytes.getInt();
+        m_additionalColumnsCount_ = bytes.getInt();
+        int scriptExtensionsOffset = bytes.getInt();
+        int reservedOffset7 = bytes.getInt();
+        /* reservedOffset8 = */ bytes.getInt();
+        /* dataTopOffset = */ bytes.getInt();
+        m_maxBlockScriptValue_ = bytes.getInt();
+        m_maxJTGValue_ = bytes.getInt();
+        ICUBinary.skipBytes(bytes, (16 - 12) << 2);
+
+        // read the main properties trie
+        m_trie_ = Trie2_16.createFromSerialized(bytes);
+        int expectedTrieLength = (propertyOffset - 16) * 4;
+        int trieLength = m_trie_.getSerializedLength();
+        if(trieLength > expectedTrieLength) {
+            throw new IOException("uprops.icu: not enough bytes for main trie");
+        }
+        // skip padding after trie bytes
+        ICUBinary.skipBytes(bytes, expectedTrieLength - trieLength);
+
+        // skip unused intervening data structures
+        ICUBinary.skipBytes(bytes, (additionalOffset - propertyOffset) * 4);
 
-        m_trie_.putIndexData(this);
+        if(m_additionalColumnsCount_ > 0) {
+            // reads the additional property block
+            m_additionalTrie_ = Trie2_16.createFromSerialized(bytes);
+            expectedTrieLength = (additionalVectorsOffset-additionalOffset)*4;
+            trieLength = m_additionalTrie_.getSerializedLength();
+            if(trieLength > expectedTrieLength) {
+                throw new IOException("uprops.icu: not enough bytes for additional-properties trie");
+            }
+            // skip padding after trie bytes
+            ICUBinary.skipBytes(bytes, expectedTrieLength - trieLength);
+
+            // additional properties
+            int size = scriptExtensionsOffset - additionalVectorsOffset;
+            m_additionalVectors_ = new int[size];
+            for (int i = 0; i < size; i ++) {
+                m_additionalVectors_[i] = bytes.getInt();
+            }
+        }
+
+        // Script_Extensions
+        int numChars = (reservedOffset7 - scriptExtensionsOffset) * 2;
+        if(numChars > 0) {
+            m_scriptExtensions_ = new char[numChars];
+            for(int i = 0; i < numChars; ++i) {
+                m_scriptExtensions_[i] = bytes.getChar();
+            }
+        }
     }
 
+    private static final class IsAcceptable implements ICUBinary.Authenticate {
+        // @Override when we switch to Java 6
+        public boolean isDataVersionAcceptable(byte version[]) {
+            return version[0] == 7;
+        }
+    }
+
+    private static final int DATA_FORMAT = 0x5550726F;  // "UPro"
+
     public void upropsvec_addPropertyStarts(UnicodeSet set) {
         /* add the start code point of each same-value range of the properties vectors trie */
         if(m_additionalColumnsCount_>0) {
             /* if m_additionalColumnsCount_==0 then the properties vectors trie may not be there at all */
-            TrieIterator propsVectorsIter = new TrieIterator(m_additionalTrie_);
-            RangeValueIterator.Element propsVectorsResult = new RangeValueIterator.Element();
-            while(propsVectorsIter.next(propsVectorsResult)){
-                set.add(propsVectorsResult.start);
+            Iterator<Trie2.Range> trieIterator = m_additionalTrie_.iterator();
+            Trie2.Range range;
+            while(trieIterator.hasNext() && !(range=trieIterator.next()).leadSurrogate) {
+                set.add(range.startCodePoint);
             }
         }
     }
 
+    // This static initializer block must be placed after
+    // other static member initialization
+    static {
+        try {
+            INSTANCE = new UCharacterProperty();
+        }
+        catch (IOException e) {
+            throw new MissingResourceException(e.getMessage(),DATA_FILE_NAME_,"");
+        }
+    }
+
+
+    // Moved from UProperty.java
+    /**
+     * Enumerated property Bidi_Paired_Bracket_Type (new in Unicode 6.3).
+     * Used in UAX #9: Unicode Bidirectional Algorithm
+     * (http://www.unicode.org/reports/tr9/)
+     * Returns UCharacter.BidiPairedBracketType values.
+     * @stable ICU 52
+     */
+    public static final int BIDI_PAIRED_BRACKET_TYPE = 0x1015;
+
 }
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/UCharacterPropertyReader.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,190 +0,0 @@
-/*
- * Copyright (c) 2005, 2009, 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.
- */
-/*
- *******************************************************************************
- * (C) Copyright IBM Corp. and others, 1996-2009 - All Rights Reserved         *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
- *******************************************************************************
- */
-
-package sun.text.normalizer;
-
-import java.io.DataInputStream;
-import java.io.InputStream;
-import java.io.IOException;
-
-/**
-* <p>Internal reader class for ICU data file uprops.icu containing
-* Unicode codepoint data.</p>
-* <p>This class simply reads uprops.icu, authenticates that it is a valid
-* ICU data file and split its contents up into blocks of data for use in
-* <a href=UCharacterProperty.html>com.ibm.icu.impl.UCharacterProperty</a>.
-* </p>
-* <p>uprops.icu which is in big-endian format is jared together with this
-* package.</p>
-*
-* Unicode character properties file format see
-* (ICU4C)/source/tools/genprops/store.c
-*
-* @author Syn Wee Quek
-* @since release 2.1, February 1st 2002
-*/
-final class UCharacterPropertyReader implements ICUBinary.Authenticate
-{
-    // public methods ----------------------------------------------------
-
-    public boolean isDataVersionAcceptable(byte version[])
-    {
-        return version[0] == DATA_FORMAT_VERSION_[0]
-               && version[2] == DATA_FORMAT_VERSION_[2]
-               && version[3] == DATA_FORMAT_VERSION_[3];
-    }
-
-    // protected constructor ---------------------------------------------
-
-    /**
-    * <p>Protected constructor.</p>
-    * @param inputStream ICU uprop.dat file input stream
-    * @exception IOException throw if data file fails authentication
-    */
-    protected UCharacterPropertyReader(InputStream inputStream)
-                                                        throws IOException
-    {
-        m_unicodeVersion_ = ICUBinary.readHeader(inputStream, DATA_FORMAT_ID_,
-                                                 this);
-        m_dataInputStream_ = new DataInputStream(inputStream);
-    }
-
-    // protected methods -------------------------------------------------
-
-    /**
-    * <p>Reads uprops.icu, parse it into blocks of data to be stored in
-    * UCharacterProperty.</P
-    * @param ucharppty UCharacterProperty instance
-    * @exception IOException thrown when data reading fails
-    */
-    protected void read(UCharacterProperty ucharppty) throws IOException
-    {
-        // read the indexes
-        int count = INDEX_SIZE_;
-        m_propertyOffset_          = m_dataInputStream_.readInt();
-        count --;
-        m_exceptionOffset_         = m_dataInputStream_.readInt();
-        count --;
-        m_caseOffset_              = m_dataInputStream_.readInt();
-        count --;
-        m_additionalOffset_        = m_dataInputStream_.readInt();
-        count --;
-        m_additionalVectorsOffset_ = m_dataInputStream_.readInt();
-        count --;
-        m_additionalColumnsCount_  = m_dataInputStream_.readInt();
-        count --;
-        m_reservedOffset_          = m_dataInputStream_.readInt();
-        count --;
-        m_dataInputStream_.skipBytes(3 << 2);
-        count -= 3;
-        ucharppty.m_maxBlockScriptValue_ = m_dataInputStream_.readInt();
-        count --; // 10
-        ucharppty.m_maxJTGValue_ = m_dataInputStream_.readInt();
-        count --; // 11
-        m_dataInputStream_.skipBytes(count << 2);
-
-        // read the trie index block
-        // m_props_index_ in terms of ints
-        ucharppty.m_trie_ = new CharTrie(m_dataInputStream_, null);
-
-        // skip the 32 bit properties block
-        int size = m_exceptionOffset_ - m_propertyOffset_;
-        m_dataInputStream_.skipBytes(size * 4);
-
-        // reads the 32 bit exceptions block
-        size = m_caseOffset_ - m_exceptionOffset_;
-        m_dataInputStream_.skipBytes(size * 4);
-
-        // reads the 32 bit case block
-        size = (m_additionalOffset_ - m_caseOffset_) << 1;
-        m_dataInputStream_.skipBytes(size * 2);
-
-        if(m_additionalColumnsCount_ > 0) {
-            // reads the additional property block
-            ucharppty.m_additionalTrie_ = new CharTrie(m_dataInputStream_, null);
-
-            // additional properties
-            size = m_reservedOffset_ - m_additionalVectorsOffset_;
-            ucharppty.m_additionalVectors_ = new int[size];
-            for (int i = 0; i < size; i ++) {
-                ucharppty.m_additionalVectors_[i] = m_dataInputStream_.readInt();
-            }
-        }
-
-        m_dataInputStream_.close();
-        ucharppty.m_additionalColumnsCount_ = m_additionalColumnsCount_;
-        ucharppty.m_unicodeVersion_ = VersionInfo.getInstance(
-                         (int)m_unicodeVersion_[0], (int)m_unicodeVersion_[1],
-                         (int)m_unicodeVersion_[2], (int)m_unicodeVersion_[3]);
-    }
-
-    // private variables -------------------------------------------------
-
-    /**
-    * Index size
-    */
-    private static final int INDEX_SIZE_ = 16;
-
-    /**
-    * ICU data file input stream
-    */
-    private DataInputStream m_dataInputStream_;
-
-    /**
-    * Offset information in the indexes.
-    */
-    private int m_propertyOffset_;
-    private int m_exceptionOffset_;
-    private int m_caseOffset_;
-    private int m_additionalOffset_;
-    private int m_additionalVectorsOffset_;
-    private int m_additionalColumnsCount_;
-    private int m_reservedOffset_;
-    private byte m_unicodeVersion_[];
-
-    /**
-    * Data format "UPro".
-    */
-    private static final byte DATA_FORMAT_ID_[] = {(byte)0x55, (byte)0x50,
-                                                    (byte)0x72, (byte)0x6F};
-    /**
-     * Format version; this code works with all versions with the same major
-     * version number and the same Trie bit distribution.
-     */
-    private static final byte DATA_FORMAT_VERSION_[] = {(byte)0x5, (byte)0,
-                                             (byte)Trie.INDEX_STAGE_1_SHIFT_,
-                                             (byte)Trie.INDEX_STAGE_2_SHIFT_};
-}
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/UTF16.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/UTF16.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2009, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -22,15 +22,10 @@
  * or visit www.oracle.com if you need additional information or have any
  * questions.
  */
-/*
+/**
  *******************************************************************************
- * (C) Copyright IBM Corp. and others, 1996-2009 - All Rights Reserved         *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
+ * Copyright (C) 1996-2014, International Business Machines Corporation and
+ * others. All Rights Reserved.
  *******************************************************************************
  */
 
@@ -57,21 +52,21 @@
  *
  * // iteration forwards: Changes for UTF-32
  * int ch;
- * for (int i = 0; i < s.length(); i+=UTF16.getCharCount(ch)) {
- *     ch = UTF16.charAt(s,i);
+ * for (int i = 0; i < s.length(); i += UTF16.getCharCount(ch)) {
+ *     ch = UTF16.charAt(s, i);
  *     doSomethingWith(ch);
  * }
  *
  * // iteration backwards: Original
- * for (int i = s.length() -1; i >= 0; --i) {
+ * for (int i = s.length() - 1; i >= 0; --i) {
  *     char ch = s.charAt(i);
  *     doSomethingWith(ch);
  * }
  *
  * // iteration backwards: Changes for UTF-32
  * int ch;
- * for (int i = s.length() -1; i > 0; i-=UTF16.getCharCount(ch)) {
- *     ch = UTF16.charAt(s,i);
+ * for (int i = s.length() - 1; i > 0; i -= UTF16.getCharCount(ch)) {
+ *     ch = UTF16.charAt(s, i);
  *     doSomethingWith(ch);
  * }
  * }</pre>
@@ -93,7 +88,7 @@
  *   back if and only if <code>bounds(string, offset16) != TRAIL</code>.
  *   </li>
  *   <li>
- *    <strong>Exceptions:</strong> The error checking will throw an exception
+ *   <strong>Exceptions:</strong> The error checking will throw an exception
  *   if indices are out of bounds. Other than that, all methods will
  *   behave reasonably, even if unmatched surrogates or out-of-bounds UTF-32
  *   values are present. <code>UCharacter.isLegal()</code> can be used to check
@@ -106,10 +101,10 @@
  *   practice as missing glyphs (see the Unicode Standard Section 5.4, 5.5).
  *   </li>
  *   <li>
- *     <strong>Optimization:</strong> The method implementations may need
- *     optimization if the compiler doesn't fold static final methods. Since
- *     surrogate pairs will form an exceeding small percentage of all the text
- *     in the world, the singleton case should always be optimized for.
+ *   <strong>Optimization:</strong> The method implementations may need
+ *   optimization if the compiler doesn't fold static final methods. Since
+ *   surrogate pairs will form an exceeding small percentage of all the text
+ *   in the world, the singleton case should always be optimized for.
  *   </li>
  * </ul>
  * @author Mark Davis, with help from Markus Scherer
@@ -135,7 +130,7 @@
      * The minimum value for Supplementary code points
      * @stable ICU 2.1
      */
-    public static final int SUPPLEMENTARY_MIN_VALUE  = 0x10000;
+    public static final int SUPPLEMENTARY_MIN_VALUE = 0x10000;
     /**
      * Lead surrogate minimum value
      * @stable ICU 2.1
@@ -161,7 +156,41 @@
      * @stable ICU 2.1
      */
     public static final int SURROGATE_MIN_VALUE = LEAD_SURROGATE_MIN_VALUE;
+    /**
+     * Lead surrogate bitmask
+     */
+    private static final int LEAD_SURROGATE_BITMASK = 0xFFFFFC00;
+    /**
+     * Trail surrogate bitmask
+     */
+    private static final int TRAIL_SURROGATE_BITMASK = 0xFFFFFC00;
+    /**
+     * Surrogate bitmask
+     */
+    private static final int SURROGATE_BITMASK = 0xFFFFF800;
+    /**
+     * Lead surrogate bits
+     */
+    private static final int LEAD_SURROGATE_BITS = 0xD800;
+    /**
+     * Trail surrogate bits
+     */
+    private static final int TRAIL_SURROGATE_BITS = 0xDC00;
+    /**
+     * Surrogate bits
+     */
+    private static final int SURROGATE_BITS = 0xD800;
 
+    // constructor --------------------------------------------------------
+
+    // /CLOVER:OFF
+    /**
+     * Prevent instance from being created.
+     */
+    private UTF16() {
+    }
+
+    // /CLOVER:ON
     // public method ------------------------------------------------------
 
     /**
@@ -222,7 +251,7 @@
     }
 
     /**
-     * Extract a single UTF-32 value from a substring.
+     * Extract a single UTF-32 value from a string.
      * Used when iterating forwards or backwards (with
      * <code>UTF16.getCharCount()</code>, as well as random access. If a
      * validity check is required, use
@@ -232,19 +261,72 @@
      * character will be returned. If a complete supplementary character is
      * not found the incomplete character will be returned
      * @param source array of UTF-16 chars
-     * @param start offset to substring in the source array for analyzing
-     * @param limit offset to substring in the source array for analyzing
-     * @param offset16 UTF-16 offset relative to start
+     * @param offset16 UTF-16 offset to the start of the character.
      * @return UTF-32 value for the UTF-32 value that contains the char at
      *         offset16. The boundaries of that codepoint are the same as in
      *         <code>bounds32()</code>.
-     * @exception IndexOutOfBoundsException thrown if offset16 is not within
-     *            the range of start and limit.
+     * @exception IndexOutOfBoundsException thrown if offset16 is out of bounds.
      * @stable ICU 2.1
      */
-    public static int charAt(char source[], int start, int limit,
-                             int offset16)
-    {
+    public static int charAt(CharSequence source, int offset16) {
+        char single = source.charAt(offset16);
+        if (single < UTF16.LEAD_SURROGATE_MIN_VALUE) {
+            return single;
+        }
+        return _charAt(source, offset16, single);
+    }
+
+    private static int _charAt(CharSequence source, int offset16, char single) {
+        if (single > UTF16.TRAIL_SURROGATE_MAX_VALUE) {
+            return single;
+        }
+
+        // Convert the UTF-16 surrogate pair if necessary.
+        // For simplicity in usage, and because the frequency of pairs is
+        // low, look both directions.
+
+        if (single <= UTF16.LEAD_SURROGATE_MAX_VALUE) {
+            ++offset16;
+            if (source.length() != offset16) {
+                char trail = source.charAt(offset16);
+                if (trail >= UTF16.TRAIL_SURROGATE_MIN_VALUE
+                        && trail <= UTF16.TRAIL_SURROGATE_MAX_VALUE) {
+                    return UCharacterProperty.getRawSupplementary(single, trail);
+                }
+            }
+        } else {
+            --offset16;
+            if (offset16 >= 0) {
+                // single is a trail surrogate so
+                char lead = source.charAt(offset16);
+                if (lead >= UTF16.LEAD_SURROGATE_MIN_VALUE
+                        && lead <= UTF16.LEAD_SURROGATE_MAX_VALUE) {
+                    return UCharacterProperty.getRawSupplementary(lead, single);
+                }
+            }
+        }
+        return single; // return unmatched surrogate
+    }
+
+    /**
+     * Extract a single UTF-32 value from a substring. Used when iterating forwards or backwards
+     * (with <code>UTF16.getCharCount()</code>, as well as random access. If a validity check is
+     * required, use <code><a href="../lang/UCharacter.html#isLegal(char)">UCharacter.isLegal()
+     * </a></code>
+     * on the return value. If the char retrieved is part of a surrogate pair, its supplementary
+     * character will be returned. If a complete supplementary character is not found the incomplete
+     * character will be returned
+     *
+     * @param source Array of UTF-16 chars
+     * @param start Offset to substring in the source array for analyzing
+     * @param limit Offset to substring in the source array for analyzing
+     * @param offset16 UTF-16 offset relative to start
+     * @return UTF-32 value for the UTF-32 value that contains the char at offset16. The boundaries
+     *         of that codepoint are the same as in <code>bounds32()</code>.
+     * @exception IndexOutOfBoundsException Thrown if offset16 is not within the range of start and limit.
+     * @stable ICU 2.1
+     */
+    public static int charAt(char source[], int start, int limit, int offset16) {
         offset16 += start;
         if (offset16 < start || offset16 >= limit) {
             throw new ArrayIndexOutOfBoundsException(offset16);
@@ -259,7 +341,7 @@
         // For simplicity in usage, and because the frequency of pairs is
         // low, look both directions.
         if (single <= LEAD_SURROGATE_MAX_VALUE) {
-            offset16 ++;
+            offset16++;
             if (offset16 >= limit) {
                 return single;
             }
@@ -272,7 +354,7 @@
             if (offset16 == start) {
                 return single;
             }
-            offset16 --;
+            offset16--;
             char lead = source[offset16];
             if (isLeadSurrogate(lead))
                 return UCharacterProperty.getRawSupplementary(lead, single);
@@ -300,37 +382,34 @@
     /**
      * Determines whether the code value is a surrogate.
      * @param char16 the input character.
-     * @return true iff the input character is a surrogate.
+     * @return true if the input character is a surrogate.
      * @stable ICU 2.1
      */
     public static boolean isSurrogate(char char16)
     {
-        return LEAD_SURROGATE_MIN_VALUE <= char16 &&
-            char16 <= TRAIL_SURROGATE_MAX_VALUE;
+        return (char16 & SURROGATE_BITMASK) == SURROGATE_BITS;
     }
 
     /**
      * Determines whether the character is a trail surrogate.
      * @param char16 the input character.
-     * @return true iff the input character is a trail surrogate.
+     * @return true if the input character is a trail surrogate.
      * @stable ICU 2.1
      */
     public static boolean isTrailSurrogate(char char16)
     {
-        return (TRAIL_SURROGATE_MIN_VALUE <= char16 &&
-                char16 <= TRAIL_SURROGATE_MAX_VALUE);
+        return (char16 & TRAIL_SURROGATE_BITMASK) == TRAIL_SURROGATE_BITS;
     }
 
     /**
      * Determines whether the character is a lead surrogate.
      * @param char16 the input character.
-     * @return true iff the input character is a lead surrogate
+     * @return true if the input character is a lead surrogate
      * @stable ICU 2.1
      */
     public static boolean isLeadSurrogate(char char16)
     {
-        return LEAD_SURROGATE_MIN_VALUE <= char16 &&
-            char16 <= LEAD_SURROGATE_MAX_VALUE;
+        return (char16 & LEAD_SURROGATE_BITMASK) == LEAD_SURROGATE_BITS;
     }
 
     /**
@@ -359,7 +438,7 @@
      * <code><a href="../lang/UCharacter.html#isLegal(char)">isLegal()</a></code>
      * on char32 before calling.
      * @param char32 the input character.
-     * @return the trail surrogate if the getCharCount(ch) is 2; <br>otherwise
+     * @return the trail surrogate if the getCharCount(ch) is 2; <br> otherwise
      *         the character itself
      * @stable ICU 2.1
      */
@@ -370,7 +449,7 @@
                           (char32 & TRAIL_SURROGATE_MASK_));
         }
 
-        return (char)char32;
+        return (char) char32;
     }
 
     /**
@@ -415,16 +494,15 @@
         // Write the UTF-16 values
         if (char32 >= SUPPLEMENTARY_MIN_VALUE)
             {
-                target.append(getLeadSurrogate(char32));
-                target.append(getTrailSurrogate(char32));
-            }
+            target.append(getLeadSurrogate(char32));
+            target.append(getTrailSurrogate(char32));
+        }
         else {
-            target.append((char)char32);
+            target.append((char) char32);
         }
         return target;
     }
 
-    //// for StringPrep
     /**
      * Shifts offset16 by the argument number of codepoints within a subarray.
      * @param source char array
@@ -441,20 +519,20 @@
     public static int moveCodePointOffset(char source[], int start, int limit,
                                           int offset16, int shift32)
     {
-        int         size = source.length;
-        int         count;
-        char        ch;
-        int         result = offset16 + start;
-        if (start<0 || limit<start) {
+        int size = source.length;
+        int count;
+        char ch;
+        int result = offset16 + start;
+        if (start < 0 || limit < start) {
             throw new StringIndexOutOfBoundsException(start);
         }
-        if (limit>size) {
+        if (limit > size) {
             throw new StringIndexOutOfBoundsException(limit);
         }
-        if (offset16<0 || result>limit) {
+        if (offset16 < 0 || result > limit) {
             throw new StringIndexOutOfBoundsException(offset16);
         }
-        if (shift32 > 0 ) {
+        if (shift32 > 0) {
             if (shift32 + result > size) {
                 throw new StringIndexOutOfBoundsException(result);
             }
@@ -462,29 +540,29 @@
             while (result < limit && count > 0)
             {
                 ch = source[result];
-                if (isLeadSurrogate(ch) && (result+1 < limit) &&
-                        isTrailSurrogate(source[result+1])) {
-                    result ++;
+                if (isLeadSurrogate(ch) && (result + 1 < limit) &&
+                    isTrailSurrogate(source[result + 1])) {
+                    result++;
                 }
-                count --;
-                result ++;
+                count--;
+                result++;
             }
         } else {
             if (result + shift32 < start) {
                 throw new StringIndexOutOfBoundsException(result);
             }
-            for (count=-shift32; count>0; count--) {
+            for (count = -shift32; count > 0; count--) {
                 result--;
-                if (result<start) {
+                if (result < start) {
                     break;
                 }
                 ch = source[result];
-                if (isTrailSurrogate(ch) && result>start && isLeadSurrogate(source[result-1])) {
+                if (isTrailSurrogate(ch) && result > start && isLeadSurrogate(source[result - 1])) {
                     result--;
                 }
             }
         }
-        if (count != 0)  {
+        if (count != 0) {
             throw new StringIndexOutOfBoundsException(shift32);
         }
         result -= start;
@@ -501,7 +579,7 @@
     /**
      * Mask to retrieve the significant value from a trail surrogate.
      */
-    private static final int TRAIL_SURROGATE_MASK_     = 0x3FF;
+    private static final int TRAIL_SURROGATE_MASK_ = 0x3FF;
 
     /**
      * Value that all lead surrogate starts with
@@ -509,7 +587,7 @@
     private static final int LEAD_SURROGATE_OFFSET_ =
         LEAD_SURROGATE_MIN_VALUE -
         (SUPPLEMENTARY_MIN_VALUE
-         >> LEAD_SURROGATE_SHIFT_);
+        >> LEAD_SURROGATE_SHIFT_);
 
     // private methods ------------------------------------------------------
 
@@ -527,7 +605,7 @@
     private static String toString(int ch)
     {
         if (ch < SUPPLEMENTARY_MIN_VALUE) {
-            return String.valueOf((char)ch);
+            return String.valueOf((char) ch);
         }
 
         StringBuilder result = new StringBuilder();
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/UnicodeMatcher.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,59 +0,0 @@
-/*
- * Copyright (c) 2005, 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.
- */
-
-/*
- *******************************************************************************
- * (C) Copyright IBM Corp. 1996-2005 - All Rights Reserved                     *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
- *******************************************************************************
- */
-
-package sun.text.normalizer;
-
-/**
- * <code>UnicodeMatcher</code> defines a protocol for objects that can
- * match a range of characters in a Replaceable string.
- * @stable ICU 2.0
- */
-public interface UnicodeMatcher {
-
-    /**
-     * The character at index {@code i}, where
-     * {@code i < contextStart || i >= contextLimit},
-     * is ETHER.  This allows explicit matching by rules and UnicodeSets
-     * of text outside the context.  In traditional terms, this allows anchoring
-     * at the start and/or end.
-     * @stable ICU 2.0
-     */
-    static final char ETHER = '\uFFFF';
-
-}
-
-//eof
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/UnicodeSet.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/UnicodeSet.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -22,29 +22,31 @@
  * or visit www.oracle.com if you need additional information or have any
  * questions.
  */
+
 /*
  *******************************************************************************
- * (C) Copyright IBM Corp. and others, 1996-2009 - All Rights Reserved         *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
+ * Copyright (C) 1996-2015, International Business Machines Corporation and
+ * others. All Rights Reserved.
  *******************************************************************************
  */
-
 package sun.text.normalizer;
 
+import java.io.IOException;
 import java.text.ParsePosition;
-import java.util.Iterator;
+import java.util.ArrayList;
 import java.util.TreeSet;
 
 /**
- * A mutable set of Unicode characters and multicharacter strings.  Objects of this class
- * represent <em>character classes</em> used in regular expressions.
- * A character specifies a subset of Unicode code points.  Legal
- * code points are U+0000 to U+10FFFF, inclusive.
+ * A mutable set of Unicode characters and multicharacter strings.
+ * Objects of this class represent <em>character classes</em> used
+ * in regular expressions. A character specifies a subset of Unicode
+ * code points.  Legal code points are U+0000 to U+10FFFF, inclusive.
+ *
+ * Note: method freeze() will not only make the set immutable, but
+ * also makes important methods much higher performance:
+ * contains(c), containsNone(...), span(...), spanBack(...) etc.
+ * After the object is frozen, any subsequent call that wants to change
+ * the object will throw UnsupportedOperationException.
  *
  * <p>The UnicodeSet class is not designed to be subclassed.
  *
@@ -118,7 +120,7 @@
  * </blockquote>
  *
  * Any character may be preceded by a backslash in order to remove any special
- * meaning.  White space characters, as defined by UCharacterProperty.isRuleWhiteSpace(), are
+ * meaning.  White space characters, as defined by the Unicode Pattern_White_Space property, are
  * ignored, unless they are escaped.
  *
  * <p>Property patterns specify a set of characters having a certain
@@ -267,18 +269,24 @@
  *     </tr>
  *   </table>
  * </blockquote>
- * <p>To iterate over contents of UnicodeSet, use UnicodeSetIterator class.
+ * <p>To iterate over contents of UnicodeSet, the following are available:
+ * <ul><li>{@link #ranges()} to iterate through the ranges</li>
+ * <li>{@link #strings()} to iterate through the strings</li>
+ * <li>{@link #iterator()} to iterate through the entire contents in a single loop.
+ * That method is, however, not particularly efficient, since it "boxes" each code point into a String.
+ * </ul>
+ * All of the above can be used in <b>for</b> loops.
+ * The {@link com.ibm.icu.text.UnicodeSetIterator UnicodeSetIterator} can also be used, but not in <b>for</b> loops.
+ * <p>To replace, count elements, or delete spans, see {@link com.ibm.icu.text.UnicodeSetSpanner UnicodeSetSpanner}.
  *
  * @author Alan Liu
  * @stable ICU 2.0
- * @see UnicodeSetIterator
  */
-@SuppressWarnings("deprecation")
-public class UnicodeSet implements UnicodeMatcher {
+class UnicodeSet {
 
     private static final int LOW = 0x000000; // LOW <= all valid values. ZERO for codepoints
     private static final int HIGH = 0x110000; // HIGH > all valid values. 10000 for code units.
-                                             // 110000 for codepoints
+    // 110000 for codepoints
 
     /**
      * Minimum value that can be stored in a UnicodeSet.
@@ -299,7 +307,7 @@
 
     // NOTE: normally the field should be of type SortedSet; but that is missing a public clone!!
     // is not private so that UnicodeSetIterator can get access
-    TreeSet<String> strings = new TreeSet<>();
+    TreeSet<String> strings = new TreeSet<String>();
 
     /**
      * The pattern representation of this set.  This may not be the
@@ -310,18 +318,14 @@
      * indicating that toPattern() must generate a pattern
      * representation from the inversion list.
      */
-    private String pat = null;
 
     private static final int START_EXTRA = 16;         // initial storage. Must be >= 0
     private static final int GROW_EXTRA = START_EXTRA; // extra amount for growth. Must be >= 0
 
-    /**
-     * A set of all characters _except_ the second through last characters of
-     * certain ranges.  These ranges are ranges of characters whose
-     * properties are all exactly alike, e.g. CJK Ideographs from
-     * U+4E00 to U+9FA5.
-     */
-    private static UnicodeSet INCLUSIONS[] = null;
+    private static UnicodeSet INCLUSION = null;
+
+    private volatile BMPSet bmpSet; // The set is frozen if bmpSet or stringSpan is not null.
+    private volatile UnicodeSetStringSpan stringSpan;
 
     //----------------------------------------------------------------
     // Public API
@@ -331,14 +335,22 @@
      * Constructs an empty set.
      * @stable ICU 2.0
      */
-    public UnicodeSet() {
+    private UnicodeSet() {
         list = new int[1 + START_EXTRA];
         list[len++] = HIGH;
     }
 
     /**
-     * Constructs a set containing the given range.
-     * If {@code end > start} then an empty set is created.
+     * Constructs a copy of an existing set.
+     * @stable ICU 2.0
+     */
+    private UnicodeSet(UnicodeSet other) {
+        set(other);
+    }
+
+    /**
+     * Constructs a set containing the given range. If <code>end >
+     * start</code> then an empty set is created.
      *
      * @param start first character, inclusive, of range
      * @param end last character, inclusive, of range
@@ -359,7 +371,7 @@
      */
     public UnicodeSet(String pattern) {
         this();
-        applyPattern(pattern, null, null, IGNORE_SPACE);
+        applyPattern(pattern, null);
     }
 
     /**
@@ -368,172 +380,29 @@
      * copied to this object
      * @stable ICU 2.0
      */
-    @SuppressWarnings("unchecked") // Casting result of clone of a collection
     public UnicodeSet set(UnicodeSet other) {
+        checkFrozen();
         list = other.list.clone();
         len = other.len;
-        pat = other.pat;
-        strings = (TreeSet)other.strings.clone();
+        strings = new TreeSet<String>(other.strings);
         return this;
     }
 
     /**
-     * Modifies this set to represent the set specified by the given pattern.
-     * See the class description for the syntax of the pattern language.
-     * Whitespace is ignored.
-     * @param pattern a string specifying what characters are in the set
-     * @exception java.lang.IllegalArgumentException if the pattern
-     * contains a syntax error.
+     * Returns the number of elements in this set (its cardinality)
+     * Note than the elements of a set may include both individual
+     * codepoints and strings.
+     *
+     * @return the number of elements in this set (its cardinality).
      * @stable ICU 2.0
      */
-    public final UnicodeSet applyPattern(String pattern) {
-        return applyPattern(pattern, null, null, IGNORE_SPACE);
-    }
-
-    /**
-     * Append the <code>toPattern()</code> representation of a
-     * string to the given <code>StringBuffer</code>.
-     */
-    private static void _appendToPat(StringBuffer buf, String s, boolean escapeUnprintable) {
-        for (int i = 0; i < s.length(); i += UTF16.getCharCount(i)) {
-            _appendToPat(buf, UTF16.charAt(s, i), escapeUnprintable);
-        }
-    }
-
-    /**
-     * Append the <code>toPattern()</code> representation of a
-     * character to the given <code>StringBuffer</code>.
-     */
-    private static void _appendToPat(StringBuffer buf, int c, boolean escapeUnprintable) {
-        if (escapeUnprintable && Utility.isUnprintable(c)) {
-            // Use hex escape notation (<backslash>uxxxx or <backslash>Uxxxxxxxx) for anything
-            // unprintable
-            if (Utility.escapeUnprintable(buf, c)) {
-                return;
-            }
-        }
-        // Okay to let ':' pass through
-        switch (c) {
-        case '[': // SET_OPEN:
-        case ']': // SET_CLOSE:
-        case '-': // HYPHEN:
-        case '^': // COMPLEMENT:
-        case '&': // INTERSECTION:
-        case '\\': //BACKSLASH:
-        case '{':
-        case '}':
-        case '$':
-        case ':':
-            buf.append('\\');
-            break;
-        default:
-            // Escape whitespace
-            if (UCharacterProperty.isRuleWhiteSpace(c)) {
-                buf.append('\\');
-            }
-            break;
+    public int size() {
+        int n = 0;
+        int count = getRangeCount();
+        for (int i = 0; i < count; ++i) {
+            n += getRangeEnd(i) - getRangeStart(i) + 1;
         }
-        UTF16.append(buf, c);
-    }
-
-    /**
-     * Append a string representation of this set to result.  This will be
-     * a cleaned version of the string passed to applyPattern(), if there
-     * is one.  Otherwise it will be generated.
-     */
-    private StringBuffer _toPattern(StringBuffer result,
-                                    boolean escapeUnprintable) {
-        if (pat != null) {
-            int i;
-            int backslashCount = 0;
-            for (i=0; i<pat.length(); ) {
-                int c = UTF16.charAt(pat, i);
-                i += UTF16.getCharCount(c);
-                if (escapeUnprintable && Utility.isUnprintable(c)) {
-                    // If the unprintable character is preceded by an odd
-                    // number of backslashes, then it has been escaped.
-                    // Before unescaping it, we delete the final
-                    // backslash.
-                    if ((backslashCount % 2) == 1) {
-                        result.setLength(result.length() - 1);
-                    }
-                    Utility.escapeUnprintable(result, c);
-                    backslashCount = 0;
-                } else {
-                    UTF16.append(result, c);
-                    if (c == '\\') {
-                        ++backslashCount;
-                    } else {
-                        backslashCount = 0;
-                    }
-                }
-            }
-            return result;
-        }
-
-        return _generatePattern(result, escapeUnprintable, true);
-    }
-
-    /**
-     * Generate and append a string representation of this set to result.
-     * This does not use this.pat, the cleaned up copy of the string
-     * passed to applyPattern().
-     * @param includeStrings if false, doesn't include the strings.
-     * @stable ICU 3.8
-     */
-    public StringBuffer _generatePattern(StringBuffer result,
-                                         boolean escapeUnprintable, boolean includeStrings) {
-        result.append('[');
-
-        int count = getRangeCount();
-
-        // If the set contains at least 2 intervals and includes both
-        // MIN_VALUE and MAX_VALUE, then the inverse representation will
-        // be more economical.
-        if (count > 1 &&
-            getRangeStart(0) == MIN_VALUE &&
-            getRangeEnd(count-1) == MAX_VALUE) {
-
-            // Emit the inverse
-            result.append('^');
-
-            for (int i = 1; i < count; ++i) {
-                int start = getRangeEnd(i-1)+1;
-                int end = getRangeStart(i)-1;
-                _appendToPat(result, start, escapeUnprintable);
-                if (start != end) {
-                    if ((start+1) != end) {
-                        result.append('-');
-                    }
-                    _appendToPat(result, end, escapeUnprintable);
-                }
-            }
-        }
-
-        // Default; emit the ranges as pairs
-        else {
-            for (int i = 0; i < count; ++i) {
-                int start = getRangeStart(i);
-                int end = getRangeEnd(i);
-                _appendToPat(result, start, escapeUnprintable);
-                if (start != end) {
-                    if ((start+1) != end) {
-                        result.append('-');
-                    }
-                    _appendToPat(result, end, escapeUnprintable);
-                }
-            }
-        }
-
-        if (includeStrings && strings.size() > 0) {
-            Iterator<String> it = strings.iterator();
-            while (it.hasNext()) {
-                result.append('{');
-                _appendToPat(result, it.next(), escapeUnprintable);
-                result.append('}');
-            }
-        }
-        return result.append(']');
+        return n + strings.size();
     }
 
     // for internal use, after checkFrozen has been called
@@ -559,6 +428,7 @@
      * @stable ICU 2.0
      */
     public final UnicodeSet add(int c) {
+        checkFrozen();
         return add_unchecked(c);
     }
 
@@ -643,7 +513,6 @@
             len += 2;
         }
 
-        pat = null;
         return this;
     }
 
@@ -657,11 +526,11 @@
      * @return this object, for chaining
      * @stable ICU 2.0
      */
-    public final UnicodeSet add(String s) {
+    public final UnicodeSet add(CharSequence s) {
+        checkFrozen();
         int cp = getSingleCP(s);
         if (cp < 0) {
-            strings.add(s);
-            pat = null;
+            strings.add(s.toString());
         } else {
             add_unchecked(cp, cp);
         }
@@ -669,11 +538,13 @@
     }
 
     /**
+     * Utility for getting code point from single code point CharSequence.
+     * See the public UTF16.getSingleCodePoint()
      * @return a code point IF the string consists of a single one.
      * otherwise returns -1.
-     * @param string to test
+     * @param s to test
      */
-    private static int getSingleCP(String s) {
+    private static int getSingleCP(CharSequence s) {
         if (s.length() < 1) {
             throw new IllegalArgumentException("Can't use zero-length strings in UnicodeSet");
         }
@@ -701,6 +572,7 @@
      * @stable ICU 2.0
      */
     public UnicodeSet complement(int start, int end) {
+        checkFrozen();
         if (start < MIN_VALUE || start > MAX_VALUE) {
             throw new IllegalArgumentException("Invalid code point U+" + Utility.hex(start, 6));
         }
@@ -710,26 +582,6 @@
         if (start <= end) {
             xor(range(start, end), 2, 0);
         }
-        pat = null;
-        return this;
-    }
-
-    /**
-     * This is equivalent to
-     * <code>complement(MIN_VALUE, MAX_VALUE)</code>.
-     * @stable ICU 2.0
-     */
-    public UnicodeSet complement() {
-        if (list[0] == LOW) {
-            System.arraycopy(list, 1, list, 0, len-1);
-            --len;
-        } else {
-            ensureCapacity(len+1);
-            System.arraycopy(list, 0, list, 1, len);
-            list[0] = LOW;
-            ++len;
-        }
-        pat = null;
         return this;
     }
 
@@ -743,6 +595,12 @@
         if (c < MIN_VALUE || c > MAX_VALUE) {
             throw new IllegalArgumentException("Invalid code point U+" + Utility.hex(c, 6));
         }
+        if (bmpSet != null) {
+            return bmpSet.contains(c);
+        }
+        if (stringSpan != null) {
+            return stringSpan.contains(c);
+        }
 
         /*
         // Set i to the index of the start item greater than ch
@@ -751,7 +609,7 @@
         while (true) {
             if (c < list[++i]) break;
         }
-        */
+         */
 
         int i = findCodePoint(c);
 
@@ -790,7 +648,7 @@
         // invariant: c < list[hi]
         for (;;) {
             int i = (lo + hi) >>> 1;
-            if (i == lo) return hi;
+        if (i == lo) return hi;
             if (c < list[i]) {
                 hi = i;
             } else {
@@ -800,22 +658,6 @@
     }
 
     /**
-     * Adds all of the elements in the specified set to this set if
-     * they're not already present.  This operation effectively
-     * modifies this set so that its value is the <i>union</i> of the two
-     * sets.  The behavior of this operation is unspecified if the specified
-     * collection is modified while the operation is in progress.
-     *
-     * @param c set whose elements are to be added to this set.
-     * @stable ICU 2.0
-     */
-    public UnicodeSet addAll(UnicodeSet c) {
-        add(c.list, c.len, 0);
-        strings.addAll(c.strings);
-        return this;
-    }
-
-    /**
      * Retains only the elements in this set that are contained in the
      * specified set.  In other words, removes from this set all of
      * its elements that are not contained in the specified set.  This
@@ -826,36 +668,21 @@
      * @stable ICU 2.0
      */
     public UnicodeSet retainAll(UnicodeSet c) {
+        checkFrozen();
         retain(c.list, c.len, 0);
         strings.retainAll(c.strings);
         return this;
     }
 
     /**
-     * Removes from this set all of its elements that are contained in the
-     * specified set.  This operation effectively modifies this
-     * set so that its value is the <i>asymmetric set difference</i> of
-     * the two sets.
-     *
-     * @param c set that defines which elements will be removed from
-     *          this set.
-     * @stable ICU 2.0
-     */
-    public UnicodeSet removeAll(UnicodeSet c) {
-        retain(c.list, c.len, 2);
-        strings.removeAll(c.strings);
-        return this;
-    }
-
-    /**
      * Removes all of the elements from this set.  This set will be
      * empty after this call returns.
      * @stable ICU 2.0
      */
     public UnicodeSet clear() {
+        checkFrozen();
         list[0] = HIGH;
         len = 1;
-        pat = null;
         strings.clear();
         return this;
     }
@@ -923,405 +750,18 @@
      * of <code>pattern</code>
      * @exception java.lang.IllegalArgumentException if the parse fails.
      */
-    UnicodeSet applyPattern(String pattern,
-                      ParsePosition pos,
-                      SymbolTable symbols,
-                      int options) {
-
-        // Need to build the pattern in a temporary string because
-        // _applyPattern calls add() etc., which set pat to empty.
-        boolean parsePositionWasNull = pos == null;
-        if (parsePositionWasNull) {
-            pos = new ParsePosition(0);
-        }
-
-        StringBuffer rebuiltPat = new StringBuffer();
-        RuleCharacterIterator chars =
-            new RuleCharacterIterator(pattern, symbols, pos);
-        applyPattern(chars, symbols, rebuiltPat, options);
-        if (chars.inVariable()) {
-            syntaxError(chars, "Extra chars in variable value");
-        }
-        pat = rebuiltPat.toString();
-        if (parsePositionWasNull) {
-            int i = pos.getIndex();
-
-            // Skip over trailing whitespace
-            if ((options & IGNORE_SPACE) != 0) {
-                i = Utility.skipWhitespace(pattern, i);
-            }
-
-            if (i != pattern.length()) {
-                throw new IllegalArgumentException("Parse of \"" + pattern +
-                                                   "\" failed at " + i);
-            }
-        }
-        return this;
-    }
-
-    /**
-     * Parse the pattern from the given RuleCharacterIterator.  The
-     * iterator is advanced over the parsed pattern.
-     * @param chars iterator over the pattern characters.  Upon return
-     * it will be advanced to the first character after the parsed
-     * pattern, or the end of the iteration if all characters are
-     * parsed.
-     * @param symbols symbol table to use to parse and dereference
-     * variables, or null if none.
-     * @param rebuiltPat the pattern that was parsed, rebuilt or
-     * copied from the input pattern, as appropriate.
-     * @param options a bit mask of zero or more of the following:
-     * IGNORE_SPACE, CASE.
-     */
-    void applyPattern(RuleCharacterIterator chars, SymbolTable symbols,
-                      StringBuffer rebuiltPat, int options) {
-        // Syntax characters: [ ] ^ - & { }
-
-        // Recognized special forms for chars, sets: c-c s-s s&s
-
-        int opts = RuleCharacterIterator.PARSE_VARIABLES |
-                   RuleCharacterIterator.PARSE_ESCAPES;
-        if ((options & IGNORE_SPACE) != 0) {
-            opts |= RuleCharacterIterator.SKIP_WHITESPACE;
+    private UnicodeSet applyPattern(String pattern,
+            ParsePosition pos) {
+        if ("[:age=3.2:]".equals(pattern)) {
+            checkFrozen();
+            VersionInfo version = VersionInfo.getInstance("3.2");
+            applyFilter(new VersionFilter(version), UCharacterProperty.SRC_PROPSVEC);
+        } else {
+            throw new IllegalStateException("UnicodeSet.applyPattern(unexpected pattern "
+                          + pattern + ")");
         }
 
-        StringBuffer patBuf = new StringBuffer(), buf = null;
-        boolean usePat = false;
-        UnicodeSet scratch = null;
-        Object backup = null;
-
-        // mode: 0=before [, 1=between [...], 2=after ]
-        // lastItem: 0=none, 1=char, 2=set
-        int lastItem = 0, lastChar = 0, mode = 0;
-        char op = 0;
-
-        boolean invert = false;
-
-        clear();
-
-        while (mode != 2 && !chars.atEnd()) {
-            if (false) {
-                // Debugging assertion
-                if (!((lastItem == 0 && op == 0) ||
-                      (lastItem == 1 && (op == 0 || op == '-')) ||
-                      (lastItem == 2 && (op == 0 || op == '-' || op == '&')))) {
-                    throw new IllegalArgumentException();
-                }
-            }
-
-            int c = 0;
-            boolean literal = false;
-            UnicodeSet nested = null;
-
-            // -------- Check for property pattern
-
-            // setMode: 0=none, 1=unicodeset, 2=propertypat, 3=preparsed
-            int setMode = 0;
-            if (resemblesPropertyPattern(chars, opts)) {
-                setMode = 2;
-            }
-
-            // -------- Parse '[' of opening delimiter OR nested set.
-            // If there is a nested set, use `setMode' to define how
-            // the set should be parsed.  If the '[' is part of the
-            // opening delimiter for this pattern, parse special
-            // strings "[", "[^", "[-", and "[^-".  Check for stand-in
-            // characters representing a nested set in the symbol
-            // table.
-
-            else {
-                // Prepare to backup if necessary
-                backup = chars.getPos(backup);
-                c = chars.next(opts);
-                literal = chars.isEscaped();
-
-                if (c == '[' && !literal) {
-                    if (mode == 1) {
-                        chars.setPos(backup); // backup
-                        setMode = 1;
-                    } else {
-                        // Handle opening '[' delimiter
-                        mode = 1;
-                        patBuf.append('[');
-                        backup = chars.getPos(backup); // prepare to backup
-                        c = chars.next(opts);
-                        literal = chars.isEscaped();
-                        if (c == '^' && !literal) {
-                            invert = true;
-                            patBuf.append('^');
-                            backup = chars.getPos(backup); // prepare to backup
-                            c = chars.next(opts);
-                            literal = chars.isEscaped();
-                        }
-                        // Fall through to handle special leading '-';
-                        // otherwise restart loop for nested [], \p{}, etc.
-                        if (c == '-') {
-                            literal = true;
-                            // Fall through to handle literal '-' below
-                        } else {
-                            chars.setPos(backup); // backup
-                            continue;
-                        }
-                    }
-                } else if (symbols != null) {
-                     UnicodeMatcher m = symbols.lookupMatcher(c); // may be null
-                     if (m != null) {
-                         try {
-                             nested = (UnicodeSet) m;
-                             setMode = 3;
-                         } catch (ClassCastException e) {
-                             syntaxError(chars, "Syntax error");
-                         }
-                     }
-                }
-            }
-
-            // -------- Handle a nested set.  This either is inline in
-            // the pattern or represented by a stand-in that has
-            // previously been parsed and was looked up in the symbol
-            // table.
-
-            if (setMode != 0) {
-                if (lastItem == 1) {
-                    if (op != 0) {
-                        syntaxError(chars, "Char expected after operator");
-                    }
-                    add_unchecked(lastChar, lastChar);
-                    _appendToPat(patBuf, lastChar, false);
-                    lastItem = op = 0;
-                }
-
-                if (op == '-' || op == '&') {
-                    patBuf.append(op);
-                }
-
-                if (nested == null) {
-                    if (scratch == null) scratch = new UnicodeSet();
-                    nested = scratch;
-                }
-                switch (setMode) {
-                case 1:
-                    nested.applyPattern(chars, symbols, patBuf, options);
-                    break;
-                case 2:
-                    chars.skipIgnored(opts);
-                    nested.applyPropertyPattern(chars, patBuf, symbols);
-                    break;
-                case 3: // `nested' already parsed
-                    nested._toPattern(patBuf, false);
-                    break;
-                }
-
-                usePat = true;
-
-                if (mode == 0) {
-                    // Entire pattern is a category; leave parse loop
-                    set(nested);
-                    mode = 2;
-                    break;
-                }
-
-                switch (op) {
-                case '-':
-                    removeAll(nested);
-                    break;
-                case '&':
-                    retainAll(nested);
-                    break;
-                case 0:
-                    addAll(nested);
-                    break;
-                }
-
-                op = 0;
-                lastItem = 2;
-
-                continue;
-            }
-
-            if (mode == 0) {
-                syntaxError(chars, "Missing '['");
-            }
-
-            // -------- Parse special (syntax) characters.  If the
-            // current character is not special, or if it is escaped,
-            // then fall through and handle it below.
-
-            if (!literal) {
-                switch (c) {
-                case ']':
-                    if (lastItem == 1) {
-                        add_unchecked(lastChar, lastChar);
-                        _appendToPat(patBuf, lastChar, false);
-                    }
-                    // Treat final trailing '-' as a literal
-                    if (op == '-') {
-                        add_unchecked(op, op);
-                        patBuf.append(op);
-                    } else if (op == '&') {
-                        syntaxError(chars, "Trailing '&'");
-                    }
-                    patBuf.append(']');
-                    mode = 2;
-                    continue;
-                case '-':
-                    if (op == 0) {
-                        if (lastItem != 0) {
-                            op = (char) c;
-                            continue;
-                        } else {
-                            // Treat final trailing '-' as a literal
-                            add_unchecked(c, c);
-                            c = chars.next(opts);
-                            literal = chars.isEscaped();
-                            if (c == ']' && !literal) {
-                                patBuf.append("-]");
-                                mode = 2;
-                                continue;
-                            }
-                        }
-                    }
-                    syntaxError(chars, "'-' not after char or set");
-                    break;
-                case '&':
-                    if (lastItem == 2 && op == 0) {
-                        op = (char) c;
-                        continue;
-                    }
-                    syntaxError(chars, "'&' not after set");
-                    break;
-                case '^':
-                    syntaxError(chars, "'^' not after '['");
-                    break;
-                case '{':
-                    if (op != 0) {
-                        syntaxError(chars, "Missing operand after operator");
-                    }
-                    if (lastItem == 1) {
-                        add_unchecked(lastChar, lastChar);
-                        _appendToPat(patBuf, lastChar, false);
-                    }
-                    lastItem = 0;
-                    if (buf == null) {
-                        buf = new StringBuffer();
-                    } else {
-                        buf.setLength(0);
-                    }
-                    boolean ok = false;
-                    while (!chars.atEnd()) {
-                        c = chars.next(opts);
-                        literal = chars.isEscaped();
-                        if (c == '}' && !literal) {
-                            ok = true;
-                            break;
-                        }
-                        UTF16.append(buf, c);
-                    }
-                    if (buf.length() < 1 || !ok) {
-                        syntaxError(chars, "Invalid multicharacter string");
-                    }
-                    // We have new string. Add it to set and continue;
-                    // we don't need to drop through to the further
-                    // processing
-                    add(buf.toString());
-                    patBuf.append('{');
-                    _appendToPat(patBuf, buf.toString(), false);
-                    patBuf.append('}');
-                    continue;
-                case SymbolTable.SYMBOL_REF:
-                    //         symbols  nosymbols
-                    // [a-$]   error    error (ambiguous)
-                    // [a$]    anchor   anchor
-                    // [a-$x]  var "x"* literal '$'
-                    // [a-$.]  error    literal '$'
-                    // *We won't get here in the case of var "x"
-                    backup = chars.getPos(backup);
-                    c = chars.next(opts);
-                    literal = chars.isEscaped();
-                    boolean anchor = (c == ']' && !literal);
-                    if (symbols == null && !anchor) {
-                        c = SymbolTable.SYMBOL_REF;
-                        chars.setPos(backup);
-                        break; // literal '$'
-                    }
-                    if (anchor && op == 0) {
-                        if (lastItem == 1) {
-                            add_unchecked(lastChar, lastChar);
-                            _appendToPat(patBuf, lastChar, false);
-                        }
-                        add_unchecked(UnicodeMatcher.ETHER);
-                        usePat = true;
-                        patBuf.append(SymbolTable.SYMBOL_REF).append(']');
-                        mode = 2;
-                        continue;
-                    }
-                    syntaxError(chars, "Unquoted '$'");
-                    break;
-                default:
-                    break;
-                }
-            }
-
-            // -------- Parse literal characters.  This includes both
-            // escaped chars ("\u4E01") and non-syntax characters
-            // ("a").
-
-            switch (lastItem) {
-            case 0:
-                lastItem = 1;
-                lastChar = c;
-                break;
-            case 1:
-                if (op == '-') {
-                    if (lastChar >= c) {
-                        // Don't allow redundant (a-a) or empty (b-a) ranges;
-                        // these are most likely typos.
-                        syntaxError(chars, "Invalid range");
-                    }
-                    add_unchecked(lastChar, c);
-                    _appendToPat(patBuf, lastChar, false);
-                    patBuf.append(op);
-                    _appendToPat(patBuf, c, false);
-                    lastItem = op = 0;
-                } else {
-                    add_unchecked(lastChar, lastChar);
-                    _appendToPat(patBuf, lastChar, false);
-                    lastChar = c;
-                }
-                break;
-            case 2:
-                if (op != 0) {
-                    syntaxError(chars, "Set expected after operator");
-                }
-                lastChar = c;
-                lastItem = 1;
-                break;
-            }
-        }
-
-        if (mode != 2) {
-            syntaxError(chars, "Missing ']'");
-        }
-
-        chars.skipIgnored(opts);
-
-        if (invert) {
-            complement();
-        }
-
-        // Use the rebuilt pattern (pat) only if necessary.  Prefer the
-        // generated pattern.
-        if (usePat) {
-            rebuiltPat.append(patBuf.toString());
-        } else {
-            _generatePattern(rebuiltPat, false, true);
-        }
-    }
-
-    private static void syntaxError(RuleCharacterIterator chars, String msg) {
-        throw new IllegalArgumentException("Error: " + msg + " at \"" +
-                                           Utility.escape(chars.toString()) +
-                                           '"');
+        return this;
     }
 
     //----------------------------------------------------------------
@@ -1397,7 +837,6 @@
         int[] temp = list;
         list = buffer;
         buffer = temp;
-        pat = null;
         return this;
     }
 
@@ -1414,88 +853,87 @@
         // change from xor is that we have to check overlapping pairs
         // polarity bit 1 means a is second, bit 2 means b is.
         main:
-        while (true) {
-            switch (polarity) {
-              case 0: // both first; take lower if unequal
-                if (a < b) { // take a
-                    // Back up over overlapping ranges in buffer[]
-                    if (k > 0 && a <= buffer[k-1]) {
-                        // Pick latter end value in buffer[] vs. list[]
-                        a = max(list[i], buffer[--k]);
-                    } else {
-                        // No overlap
-                        buffer[k++] = a;
-                        a = list[i];
+            while (true) {
+                switch (polarity) {
+                case 0: // both first; take lower if unequal
+                    if (a < b) { // take a
+                        // Back up over overlapping ranges in buffer[]
+                        if (k > 0 && a <= buffer[k-1]) {
+                            // Pick latter end value in buffer[] vs. list[]
+                            a = max(list[i], buffer[--k]);
+                        } else {
+                            // No overlap
+                            buffer[k++] = a;
+                            a = list[i];
+                        }
+                        i++; // Common if/else code factored out
+                        polarity ^= 1;
+                    } else if (b < a) { // take b
+                        if (k > 0 && b <= buffer[k-1]) {
+                            b = max(other[j], buffer[--k]);
+                        } else {
+                            buffer[k++] = b;
+                            b = other[j];
+                        }
+                        j++;
+                        polarity ^= 2;
+                    } else { // a == b, take a, drop b
+                        if (a == HIGH) break main;
+                        // This is symmetrical; it doesn't matter if
+                        // we backtrack with a or b. - liu
+                        if (k > 0 && a <= buffer[k-1]) {
+                            a = max(list[i], buffer[--k]);
+                        } else {
+                            // No overlap
+                            buffer[k++] = a;
+                            a = list[i];
+                        }
+                        i++;
+                        polarity ^= 1;
+                        b = other[j++]; polarity ^= 2;
                     }
-                    i++; // Common if/else code factored out
-                    polarity ^= 1;
-                } else if (b < a) { // take b
-                    if (k > 0 && b <= buffer[k-1]) {
-                        b = max(other[j], buffer[--k]);
-                    } else {
+                    break;
+                case 3: // both second; take higher if unequal, and drop other
+                    if (b <= a) { // take a
+                        if (a == HIGH) break main;
+                        buffer[k++] = a;
+                    } else { // take b
+                        if (b == HIGH) break main;
                         buffer[k++] = b;
-                        b = other[j];
                     }
-                    j++;
-                    polarity ^= 2;
-                } else { // a == b, take a, drop b
-                    if (a == HIGH) break main;
-                    // This is symmetrical; it doesn't matter if
-                    // we backtrack with a or b. - liu
-                    if (k > 0 && a <= buffer[k-1]) {
-                        a = max(list[i], buffer[--k]);
-                    } else {
-                        // No overlap
-                        buffer[k++] = a;
-                        a = list[i];
-                    }
-                    i++;
-                    polarity ^= 1;
+                    a = list[i++]; polarity ^= 1;   // factored common code
                     b = other[j++]; polarity ^= 2;
-                }
-                break;
-              case 3: // both second; take higher if unequal, and drop other
-                if (b <= a) { // take a
-                    if (a == HIGH) break main;
-                    buffer[k++] = a;
-                } else { // take b
-                    if (b == HIGH) break main;
-                    buffer[k++] = b;
+                    break;
+                case 1: // a second, b first; if b < a, overlap
+                    if (a < b) { // no overlap, take a
+                        buffer[k++] = a; a = list[i++]; polarity ^= 1;
+                    } else if (b < a) { // OVERLAP, drop b
+                        b = other[j++]; polarity ^= 2;
+                    } else { // a == b, drop both!
+                        if (a == HIGH) break main;
+                        a = list[i++]; polarity ^= 1;
+                        b = other[j++]; polarity ^= 2;
+                    }
+                    break;
+                case 2: // a first, b second; if a < b, overlap
+                    if (b < a) { // no overlap, take b
+                        buffer[k++] = b; b = other[j++]; polarity ^= 2;
+                    } else  if (a < b) { // OVERLAP, drop a
+                        a = list[i++]; polarity ^= 1;
+                    } else { // a == b, drop both!
+                        if (a == HIGH) break main;
+                        a = list[i++]; polarity ^= 1;
+                        b = other[j++]; polarity ^= 2;
+                    }
+                    break;
                 }
-                a = list[i++]; polarity ^= 1;   // factored common code
-                b = other[j++]; polarity ^= 2;
-                break;
-              case 1: // a second, b first; if b < a, overlap
-                if (a < b) { // no overlap, take a
-                    buffer[k++] = a; a = list[i++]; polarity ^= 1;
-                } else if (b < a) { // OVERLAP, drop b
-                    b = other[j++]; polarity ^= 2;
-                } else { // a == b, drop both!
-                    if (a == HIGH) break main;
-                    a = list[i++]; polarity ^= 1;
-                    b = other[j++]; polarity ^= 2;
-                }
-                break;
-              case 2: // a first, b second; if a < b, overlap
-                if (b < a) { // no overlap, take b
-                    buffer[k++] = b; b = other[j++]; polarity ^= 2;
-                } else  if (a < b) { // OVERLAP, drop a
-                    a = list[i++]; polarity ^= 1;
-                } else { // a == b, drop both!
-                    if (a == HIGH) break main;
-                    a = list[i++]; polarity ^= 1;
-                    b = other[j++]; polarity ^= 2;
-                }
-                break;
             }
-        }
         buffer[k++] = HIGH;    // terminate
         len = k;
         // swap list and buffer
         int[] temp = list;
         list = buffer;
         buffer = temp;
-        pat = null;
         return this;
     }
 
@@ -1512,61 +950,60 @@
         // change from xor is that we have to check overlapping pairs
         // polarity bit 1 means a is second, bit 2 means b is.
         main:
-        while (true) {
-            switch (polarity) {
-              case 0: // both first; drop the smaller
-                if (a < b) { // drop a
-                    a = list[i++]; polarity ^= 1;
-                } else if (b < a) { // drop b
-                    b = other[j++]; polarity ^= 2;
-                } else { // a == b, take one, drop other
-                    if (a == HIGH) break main;
-                    buffer[k++] = a; a = list[i++]; polarity ^= 1;
-                    b = other[j++]; polarity ^= 2;
-                }
-                break;
-              case 3: // both second; take lower if unequal
-                if (a < b) { // take a
-                    buffer[k++] = a; a = list[i++]; polarity ^= 1;
-                } else if (b < a) { // take b
-                    buffer[k++] = b; b = other[j++]; polarity ^= 2;
-                } else { // a == b, take one, drop other
-                    if (a == HIGH) break main;
-                    buffer[k++] = a; a = list[i++]; polarity ^= 1;
-                    b = other[j++]; polarity ^= 2;
+            while (true) {
+                switch (polarity) {
+                case 0: // both first; drop the smaller
+                    if (a < b) { // drop a
+                        a = list[i++]; polarity ^= 1;
+                    } else if (b < a) { // drop b
+                        b = other[j++]; polarity ^= 2;
+                    } else { // a == b, take one, drop other
+                        if (a == HIGH) break main;
+                        buffer[k++] = a; a = list[i++]; polarity ^= 1;
+                        b = other[j++]; polarity ^= 2;
+                    }
+                    break;
+                case 3: // both second; take lower if unequal
+                    if (a < b) { // take a
+                        buffer[k++] = a; a = list[i++]; polarity ^= 1;
+                    } else if (b < a) { // take b
+                        buffer[k++] = b; b = other[j++]; polarity ^= 2;
+                    } else { // a == b, take one, drop other
+                        if (a == HIGH) break main;
+                        buffer[k++] = a; a = list[i++]; polarity ^= 1;
+                        b = other[j++]; polarity ^= 2;
+                    }
+                    break;
+                case 1: // a second, b first;
+                    if (a < b) { // NO OVERLAP, drop a
+                        a = list[i++]; polarity ^= 1;
+                    } else if (b < a) { // OVERLAP, take b
+                        buffer[k++] = b; b = other[j++]; polarity ^= 2;
+                    } else { // a == b, drop both!
+                        if (a == HIGH) break main;
+                        a = list[i++]; polarity ^= 1;
+                        b = other[j++]; polarity ^= 2;
+                    }
+                    break;
+                case 2: // a first, b second; if a < b, overlap
+                    if (b < a) { // no overlap, drop b
+                        b = other[j++]; polarity ^= 2;
+                    } else  if (a < b) { // OVERLAP, take a
+                        buffer[k++] = a; a = list[i++]; polarity ^= 1;
+                    } else { // a == b, drop both!
+                        if (a == HIGH) break main;
+                        a = list[i++]; polarity ^= 1;
+                        b = other[j++]; polarity ^= 2;
+                    }
+                    break;
                 }
-                break;
-              case 1: // a second, b first;
-                if (a < b) { // NO OVERLAP, drop a
-                    a = list[i++]; polarity ^= 1;
-                } else if (b < a) { // OVERLAP, take b
-                    buffer[k++] = b; b = other[j++]; polarity ^= 2;
-                } else { // a == b, drop both!
-                    if (a == HIGH) break main;
-                    a = list[i++]; polarity ^= 1;
-                    b = other[j++]; polarity ^= 2;
-                }
-                break;
-              case 2: // a first, b second; if a < b, overlap
-                if (b < a) { // no overlap, drop b
-                    b = other[j++]; polarity ^= 2;
-                } else  if (a < b) { // OVERLAP, take a
-                    buffer[k++] = a; a = list[i++]; polarity ^= 1;
-                } else { // a == b, drop both!
-                    if (a == HIGH) break main;
-                    a = list[i++]; polarity ^= 1;
-                    b = other[j++]; polarity ^= 2;
-                }
-                break;
             }
-        }
         buffer[k++] = HIGH;    // terminate
         len = k;
         // swap list and buffer
         int[] temp = list;
         list = buffer;
         buffer = temp;
-        pat = null;
         return this;
     }
 
@@ -1582,58 +1019,46 @@
         boolean contains(int codePoint);
     }
 
-    // VersionInfo for unassigned characters
-    static final VersionInfo NO_VERSION = VersionInfo.getInstance(0, 0, 0, 0);
+    private static final VersionInfo NO_VERSION = VersionInfo.getInstance(0, 0, 0, 0);
 
     private static class VersionFilter implements Filter {
         VersionInfo version;
-
         VersionFilter(VersionInfo version) { this.version = version; }
-
         public boolean contains(int ch) {
             VersionInfo v = UCharacter.getAge(ch);
             // Reference comparison ok; VersionInfo caches and reuses
             // unique objects.
             return v != NO_VERSION &&
-                   v.compareTo(version) <= 0;
+                    v.compareTo(version) <= 0;
         }
     }
 
     private static synchronized UnicodeSet getInclusions(int src) {
-        if (INCLUSIONS == null) {
-            INCLUSIONS = new UnicodeSet[UCharacterProperty.SRC_COUNT];
+        if (src != UCharacterProperty.SRC_PROPSVEC) {
+            throw new IllegalStateException("UnicodeSet.getInclusions(unknown src "+src+")");
         }
-        if(INCLUSIONS[src] == null) {
+
+        if (INCLUSION == null) {
             UnicodeSet incl = new UnicodeSet();
-            switch(src) {
-            case UCharacterProperty.SRC_PROPSVEC:
-                UCharacterProperty.getInstance().upropsvec_addPropertyStarts(incl);
-                break;
-            default:
-                throw new IllegalStateException("UnicodeSet.getInclusions(unknown src "+src+")");
-            }
-            INCLUSIONS[src] = incl;
+            UCharacterProperty.INSTANCE.upropsvec_addPropertyStarts(incl);
+            INCLUSION = incl;
         }
-        return INCLUSIONS[src];
+        return INCLUSION;
     }
 
     /**
      * Generic filter-based scanning code for UCD property UnicodeSets.
      */
     private UnicodeSet applyFilter(Filter filter, int src) {
-        // Walk through all Unicode characters, noting the start
+        // Logically, walk through all Unicode characters, noting the start
         // and end of each range for which filter.contain(c) is
         // true.  Add each range to a set.
         //
-        // To improve performance, use the INCLUSIONS set, which
+        // To improve performance, use an inclusions set which
         // encodes information about character ranges that are known
-        // to have identical properties, such as the CJK Ideographs
-        // from U+4E00 to U+9FA5.  INCLUSIONS contains all characters
-        // except the first characters of such ranges.
-        //
-        // TODO Where possible, instead of scanning over code points,
-        // use internal property data to initialize UnicodeSets for
-        // those properties.  Scanning code points is slow.
+        // to have identical properties.
+        // getInclusions(src) contains exactly the first characters of
+        // same-value ranges for the given properties "source".
 
         clear();
 
@@ -1668,204 +1093,315 @@
     }
 
     /**
-     * Remove leading and trailing rule white space and compress
-     * internal rule white space to a single space character.
+     * Is this frozen, according to the Freezable interface?
      *
-     * @see UCharacterProperty#isRuleWhiteSpace
-     */
-    private static String mungeCharName(String source) {
-        StringBuffer buf = new StringBuffer();
-        for (int i=0; i<source.length(); ) {
-            int ch = UTF16.charAt(source, i);
-            i += UTF16.getCharCount(ch);
-            if (UCharacterProperty.isRuleWhiteSpace(ch)) {
-                if (buf.length() == 0 ||
-                    buf.charAt(buf.length() - 1) == ' ') {
-                    continue;
-                }
-                ch = ' '; // convert to ' '
-            }
-            UTF16.append(buf, ch);
-        }
-        if (buf.length() != 0 &&
-            buf.charAt(buf.length() - 1) == ' ') {
-            buf.setLength(buf.length() - 1);
-        }
-        return buf.toString();
-    }
-
-    /**
-     * Modifies this set to contain those code points which have the
-     * given value for the given property.  Prior contents of this
-     * set are lost.
-     * @param propertyAlias the property alias
-     * @param valueAlias the value alias
-     * @param symbols if not null, then symbols are first called to see if a property
-     * is available. If true, then everything else is skipped.
-     * @return this set
-     * @stable ICU 3.2
+     * @return value
+     * @stable ICU 3.8
      */
-    public UnicodeSet applyPropertyAlias(String propertyAlias,
-                                         String valueAlias, SymbolTable symbols) {
-        if (valueAlias.length() > 0) {
-            if (propertyAlias.equals("Age")) {
-                // Must munge name, since
-                // VersionInfo.getInstance() does not do
-                // 'loose' matching.
-                VersionInfo version = VersionInfo.getInstance(mungeCharName(valueAlias));
-                applyFilter(new VersionFilter(version), UCharacterProperty.SRC_PROPSVEC);
-                return this;
-            }
-        }
-        throw new IllegalArgumentException("Unsupported property: " + propertyAlias);
-    }
-
-    /**
-     * Return true if the given iterator appears to point at a
-     * property pattern.  Regardless of the result, return with the
-     * iterator unchanged.
-     * @param chars iterator over the pattern characters.  Upon return
-     * it will be unchanged.
-     * @param iterOpts RuleCharacterIterator options
-     */
-    private static boolean resemblesPropertyPattern(RuleCharacterIterator chars,
-                                                    int iterOpts) {
-        boolean result = false;
-        iterOpts &= ~RuleCharacterIterator.PARSE_ESCAPES;
-        Object pos = chars.getPos(null);
-        int c = chars.next(iterOpts);
-        if (c == '[' || c == '\\') {
-            int d = chars.next(iterOpts & ~RuleCharacterIterator.SKIP_WHITESPACE);
-            result = (c == '[') ? (d == ':') :
-                     (d == 'N' || d == 'p' || d == 'P');
-        }
-        chars.setPos(pos);
-        return result;
+    public boolean isFrozen() {
+        return (bmpSet != null || stringSpan != null);
     }
 
     /**
-     * Parse the given property pattern at the given parse position.
-     * @param symbols TODO
+     * Freeze this class, according to the Freezable interface.
+     *
+     * @return this
+     * @stable ICU 4.4
      */
-    private UnicodeSet applyPropertyPattern(String pattern, ParsePosition ppos, SymbolTable symbols) {
-        int pos = ppos.getIndex();
-
-        // On entry, ppos should point to one of the following locations:
-
-        // Minimum length is 5 characters, e.g. \p{L}
-        if ((pos+5) > pattern.length()) {
-            return null;
-        }
-
-        boolean posix = false; // true for [:pat:], false for \p{pat} \P{pat} \N{pat}
-        boolean isName = false; // true for \N{pat}, o/w false
-        boolean invert = false;
+    public UnicodeSet freeze() {
+        if (!isFrozen()) {
+            // Do most of what compact() does before freezing because
+            // compact() will not work when the set is frozen.
+            // Small modification: Don't shrink if the savings would be tiny (<=GROW_EXTRA).
 
-        // Look for an opening [:, [:^, \p, or \P
-        if (pattern.regionMatches(pos, "[:", 0, 2)) {
-            posix = true;
-            pos = Utility.skipWhitespace(pattern, pos+2);
-            if (pos < pattern.length() && pattern.charAt(pos) == '^') {
-                ++pos;
-                invert = true;
-            }
-        } else if (pattern.regionMatches(true, pos, "\\p", 0, 2) ||
-                   pattern.regionMatches(pos, "\\N", 0, 2)) {
-            char c = pattern.charAt(pos+1);
-            invert = (c == 'P');
-            isName = (c == 'N');
-            pos = Utility.skipWhitespace(pattern, pos+2);
-            if (pos == pattern.length() || pattern.charAt(pos++) != '{') {
-                // Syntax error; "\p" or "\P" not followed by "{"
-                return null;
+            // Delete buffer first to defragment memory less.
+            buffer = null;
+            if (list.length > (len + GROW_EXTRA)) {
+                // Make the capacity equal to len or 1.
+                // We don't want to realloc of 0 size.
+                int capacity = (len == 0) ? 1 : len;
+                int[] oldList = list;
+                list = new int[capacity];
+                for (int i = capacity; i-- > 0;) {
+                    list[i] = oldList[i];
+                }
             }
-        } else {
-            // Open delimiter not seen
-            return null;
-        }
 
-        // Look for the matching close delimiter, either :] or }
-        int close = pattern.indexOf(posix ? ":]" : "}", pos);
-        if (close < 0) {
-            // Syntax error; close delimiter missing
-            return null;
-        }
-
-        // Look for an '=' sign.  If this is present, we will parse a
-        // medium \p{gc=Cf} or long \p{GeneralCategory=Format}
-        // pattern.
-        int equals = pattern.indexOf('=', pos);
-        String propName, valueName;
-        if (equals >= 0 && equals < close && !isName) {
-            // Equals seen; parse medium/long pattern
-            propName = pattern.substring(pos, equals);
-            valueName = pattern.substring(equals+1, close);
-        }
-
-        else {
-            // Handle case where no '=' is seen, and \N{}
-            propName = pattern.substring(pos, close);
-            valueName = "";
-
-            // Handle \N{name}
-            if (isName) {
-                // This is a little inefficient since it means we have to
-                // parse "na" back to UProperty.NAME even though we already
-                // know it's UProperty.NAME.  If we refactor the API to
-                // support args of (int, String) then we can remove
-                // "na" and make this a little more efficient.
-                valueName = propName;
-                propName = "na";
+            // Optimize contains() and span() and similar functions.
+            if (!strings.isEmpty()) {
+                stringSpan = new UnicodeSetStringSpan(this, new ArrayList<String>(strings), UnicodeSetStringSpan.ALL);
+            }
+            if (stringSpan == null || !stringSpan.needsStringSpanUTF16()) {
+                // Optimize for code point spans.
+                // There are no strings, or
+                // all strings are irrelevant for span() etc. because
+                // all of each string's code points are contained in this set.
+                // However, fully contained strings are relevant for spanAndCount(),
+                // so we create both objects.
+                bmpSet = new BMPSet(list, len);
             }
         }
-
-        applyPropertyAlias(propName, valueName, symbols);
-
-        if (invert) {
-            complement();
-        }
-
-        // Move to the limit position after the close delimiter
-        ppos.setIndex(close + (posix ? 2 : 1));
-
         return this;
     }
 
     /**
-     * Parse a property pattern.
-     * @param chars iterator over the pattern characters.  Upon return
-     * it will be advanced to the first character after the parsed
-     * pattern, or the end of the iteration if all characters are
-     * parsed.
-     * @param rebuiltPat the pattern that was parsed, rebuilt or
-     * copied from the input pattern, as appropriate.
-     * @param symbols TODO
+     * Span a string using this UnicodeSet.
+     * <p>To replace, count elements, or delete spans, see {@link com.ibm.icu.text.UnicodeSetSpanner UnicodeSetSpanner}.
+     * @param s The string to be spanned
+     * @param spanCondition The span condition
+     * @return the length of the span
+     * @stable ICU 4.4
+     */
+    public int span(CharSequence s, SpanCondition spanCondition) {
+        return span(s, 0, spanCondition);
+    }
+
+    /**
+     * Span a string using this UnicodeSet.
+     *   If the start index is less than 0, span will start from 0.
+     *   If the start index is greater than the string length, span returns the string length.
+     * <p>To replace, count elements, or delete spans, see {@link com.ibm.icu.text.UnicodeSetSpanner UnicodeSetSpanner}.
+     * @param s The string to be spanned
+     * @param start The start index that the span begins
+     * @param spanCondition The span condition
+     * @return the string index which ends the span (i.e. exclusive)
+     * @stable ICU 4.4
      */
-    private void applyPropertyPattern(RuleCharacterIterator chars,
-                                      StringBuffer rebuiltPat, SymbolTable symbols) {
-        String patStr = chars.lookahead();
-        ParsePosition pos = new ParsePosition(0);
-        applyPropertyPattern(patStr, pos, symbols);
-        if (pos.getIndex() == 0) {
-            syntaxError(chars, "Invalid property pattern");
+    public int span(CharSequence s, int start, SpanCondition spanCondition) {
+        int end = s.length();
+        if (start < 0) {
+            start = 0;
+        } else if (start >= end) {
+            return end;
+        }
+        if (bmpSet != null) {
+            // Frozen set without strings, or no string is relevant for span().
+            return bmpSet.span(s, start, spanCondition, null);
+        }
+        if (stringSpan != null) {
+            return stringSpan.span(s, start, spanCondition);
+        } else if (!strings.isEmpty()) {
+            int which = spanCondition == SpanCondition.NOT_CONTAINED ? UnicodeSetStringSpan.FWD_UTF16_NOT_CONTAINED
+                    : UnicodeSetStringSpan.FWD_UTF16_CONTAINED;
+            UnicodeSetStringSpan strSpan = new UnicodeSetStringSpan(this, new ArrayList<String>(strings), which);
+            if (strSpan.needsStringSpanUTF16()) {
+                return strSpan.span(s, start, spanCondition);
+            }
+        }
+
+        return spanCodePointsAndCount(s, start, spanCondition, null);
+    }
+
+    /**
+     * Same as span() but also counts the smallest number of set elements on any path across the span.
+     * <p>To replace, count elements, or delete spans, see {@link com.ibm.icu.text.UnicodeSetSpanner UnicodeSetSpanner}.
+     * @param outCount An output-only object (must not be null) for returning the count.
+     * @return the limit (exclusive end) of the span
+     */
+    public int spanAndCount(CharSequence s, int start, SpanCondition spanCondition, OutputInt outCount) {
+        if (outCount == null) {
+            throw new IllegalArgumentException("outCount must not be null");
         }
-        chars.jumpahead(pos.getIndex());
-        rebuiltPat.append(patStr, 0, pos.getIndex());
+        int end = s.length();
+        if (start < 0) {
+            start = 0;
+        } else if (start >= end) {
+            return end;
+        }
+        if (stringSpan != null) {
+            // We might also have bmpSet != null,
+            // but fully-contained strings are relevant for counting elements.
+            return stringSpan.spanAndCount(s, start, spanCondition, outCount);
+        } else if (bmpSet != null) {
+            return bmpSet.span(s, start, spanCondition, outCount);
+        } else if (!strings.isEmpty()) {
+            int which = spanCondition == SpanCondition.NOT_CONTAINED ? UnicodeSetStringSpan.FWD_UTF16_NOT_CONTAINED
+                    : UnicodeSetStringSpan.FWD_UTF16_CONTAINED;
+            which |= UnicodeSetStringSpan.WITH_COUNT;
+            UnicodeSetStringSpan strSpan = new UnicodeSetStringSpan(this, new ArrayList<String>(strings), which);
+            return strSpan.spanAndCount(s, start, spanCondition, outCount);
+        }
+
+        return spanCodePointsAndCount(s, start, spanCondition, outCount);
+    }
+
+    private int spanCodePointsAndCount(CharSequence s, int start,
+            SpanCondition spanCondition, OutputInt outCount) {
+        // Pin to 0/1 values.
+        boolean spanContained = (spanCondition != SpanCondition.NOT_CONTAINED);
+
+        int c;
+        int next = start;
+        int length = s.length();
+        int count = 0;
+        do {
+            c = Character.codePointAt(s, next);
+            if (spanContained != contains(c)) {
+                break;
+            }
+            ++count;
+            next += Character.charCount(c);
+        } while (next < length);
+        if (outCount != null) { outCount.value = count; }
+        return next;
     }
 
-    //----------------------------------------------------------------
-    // Case folding API
-    //----------------------------------------------------------------
+    /**
+     * Span a string backwards (from the fromIndex) using this UnicodeSet.
+     * If the fromIndex is less than 0, spanBack will return 0.
+     * If fromIndex is greater than the string length, spanBack will start from the string length.
+     * <p>To replace, count elements, or delete spans, see {@link com.ibm.icu.text.UnicodeSetSpanner UnicodeSetSpanner}.
+     * @param s The string to be spanned
+     * @param fromIndex The index of the char (exclusive) that the string should be spanned backwards
+     * @param spanCondition The span condition
+     * @return The string index which starts the span (i.e. inclusive).
+     * @stable ICU 4.4
+     */
+    public int spanBack(CharSequence s, int fromIndex, SpanCondition spanCondition) {
+        if (fromIndex <= 0) {
+            return 0;
+        }
+        if (fromIndex > s.length()) {
+            fromIndex = s.length();
+        }
+        if (bmpSet != null) {
+            // Frozen set without strings, or no string is relevant for spanBack().
+            return bmpSet.spanBack(s, fromIndex, spanCondition);
+        }
+        if (stringSpan != null) {
+            return stringSpan.spanBack(s, fromIndex, spanCondition);
+        } else if (!strings.isEmpty()) {
+            int which = (spanCondition == SpanCondition.NOT_CONTAINED)
+                    ? UnicodeSetStringSpan.BACK_UTF16_NOT_CONTAINED
+                            : UnicodeSetStringSpan.BACK_UTF16_CONTAINED;
+            UnicodeSetStringSpan strSpan = new UnicodeSetStringSpan(this, new ArrayList<String>(strings), which);
+            if (strSpan.needsStringSpanUTF16()) {
+                return strSpan.spanBack(s, fromIndex, spanCondition);
+            }
+        }
+
+        // Pin to 0/1 values.
+        boolean spanContained = (spanCondition != SpanCondition.NOT_CONTAINED);
+
+        int c;
+        int prev = fromIndex;
+        do {
+            c = Character.codePointBefore(s, prev);
+            if (spanContained != contains(c)) {
+                break;
+            }
+            prev -= Character.charCount(c);
+        } while (prev > 0);
+        return prev;
+    }
+
+    /**
+     * Clone a thawed version of this class, according to the Freezable interface.
+     * @return the clone, not frozen
+     * @stable ICU 4.4
+     */
+    public UnicodeSet cloneAsThawed() {
+        UnicodeSet result = new UnicodeSet(this);
+        assert !result.isFrozen();
+        return result;
+    }
+
+    // internal function
+    private void checkFrozen() {
+        if (isFrozen()) {
+            throw new UnsupportedOperationException("Attempt to modify frozen object");
+        }
+    }
 
     /**
-     * Bitmask for constructor and applyPattern() indicating that
-     * white space should be ignored.  If set, ignore characters for
-     * which UCharacterProperty.isRuleWhiteSpace() returns true,
-     * unless they are quoted or escaped.  This may be ORed together
-     * with other selectors.
-     * @stable ICU 3.8
+     * Argument values for whether span() and similar functions continue while the current character is contained vs.
+     * not contained in the set.
+     * <p>
+     * The functionality is straightforward for sets with only single code points, without strings (which is the common
+     * case):
+     * <ul>
+     * <li>CONTAINED and SIMPLE work the same.
+     * <li>CONTAINED and SIMPLE are inverses of NOT_CONTAINED.
+     * <li>span() and spanBack() partition any string the
+     * same way when alternating between span(NOT_CONTAINED) and span(either "contained" condition).
+     * <li>Using a
+     * complemented (inverted) set and the opposite span conditions yields the same results.
+     * </ul>
+     * When a set contains multi-code point strings, then these statements may not be true, depending on the strings in
+     * the set (for example, whether they overlap with each other) and the string that is processed. For a set with
+     * strings:
+     * <ul>
+     * <li>The complement of the set contains the opposite set of code points, but the same set of strings.
+     * Therefore, complementing both the set and the span conditions may yield different results.
+     * <li>When starting spans
+     * at different positions in a string (span(s, ...) vs. span(s+1, ...)) the ends of the spans may be different
+     * because a set string may start before the later position.
+     * <li>span(SIMPLE) may be shorter than
+     * span(CONTAINED) because it will not recursively try all possible paths. For example, with a set which
+     * contains the three strings "xy", "xya" and "ax", span("xyax", CONTAINED) will return 4 but span("xyax",
+     * SIMPLE) will return 3. span(SIMPLE) will never be longer than span(CONTAINED).
+     * <li>With either "contained" condition, span() and spanBack() may partition a string in different ways. For example,
+     * with a set which contains the two strings "ab" and "ba", and when processing the string "aba", span() will yield
+     * contained/not-contained boundaries of { 0, 2, 3 } while spanBack() will yield boundaries of { 0, 1, 3 }.
+     * </ul>
+     * Note: If it is important to get the same boundaries whether iterating forward or backward through a string, then
+     * either only span() should be used and the boundaries cached for backward operation, or an ICU BreakIterator could
+     * be used.
+     * <p>
+     * Note: Unpaired surrogates are treated like surrogate code points. Similarly, set strings match only on code point
+     * boundaries, never in the middle of a surrogate pair.
+     *
+     * @stable ICU 4.4
      */
-    public static final int IGNORE_SPACE = 1;
+    public enum SpanCondition {
+        /**
+         * Continues a span() while there is no set element at the current position.
+         * Increments by one code point at a time.
+         * Stops before the first set element (character or string).
+         * (For code points only, this is like while contains(current)==false).
+         * <p>
+         * When span() returns, the substring between where it started and the position it returned consists only of
+         * characters that are not in the set, and none of its strings overlap with the span.
+         *
+         * @stable ICU 4.4
+         */
+        NOT_CONTAINED,
+
+        /**
+         * Spans the longest substring that is a concatenation of set elements (characters or strings).
+         * (For characters only, this is like while contains(current)==true).
+         * <p>
+         * When span() returns, the substring between where it started and the position it returned consists only of set
+         * elements (characters or strings) that are in the set.
+         * <p>
+         * If a set contains strings, then the span will be the longest substring for which there
+         * exists at least one non-overlapping concatenation of set elements (characters or strings).
+         * This is equivalent to a POSIX regular expression for <code>(OR of each set element)*</code>.
+         * (Java/ICU/Perl regex stops at the first match of an OR.)
+         *
+         * @stable ICU 4.4
+         */
+        CONTAINED,
+
+        /**
+         * Continues a span() while there is a set element at the current position.
+         * Increments by the longest matching element at each position.
+         * (For characters only, this is like while contains(current)==true).
+         * <p>
+         * When span() returns, the substring between where it started and the position it returned consists only of set
+         * elements (characters or strings) that are in the set.
+         * <p>
+         * If a set only contains single characters, then this is the same as CONTAINED.
+         * <p>
+         * If a set contains strings, then the span will be the longest substring with a match at each position with the
+         * longest single set element (character or string).
+         * <p>
+         * Use this span condition together with other longest-match algorithms, such as ICU converters
+         * (ucnv_getUnicodeSet()).
+         *
+         * @stable ICU 4.4
+         */
+        SIMPLE,
+    }
 
 }
-
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/UnicodeSetIterator.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,219 +0,0 @@
-/*
- * Copyright (c) 2005, 2011, 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.
- */
-/*
- *******************************************************************************
- * (C) Copyright IBM Corp. and others, 1996-2009 - All Rights Reserved         *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
- *******************************************************************************
- */
-
-package sun.text.normalizer;
-
-import java.util.Iterator;
-
-/**
- * UnicodeSetIterator iterates over the contents of a UnicodeSet.  It
- * iterates over either code points or code point ranges.  After all
- * code points or ranges have been returned, it returns the
- * multicharacter strings of the UnicodSet, if any.
- *
- * <p>To iterate over code points, use a loop like this:
- * <pre>
- * UnicodeSetIterator it(set);
- * while (set.next()) {
- *   if (set.codepoint != UnicodeSetIterator::IS_STRING) {
- *     processCodepoint(set.codepoint);
- *   } else {
- *     processString(set.string);
- *   }
- * }
- * </pre>
- *
- * <p>To iterate over code point ranges, use a loop like this:
- * <pre>
- * UnicodeSetIterator it(set);
- * while (set.nextRange()) {
- *   if (set.codepoint != UnicodeSetIterator::IS_STRING) {
- *     processCodepointRange(set.codepoint, set.codepointEnd);
- *   } else {
- *     processString(set.string);
- *   }
- * }
- * </pre>
- * @author M. Davis
- * @stable ICU 2.0
- */
-public class UnicodeSetIterator {
-
-    /**
-     * Value of {@code codepoint} if the iterator points to a string.
-     * If {@code codepoint == IS_STRING}, then examine
-     * {@code string} for the current iteration result.
-     * @stable ICU 2.0
-     */
-    public static int IS_STRING = -1;
-
-    /**
-     * Current code point, or the special value {@code IS_STRING}, if
-     * the iterator points to a string.
-     * @stable ICU 2.0
-     */
-    public int codepoint;
-
-    /**
-     * When iterating over ranges using {@code nextRange()},
-     * {@code codepointEnd} contains the inclusive end of the
-     * iteration range, if {@code codepoint != IS_STRING}.  If
-     * iterating over code points using {@code next()}, or if
-     * {@code codepoint == IS_STRING}, then the value of
-     * {@code codepointEnd} is undefined.
-     * @stable ICU 2.0
-     */
-    public int codepointEnd;
-
-    /**
-     * If {@code codepoint == IS_STRING}, then {@code string} points
-     * to the current string.  If {@code codepoint != IS_STRING}, the
-     * value of {@code string} is undefined.
-     * @stable ICU 2.0
-     */
-    public String string;
-
-    /**
-     * Create an iterator over the given set.
-     * @param set set to iterate over
-     * @stable ICU 2.0
-     */
-    public UnicodeSetIterator(UnicodeSet set) {
-        reset(set);
-    }
-
-    /**
-     * Returns the next element in the set, either a code point range
-     * or a string.  If there are no more elements in the set, return
-     * false.  If {@code codepoint == IS_STRING}, the value is a
-     * string in the {@code string} field.  Otherwise the value is a
-     * range of one or more code points from {@code codepoint} to
-     * {@code codepointeEnd} inclusive.
-     *
-     * <p>The order of iteration is all code points ranges in sorted
-     * order, followed by all strings sorted order.  Ranges are
-     * disjoint and non-contiguous.  {@code string} is undefined
-     * unless {@code codepoint == IS_STRING}.  Do not mix calls to
-     * {@code next()} and {@code nextRange()} without calling
-     * {@code reset()} between them.  The results of doing so are
-     * undefined.
-     *
-     * @return true if there was another element in the set and this
-     * object contains the element.
-     * @stable ICU 2.0
-     */
-    public boolean nextRange() {
-        if (nextElement <= endElement) {
-            codepointEnd = endElement;
-            codepoint = nextElement;
-            nextElement = endElement+1;
-            return true;
-        }
-        if (range < endRange) {
-            loadRange(++range);
-            codepointEnd = endElement;
-            codepoint = nextElement;
-            nextElement = endElement+1;
-            return true;
-        }
-
-        // stringIterator == null iff there are no string elements remaining
-
-        if (stringIterator == null) return false;
-        codepoint = IS_STRING; // signal that value is actually a string
-        string = stringIterator.next();
-        if (!stringIterator.hasNext()) stringIterator = null;
-        return true;
-    }
-
-    /**
-     * Sets this iterator to visit the elements of the given set and
-     * resets it to the start of that set.  The iterator is valid only
-     * so long as {@code set} is valid.
-     * @param uset the set to iterate over.
-     * @stable ICU 2.0
-     */
-    public void reset(UnicodeSet uset) {
-        set = uset;
-        reset();
-    }
-
-    /**
-     * Resets this iterator to the start of the set.
-     * @stable ICU 2.0
-     */
-    public void reset() {
-        endRange = set.getRangeCount() - 1;
-        range = 0;
-        endElement = -1;
-        nextElement = 0;
-        if (endRange >= 0) {
-            loadRange(range);
-        }
-        stringIterator = null;
-        if (set.strings != null) {
-            stringIterator = set.strings.iterator();
-            if (!stringIterator.hasNext()) stringIterator = null;
-        }
-    }
-
-    // ======================= PRIVATES ===========================
-
-    private UnicodeSet set;
-    private int endRange = 0;
-    private int range = 0;
-    /**
-     * @internal
-     */
-    protected int endElement;
-    /**
-     * @internal
-     */
-    protected int nextElement;
-    private Iterator<String> stringIterator = null;
-
-    /**
-     * Invariant: stringIterator is null when there are no (more) strings remaining
-     */
-
-    /**
-     * @internal
-     */
-    protected void loadRange(int aRange) {
-        nextElement = set.getRangeStart(aRange);
-        endElement = set.getRangeEnd(aRange);
-    }
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/UnicodeSetStringSpan.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,1165 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/*
+ ******************************************************************************
+ *
+ *   Copyright (C) 2009-2014, International Business Machines
+ *   Corporation and others.  All Rights Reserved.
+ *
+ ******************************************************************************
+ */
+
+package sun.text.normalizer;
+
+import java.util.ArrayList;
+
+import sun.text.normalizer.UnicodeSet.SpanCondition;
+
+/*
+ * Implement span() etc. for a set with strings.
+ * Avoid recursion because of its exponential complexity.
+ * Instead, try multiple paths at once and track them with an IndexList.
+ */
+class UnicodeSetStringSpan {
+
+    /*
+     * Which span() variant will be used? The object is either built for one variant and used once,
+     * or built for all and may be used many times.
+     */
+    public static final int WITH_COUNT    = 0x40;  // spanAndCount() may be called
+    public static final int FWD           = 0x20;
+    public static final int BACK          = 0x10;
+    // public static final int UTF16      = 8;
+    public static final int CONTAINED     = 2;
+    public static final int NOT_CONTAINED = 1;
+
+    public static final int ALL = 0x7f;
+
+    public static final int FWD_UTF16_CONTAINED      = FWD  | /* UTF16 | */    CONTAINED;
+    public static final int FWD_UTF16_NOT_CONTAINED  = FWD  | /* UTF16 | */NOT_CONTAINED;
+    public static final int BACK_UTF16_CONTAINED     = BACK | /* UTF16 | */    CONTAINED;
+    public static final int BACK_UTF16_NOT_CONTAINED = BACK | /* UTF16 | */NOT_CONTAINED;
+
+    /**
+     * Special spanLength short values. (since Java has not unsigned byte type)
+     * All code points in the string are contained in the parent set.
+     */
+    static final short ALL_CP_CONTAINED = 0xff;
+
+    /** The spanLength is >=0xfe. */
+    static final short LONG_SPAN = ALL_CP_CONTAINED - 1;
+
+    /** Set for span(). Same as parent but without strings. */
+    private UnicodeSet spanSet;
+
+    /**
+     * Set for span(not contained).
+     * Same as spanSet, plus characters that start or end strings.
+     */
+    private UnicodeSet spanNotSet;
+
+    /** The strings of the parent set. */
+    private ArrayList<String> strings;
+
+    /** The lengths of span(), spanBack() etc. for each string. */
+    private short[] spanLengths;
+
+    /** Maximum lengths of relevant strings. */
+    private int maxLength16;
+
+    /** Are there strings that are not fully contained in the code point set? */
+    private boolean someRelevant;
+
+    /** Set up for all variants of span()? */
+    private boolean all;
+
+    /** Span helper */
+    private OffsetList offsets;
+
+    /**
+     * Constructs for all variants of span(), or only for any one variant.
+     * Initializes as little as possible, for single use.
+     */
+    public UnicodeSetStringSpan(final UnicodeSet set, final ArrayList<String> setStrings, int which) {
+        spanSet = new UnicodeSet(0, 0x10ffff);
+        // TODO: With Java 6, just take the parent set's strings as is,
+        // as a NavigableSet<String>, rather than as an ArrayList copy of the set of strings.
+        // Then iterate via the first() and higher() methods.
+        // (We do not want to create multiple Iterator objects in each span().)
+        // See ICU ticket #7454.
+        strings = setStrings;
+        all = (which == ALL);
+        spanSet.retainAll(set);
+        if (0 != (which & NOT_CONTAINED)) {
+            // Default to the same sets.
+            // addToSpanNotSet() will create a separate set if necessary.
+            spanNotSet = spanSet;
+        }
+        offsets = new OffsetList();
+
+        // Determine if the strings even need to be taken into account at all for span() etc.
+        // If any string is relevant, then all strings need to be used for
+        // span(longest match) but only the relevant ones for span(while contained).
+        // TODO: Possible optimization: Distinguish CONTAINED vs. LONGEST_MATCH
+        // and do not store UTF-8 strings if !thisRelevant and CONTAINED.
+        // (Only store irrelevant UTF-8 strings for LONGEST_MATCH where they are relevant after all.)
+        // Also count the lengths of the UTF-8 versions of the strings for memory allocation.
+        int stringsLength = strings.size();
+
+        int i, spanLength;
+        someRelevant = false;
+        for (i = 0; i < stringsLength; ++i) {
+            String string = strings.get(i);
+            int length16 = string.length();
+            spanLength = spanSet.span(string, SpanCondition.CONTAINED);
+            if (spanLength < length16) { // Relevant string.
+                someRelevant = true;
+            }
+            if (/* (0 != (which & UTF16)) && */ length16 > maxLength16) {
+                maxLength16 = length16;
+            }
+        }
+        if (!someRelevant && (which & WITH_COUNT) == 0) {
+            return;
+        }
+
+        // Freeze after checking for the need to use strings at all because freezing
+        // a set takes some time and memory which are wasted if there are no relevant strings.
+        if (all) {
+            spanSet.freeze();
+        }
+
+        int spanBackLengthsOffset;
+
+        // Allocate a block of meta data.
+        int allocSize;
+        if (all) {
+            // 2 sets of span lengths
+            allocSize = stringsLength * (2);
+        } else {
+            allocSize = stringsLength; // One set of span lengths.
+        }
+        spanLengths = new short[allocSize];
+
+        if (all) {
+            // Store span lengths for all span() variants.
+            spanBackLengthsOffset = stringsLength;
+        } else {
+            // Store span lengths for only one span() variant.
+            spanBackLengthsOffset = 0;
+        }
+
+        // Set the meta data and spanNotSet and write the UTF-8 strings.
+
+        for (i = 0; i < stringsLength; ++i) {
+            String string = strings.get(i);
+            int length16 = string.length();
+            spanLength = spanSet.span(string, SpanCondition.CONTAINED);
+            if (spanLength < length16) { // Relevant string.
+                if (true /* 0 != (which & UTF16) */) {
+                    if (0 != (which & CONTAINED)) {
+                        if (0 != (which & FWD)) {
+                            spanLengths[i] = makeSpanLengthByte(spanLength);
+                        }
+                        if (0 != (which & BACK)) {
+                            spanLength = length16
+                                    - spanSet.spanBack(string, length16, SpanCondition.CONTAINED);
+                            spanLengths[spanBackLengthsOffset + i] = makeSpanLengthByte(spanLength);
+                        }
+                    } else /* not CONTAINED, not all, but NOT_CONTAINED */{
+                        spanLengths[i] = spanLengths[spanBackLengthsOffset + i] = 0; // Only store a relevant/irrelevant
+                                                                                     // flag.
+                    }
+                }
+                if (0 != (which & NOT_CONTAINED)) {
+                    // Add string start and end code points to the spanNotSet so that
+                    // a span(while not contained) stops before any string.
+                    int c;
+                    if (0 != (which & FWD)) {
+                        c = string.codePointAt(0);
+                        addToSpanNotSet(c);
+                    }
+                    if (0 != (which & BACK)) {
+                        c = string.codePointBefore(length16);
+                        addToSpanNotSet(c);
+                    }
+                }
+            } else { // Irrelevant string.
+                if (all) {
+                    spanLengths[i] = spanLengths[spanBackLengthsOffset + i] = ALL_CP_CONTAINED;
+                } else {
+                    // All spanXYZLengths pointers contain the same address.
+                    spanLengths[i] = ALL_CP_CONTAINED;
+                }
+            }
+        }
+
+        // Finish.
+        if (all) {
+            spanNotSet.freeze();
+        }
+    }
+
+    /**
+     * Do the strings need to be checked in span() etc.?
+     *
+     * @return true if strings need to be checked (call span() here),
+     *         false if not (use a BMPSet for best performance).
+     */
+    public boolean needsStringSpanUTF16() {
+        return someRelevant;
+    }
+
+    /** For fast UnicodeSet::contains(c). */
+    public boolean contains(int c) {
+        return spanSet.contains(c);
+    }
+
+    /**
+     * Adds a starting or ending string character to the spanNotSet
+     * so that a character span ends before any string.
+     */
+    private void addToSpanNotSet(int c) {
+        if (spanNotSet == null || spanNotSet == spanSet) {
+            if (spanSet.contains(c)) {
+                return; // Nothing to do.
+            }
+            spanNotSet = spanSet.cloneAsThawed();
+        }
+        spanNotSet.add(c);
+    }
+
+    /*
+     * Note: In span() when spanLength==0
+     * (after a string match, or at the beginning after an empty code point span)
+     * and in spanNot() and spanNotUTF8(),
+     * string matching could use a binary search because all string matches are done
+     * from the same start index.
+     *
+     * For UTF-8, this would require a comparison function that returns UTF-16 order.
+     *
+     * This optimization should not be necessary for normal UnicodeSets because most sets have no strings, and most sets
+     * with strings have very few very short strings. For cases with many strings, it might be better to use a different
+     * API and implementation with a DFA (state machine).
+     */
+
+    /*
+     * Algorithm for span(SpanCondition.CONTAINED)
+     *
+     * Theoretical algorithm:
+     * - Iterate through the string, and at each code point boundary:
+     *   + If the code point there is in the set, then remember to continue after it.
+     *   + If a set string matches at the current position, then remember to continue after it.
+     *   + Either recursively span for each code point or string match, or recursively span
+     *     for all but the shortest one and iteratively continue the span with the shortest local match.
+     *   + Remember the longest recursive span (the farthest end point).
+     *   + If there is no match at the current position,
+     *     neither for the code point there nor for any set string,
+     *     then stop and return the longest recursive span length.
+     *
+     * Optimized implementation:
+     *
+     * (We assume that most sets will have very few very short strings.
+     * A span using a string-less set is extremely fast.)
+     *
+     * Create and cache a spanSet which contains all of the single code points of the original set
+     * but none of its strings.
+     *
+     * - Start with spanLength=spanSet.span(SpanCondition.CONTAINED).
+     * - Loop:
+     *   + Try to match each set string at the end of the spanLength.
+     *     ~ Set strings that start with set-contained code points
+     *       must be matched with a partial overlap
+     *       because the recursive algorithm would have tried to match them at every position.
+     *     ~ Set strings that entirely consist of set-contained code points
+     *       are irrelevant for span(SpanCondition.CONTAINED)
+     *       because the recursive algorithm would continue after them anyway and
+     *       find the longest recursive match from their end.
+     *     ~ Rather than recursing, note each end point of a set string match.
+     *   + If no set string matched after spanSet.span(),
+     *     then return with where the spanSet.span() ended.
+     *   + If at least one set string matched after spanSet.span(),
+     *     then pop the shortest string match end point and continue the loop,
+     *     trying to match all set strings from there.
+     *   + If at least one more set string matched after a previous string match, then test if the
+     *     code point after the previous string match is also contained in the set.
+     *     Continue the loop with the shortest end point of
+     *     either this code point or a matching set string.
+     *   + If no more set string matched after a previous string match,
+     *     then try another spanLength=spanSet.span(SpanCondition.CONTAINED).
+     *     Stop if spanLength==0, otherwise continue the loop.
+     *
+     * By noting each end point of a set string match, the function visits each string position at most once and
+     * finishes in linear time.
+     *
+     * The recursive algorithm may visit the same string position many times
+     * if multiple paths lead to it and finishes in exponential time.
+     */
+
+    /*
+     * Algorithm for span(SIMPLE)
+     *
+     * Theoretical algorithm:
+     * - Iterate through the string, and at each code point boundary:
+     *   + If the code point there is in the set, then remember to continue after it.
+     *   + If a set string matches at the current position, then remember to continue after it.
+     *   + Continue from the farthest match position and ignore all others.
+     *   + If there is no match at the current position, then stop and return the current position.
+     *
+     * Optimized implementation:
+     *
+     * (Same assumption and spanSet as above.)
+     *
+     * - Start with spanLength=spanSet.span(SpanCondition.CONTAINED).
+     * - Loop:
+     *   + Try to match each set string at the end of the spanLength.
+     *     ~ Set strings that start with set-contained code points
+     *       must be matched with a partial overlap
+     *       because the standard algorithm would have tried to match them earlier.
+     *     ~ Set strings that entirely consist of set-contained code points
+     *       must be matched with a full overlap because the longest-match algorithm
+     *       would hide set string matches that end earlier.
+     *       Such set strings need not be matched earlier inside the code point span
+     *       because the standard algorithm would then have
+     *       continued after the set string match anyway.
+     *     ~ Remember the longest set string match (farthest end point)
+     *       from the earliest starting point.
+     *   + If no set string matched after spanSet.span(),
+     *     then return with where the spanSet.span() ended.
+     *   + If at least one set string matched,
+     *     then continue the loop after the longest match from the earliest position.
+     *   + If no more set string matched after a previous string match,
+     *     then try another spanLength=spanSet.span(SpanCondition.CONTAINED).
+     *     Stop if spanLength==0, otherwise continue the loop.
+     */
+    /**
+     * Spans a string.
+     *
+     * @param s The string to be spanned
+     * @param start The start index that the span begins
+     * @param spanCondition The span condition
+     * @return the limit (exclusive end) of the span
+     */
+    public int span(CharSequence s, int start, SpanCondition spanCondition) {
+        if (spanCondition == SpanCondition.NOT_CONTAINED) {
+            return spanNot(s, start, null);
+        }
+        int spanLimit = spanSet.span(s, start, SpanCondition.CONTAINED);
+        if (spanLimit == s.length()) {
+            return spanLimit;
+        }
+        return spanWithStrings(s, start, spanLimit, spanCondition);
+    }
+
+    /**
+     * Synchronized method for complicated spans using the offsets.
+     * Avoids synchronization for simple cases.
+     *
+     * @param spanLimit = spanSet.span(s, start, CONTAINED)
+     */
+    private synchronized int spanWithStrings(CharSequence s, int start, int spanLimit,
+            SpanCondition spanCondition) {
+        // Consider strings; they may overlap with the span.
+        int initSize = 0;
+        if (spanCondition == SpanCondition.CONTAINED) {
+            // Use offset list to try all possibilities.
+            initSize = maxLength16;
+        }
+        offsets.setMaxLength(initSize);
+        int length = s.length();
+        int pos = spanLimit, rest = length - spanLimit;
+        int spanLength = spanLimit - start;
+        int i, stringsLength = strings.size();
+        for (;;) {
+            if (spanCondition == SpanCondition.CONTAINED) {
+                for (i = 0; i < stringsLength; ++i) {
+                    int overlap = spanLengths[i];
+                    if (overlap == ALL_CP_CONTAINED) {
+                        continue; // Irrelevant string.
+                    }
+                    String string = strings.get(i);
+
+                    int length16 = string.length();
+
+                    // Try to match this string at pos-overlap..pos.
+                    if (overlap >= LONG_SPAN) {
+                        overlap = length16;
+                        // While contained: No point matching fully inside the code point span.
+                        overlap = string.offsetByCodePoints(overlap, -1); // Length of the string minus the last code
+                                                                          // point.
+                    }
+                    if (overlap > spanLength) {
+                        overlap = spanLength;
+                    }
+                    int inc = length16 - overlap; // Keep overlap+inc==length16.
+                    for (;;) {
+                        if (inc > rest) {
+                            break;
+                        }
+                        // Try to match if the increment is not listed already.
+                        if (!offsets.containsOffset(inc) && matches16CPB(s, pos - overlap, length, string, length16)) {
+                            if (inc == rest) {
+                                return length; // Reached the end of the string.
+                            }
+                            offsets.addOffset(inc);
+                        }
+                        if (overlap == 0) {
+                            break;
+                        }
+                        --overlap;
+                        ++inc;
+                    }
+                }
+            } else /* SIMPLE */{
+                int maxInc = 0, maxOverlap = 0;
+                for (i = 0; i < stringsLength; ++i) {
+                    int overlap = spanLengths[i];
+                    // For longest match, we do need to try to match even an all-contained string
+                    // to find the match from the earliest start.
+
+                    String string = strings.get(i);
+
+                    int length16 = string.length();
+
+                    // Try to match this string at pos-overlap..pos.
+                    if (overlap >= LONG_SPAN) {
+                        overlap = length16;
+                        // Longest match: Need to match fully inside the code point span
+                        // to find the match from the earliest start.
+                    }
+                    if (overlap > spanLength) {
+                        overlap = spanLength;
+                    }
+                    int inc = length16 - overlap; // Keep overlap+inc==length16.
+                    for (;;) {
+                        if (inc > rest || overlap < maxOverlap) {
+                            break;
+                        }
+                        // Try to match if the string is longer or starts earlier.
+                        if ((overlap > maxOverlap || /* redundant overlap==maxOverlap && */inc > maxInc)
+                                && matches16CPB(s, pos - overlap, length, string, length16)) {
+                            maxInc = inc; // Longest match from earliest start.
+                            maxOverlap = overlap;
+                            break;
+                        }
+                        --overlap;
+                        ++inc;
+                    }
+                }
+
+                if (maxInc != 0 || maxOverlap != 0) {
+                    // Longest-match algorithm, and there was a string match.
+                    // Simply continue after it.
+                    pos += maxInc;
+                    rest -= maxInc;
+                    if (rest == 0) {
+                        return length; // Reached the end of the string.
+                    }
+                    spanLength = 0; // Match strings from after a string match.
+                    continue;
+                }
+            }
+            // Finished trying to match all strings at pos.
+
+            if (spanLength != 0 || pos == 0) {
+                // The position is after an unlimited code point span (spanLength!=0),
+                // not after a string match.
+                // The only position where spanLength==0 after a span is pos==0.
+                // Otherwise, an unlimited code point span is only tried again when no
+                // strings match, and if such a non-initial span fails we stop.
+                if (offsets.isEmpty()) {
+                    return pos; // No strings matched after a span.
+                }
+                // Match strings from after the next string match.
+            } else {
+                // The position is after a string match (or a single code point).
+                if (offsets.isEmpty()) {
+                    // No more strings matched after a previous string match.
+                    // Try another code point span from after the last string match.
+                    spanLimit = spanSet.span(s, pos, SpanCondition.CONTAINED);
+                    spanLength = spanLimit - pos;
+                    if (spanLength == rest || // Reached the end of the string, or
+                            spanLength == 0 // neither strings nor span progressed.
+                    ) {
+                        return spanLimit;
+                    }
+                    pos += spanLength;
+                    rest -= spanLength;
+                    continue; // spanLength>0: Match strings from after a span.
+                } else {
+                    // Try to match only one code point from after a string match if some
+                    // string matched beyond it, so that we try all possible positions
+                    // and don't overshoot.
+                    spanLength = spanOne(spanSet, s, pos, rest);
+                    if (spanLength > 0) {
+                        if (spanLength == rest) {
+                            return length; // Reached the end of the string.
+                        }
+                        // Match strings after this code point.
+                        // There cannot be any increments below it because UnicodeSet strings
+                        // contain multiple code points.
+                        pos += spanLength;
+                        rest -= spanLength;
+                        offsets.shift(spanLength);
+                        spanLength = 0;
+                        continue; // Match strings from after a single code point.
+                    }
+                    // Match strings from after the next string match.
+                }
+            }
+            int minOffset = offsets.popMinimum(null);
+            pos += minOffset;
+            rest -= minOffset;
+            spanLength = 0; // Match strings from after a string match.
+        }
+    }
+
+    /**
+     * Spans a string and counts the smallest number of set elements on any path across the span.
+     *
+     * <p>For proper counting, we cannot ignore strings that are fully contained in code point spans.
+     *
+     * <p>If the set does not have any fully-contained strings, then we could optimize this
+     * like span(), but such sets are likely rare, and this is at least still linear.
+     *
+     * @param s The string to be spanned
+     * @param start The start index that the span begins
+     * @param spanCondition The span condition
+     * @param outCount The count
+     * @return the limit (exclusive end) of the span
+     */
+    public int spanAndCount(CharSequence s, int start, SpanCondition spanCondition,
+            OutputInt outCount) {
+        if (spanCondition == SpanCondition.NOT_CONTAINED) {
+            return spanNot(s, start, outCount);
+        }
+        // Consider strings; they may overlap with the span,
+        // and they may result in a smaller count that with just code points.
+        if (spanCondition == SpanCondition.CONTAINED) {
+            return spanContainedAndCount(s, start, outCount);
+        }
+        // SIMPLE (not synchronized, does not use offsets)
+        int stringsLength = strings.size();
+        int length = s.length();
+        int pos = start;
+        int rest = length - start;
+        int count = 0;
+        while (rest != 0) {
+            // Try to match the next code point.
+            int cpLength = spanOne(spanSet, s, pos, rest);
+            int maxInc = (cpLength > 0) ? cpLength : 0;
+            // Try to match all of the strings.
+            for (int i = 0; i < stringsLength; ++i) {
+                String string = strings.get(i);
+                int length16 = string.length();
+                if (maxInc < length16 && length16 <= rest &&
+                        matches16CPB(s, pos, length, string, length16)) {
+                    maxInc = length16;
+                }
+            }
+            // We are done if there is no match beyond pos.
+            if (maxInc == 0) {
+                outCount.value = count;
+                return pos;
+            }
+            // Continue from the longest match.
+            ++count;
+            pos += maxInc;
+            rest -= maxInc;
+        }
+        outCount.value = count;
+        return pos;
+    }
+
+    private synchronized int spanContainedAndCount(CharSequence s, int start, OutputInt outCount) {
+        // Use offset list to try all possibilities.
+        offsets.setMaxLength(maxLength16);
+        int stringsLength = strings.size();
+        int length = s.length();
+        int pos = start;
+        int rest = length - start;
+        int count = 0;
+        while (rest != 0) {
+            // Try to match the next code point.
+            int cpLength = spanOne(spanSet, s, pos, rest);
+            if (cpLength > 0) {
+                offsets.addOffsetAndCount(cpLength, count + 1);
+            }
+            // Try to match all of the strings.
+            for (int i = 0; i < stringsLength; ++i) {
+                String string = strings.get(i);
+                int length16 = string.length();
+                // Note: If the strings were sorted by length, then we could also
+                // avoid trying to match if there is already a match of the same length.
+                if (length16 <= rest && !offsets.hasCountAtOffset(length16, count + 1) &&
+                        matches16CPB(s, pos, length, string, length16)) {
+                    offsets.addOffsetAndCount(length16, count + 1);
+                }
+            }
+            // We are done if there is no match beyond pos.
+            if (offsets.isEmpty()) {
+                outCount.value = count;
+                return pos;
+            }
+            // Continue from the nearest match.
+            int minOffset = offsets.popMinimum(outCount);
+            count = outCount.value;
+            pos += minOffset;
+            rest -= minOffset;
+        }
+        outCount.value = count;
+        return pos;
+    }
+
+    /**
+     * Span a string backwards.
+     *
+     * @param s The string to be spanned
+     * @param spanCondition The span condition
+     * @return The string index which starts the span (i.e. inclusive).
+     */
+    public synchronized int spanBack(CharSequence s, int length, SpanCondition spanCondition) {
+        if (spanCondition == SpanCondition.NOT_CONTAINED) {
+            return spanNotBack(s, length);
+        }
+        int pos = spanSet.spanBack(s, length, SpanCondition.CONTAINED);
+        if (pos == 0) {
+            return 0;
+        }
+        int spanLength = length - pos;
+
+        // Consider strings; they may overlap with the span.
+        int initSize = 0;
+        if (spanCondition == SpanCondition.CONTAINED) {
+            // Use offset list to try all possibilities.
+            initSize = maxLength16;
+        }
+        offsets.setMaxLength(initSize);
+        int i, stringsLength = strings.size();
+        int spanBackLengthsOffset = 0;
+        if (all) {
+            spanBackLengthsOffset = stringsLength;
+        }
+        for (;;) {
+            if (spanCondition == SpanCondition.CONTAINED) {
+                for (i = 0; i < stringsLength; ++i) {
+                    int overlap = spanLengths[spanBackLengthsOffset + i];
+                    if (overlap == ALL_CP_CONTAINED) {
+                        continue; // Irrelevant string.
+                    }
+                    String string = strings.get(i);
+
+                    int length16 = string.length();
+
+                    // Try to match this string at pos-(length16-overlap)..pos-length16.
+                    if (overlap >= LONG_SPAN) {
+                        overlap = length16;
+                        // While contained: No point matching fully inside the code point span.
+                        int len1 = 0;
+                        len1 = string.offsetByCodePoints(0, 1);
+                        overlap -= len1; // Length of the string minus the first code point.
+                    }
+                    if (overlap > spanLength) {
+                        overlap = spanLength;
+                    }
+                    int dec = length16 - overlap; // Keep dec+overlap==length16.
+                    for (;;) {
+                        if (dec > pos) {
+                            break;
+                        }
+                        // Try to match if the decrement is not listed already.
+                        if (!offsets.containsOffset(dec) && matches16CPB(s, pos - dec, length, string, length16)) {
+                            if (dec == pos) {
+                                return 0; // Reached the start of the string.
+                            }
+                            offsets.addOffset(dec);
+                        }
+                        if (overlap == 0) {
+                            break;
+                        }
+                        --overlap;
+                        ++dec;
+                    }
+                }
+            } else /* SIMPLE */{
+                int maxDec = 0, maxOverlap = 0;
+                for (i = 0; i < stringsLength; ++i) {
+                    int overlap = spanLengths[spanBackLengthsOffset + i];
+                    // For longest match, we do need to try to match even an all-contained string
+                    // to find the match from the latest end.
+
+                    String string = strings.get(i);
+
+                    int length16 = string.length();
+
+                    // Try to match this string at pos-(length16-overlap)..pos-length16.
+                    if (overlap >= LONG_SPAN) {
+                        overlap = length16;
+                        // Longest match: Need to match fully inside the code point span
+                        // to find the match from the latest end.
+                    }
+                    if (overlap > spanLength) {
+                      overlap = spanLength;
+                    }
+                    int dec = length16 - overlap; // Keep dec+overlap==length16.
+                    for (;;) {
+                        if (dec > pos || overlap < maxOverlap) {
+                            break;
+                        }
+                        // Try to match if the string is longer or ends later.
+                        if ((overlap > maxOverlap || /* redundant overlap==maxOverlap && */dec > maxDec)
+                                && matches16CPB(s, pos - dec, length, string, length16)) {
+                            maxDec = dec; // Longest match from latest end.
+                            maxOverlap = overlap;
+                            break;
+                        }
+                        --overlap;
+                        ++dec;
+                    }
+                }
+
+                if (maxDec != 0 || maxOverlap != 0) {
+                    // Longest-match algorithm, and there was a string match.
+                    // Simply continue before it.
+                    pos -= maxDec;
+                    if (pos == 0) {
+                        return 0; // Reached the start of the string.
+                    }
+                    spanLength = 0; // Match strings from before a string match.
+                    continue;
+                }
+            }
+            // Finished trying to match all strings at pos.
+
+            if (spanLength != 0 || pos == length) {
+                // The position is before an unlimited code point span (spanLength!=0),
+                // not before a string match.
+                // The only position where spanLength==0 before a span is pos==length.
+                // Otherwise, an unlimited code point span is only tried again when no
+                // strings match, and if such a non-initial span fails we stop.
+                if (offsets.isEmpty()) {
+                    return pos; // No strings matched before a span.
+                }
+                // Match strings from before the next string match.
+            } else {
+                // The position is before a string match (or a single code point).
+                if (offsets.isEmpty()) {
+                    // No more strings matched before a previous string match.
+                    // Try another code point span from before the last string match.
+                    int oldPos = pos;
+                    pos = spanSet.spanBack(s, oldPos, SpanCondition.CONTAINED);
+                    spanLength = oldPos - pos;
+                    if (pos == 0 || // Reached the start of the string, or
+                            spanLength == 0 // neither strings nor span progressed.
+                    ) {
+                        return pos;
+                    }
+                    continue; // spanLength>0: Match strings from before a span.
+                } else {
+                    // Try to match only one code point from before a string match if some
+                    // string matched beyond it, so that we try all possible positions
+                    // and don't overshoot.
+                    spanLength = spanOneBack(spanSet, s, pos);
+                    if (spanLength > 0) {
+                        if (spanLength == pos) {
+                            return 0; // Reached the start of the string.
+                        }
+                        // Match strings before this code point.
+                        // There cannot be any decrements below it because UnicodeSet strings
+                        // contain multiple code points.
+                        pos -= spanLength;
+                        offsets.shift(spanLength);
+                        spanLength = 0;
+                        continue; // Match strings from before a single code point.
+                    }
+                    // Match strings from before the next string match.
+                }
+            }
+            pos -= offsets.popMinimum(null);
+            spanLength = 0; // Match strings from before a string match.
+        }
+    }
+
+    /**
+     * Algorithm for spanNot()==span(SpanCondition.NOT_CONTAINED)
+     *
+     * Theoretical algorithm:
+     * - Iterate through the string, and at each code point boundary:
+     *   + If the code point there is in the set, then return with the current position.
+     *   + If a set string matches at the current position, then return with the current position.
+     *
+     * Optimized implementation:
+     *
+     * (Same assumption as for span() above.)
+     *
+     * Create and cache a spanNotSet which contains
+     * all of the single code points of the original set but none of its strings.
+     * For each set string add its initial code point to the spanNotSet.
+     * (Also add its final code point for spanNotBack().)
+     *
+     * - Loop:
+     *   + Do spanLength=spanNotSet.span(SpanCondition.NOT_CONTAINED).
+     *   + If the current code point is in the original set, then return the current position.
+     *   + If any set string matches at the current position, then return the current position.
+     *   + If there is no match at the current position, neither for the code point
+     *     there nor for any set string, then skip this code point and continue the loop.
+     *     This happens for set-string-initial code points that were added to spanNotSet
+     *     when there is not actually a match for such a set string.
+     *
+     * @param s The string to be spanned
+     * @param start The start index that the span begins
+     * @param outCount If not null: Receives the number of code points across the span.
+     * @return the limit (exclusive end) of the span
+     */
+    private int spanNot(CharSequence s, int start, OutputInt outCount) {
+        int length = s.length();
+        int pos = start, rest = length - start;
+        int stringsLength = strings.size();
+        int count = 0;
+        do {
+            // Span until we find a code point from the set,
+            // or a code point that starts or ends some string.
+            int spanLimit;
+            if (outCount == null) {
+                spanLimit = spanNotSet.span(s, pos, SpanCondition.NOT_CONTAINED);
+            } else {
+                spanLimit = spanNotSet.spanAndCount(s, pos, SpanCondition.NOT_CONTAINED, outCount);
+                outCount.value = count = count + outCount.value;
+            }
+            if (spanLimit == length) {
+                return length; // Reached the end of the string.
+            }
+            pos = spanLimit;
+            rest = length - spanLimit;
+
+            // Check whether the current code point is in the original set,
+            // without the string starts and ends.
+            int cpLength = spanOne(spanSet, s, pos, rest);
+            if (cpLength > 0) {
+                return pos; // There is a set element at pos.
+            }
+
+            // Try to match the strings at pos.
+            for (int i = 0; i < stringsLength; ++i) {
+                if (spanLengths[i] == ALL_CP_CONTAINED) {
+                    continue; // Irrelevant string.
+                }
+                String string = strings.get(i);
+
+                int length16 = string.length();
+                if (length16 <= rest && matches16CPB(s, pos, length, string, length16)) {
+                    return pos; // There is a set element at pos.
+                }
+            }
+
+            // The span(while not contained) ended on a string start/end which is
+            // not in the original set. Skip this code point and continue.
+            // cpLength<0
+            pos -= cpLength;
+            rest += cpLength;
+            ++count;
+        } while (rest != 0);
+        if (outCount != null) {
+            outCount.value = count;
+        }
+        return length; // Reached the end of the string.
+    }
+
+    private int spanNotBack(CharSequence s, int length) {
+        int pos = length;
+        int i, stringsLength = strings.size();
+        do {
+            // Span until we find a code point from the set,
+            // or a code point that starts or ends some string.
+            pos = spanNotSet.spanBack(s, pos, SpanCondition.NOT_CONTAINED);
+            if (pos == 0) {
+                return 0; // Reached the start of the string.
+            }
+
+            // Check whether the current code point is in the original set,
+            // without the string starts and ends.
+            int cpLength = spanOneBack(spanSet, s, pos);
+            if (cpLength > 0) {
+                return pos; // There is a set element at pos.
+            }
+
+            // Try to match the strings at pos.
+            for (i = 0; i < stringsLength; ++i) {
+                // Use spanLengths rather than a spanLengths pointer because
+                // it is easier and we only need to know whether the string is irrelevant
+                // which is the same in either array.
+                if (spanLengths[i] == ALL_CP_CONTAINED) {
+                    continue; // Irrelevant string.
+                }
+                String string = strings.get(i);
+
+                int length16 = string.length();
+                if (length16 <= pos && matches16CPB(s, pos - length16, length, string, length16)) {
+                    return pos; // There is a set element at pos.
+                }
+            }
+
+            // The span(while not contained) ended on a string start/end which is
+            // not in the original set. Skip this code point and continue.
+            // cpLength<0
+            pos += cpLength;
+        } while (pos != 0);
+        return 0; // Reached the start of the string.
+    }
+
+    static short makeSpanLengthByte(int spanLength) {
+        // 0xfe==UnicodeSetStringSpan::LONG_SPAN
+        return spanLength < LONG_SPAN ? (short) spanLength : LONG_SPAN;
+    }
+
+    // Compare strings without any argument checks. Requires length>0.
+    private static boolean matches16(CharSequence s, int start, final String t, int length) {
+        int end = start + length;
+        while (length-- > 0) {
+            if (s.charAt(--end) != t.charAt(length)) {
+                return false;
+            }
+        }
+        return true;
+    }
+
+    /**
+     * Compare 16-bit Unicode strings (which may be malformed UTF-16)
+     * at code point boundaries.
+     * That is, each edge of a match must not be in the middle of a surrogate pair.
+     * @param s       The string to match in.
+     * @param start   The start index of s.
+     * @param limit   The limit of the subsequence of s being spanned.
+     * @param t       The substring to be matched in s.
+     * @param tlength The length of t.
+     */
+    static boolean matches16CPB(CharSequence s, int start, int limit, final String t, int tlength) {
+        return matches16(s, start, t, tlength)
+                && !(0 < start && Character.isHighSurrogate(s.charAt(start - 1)) &&
+                        Character.isLowSurrogate(s.charAt(start)))
+                && !((start + tlength) < limit && Character.isHighSurrogate(s.charAt(start + tlength - 1)) &&
+                        Character.isLowSurrogate(s.charAt(start + tlength)));
+    }
+
+    /**
+     * Does the set contain the next code point?
+     * If so, return its length; otherwise return its negative length.
+     */
+    static int spanOne(final UnicodeSet set, CharSequence s, int start, int length) {
+        char c = s.charAt(start);
+        if (c >= 0xd800 && c <= 0xdbff && length >= 2) {
+            char c2 = s.charAt(start + 1);
+            if (UTF16.isTrailSurrogate(c2)) {
+                int supplementary = UCharacterProperty.getRawSupplementary(c, c2);
+                return set.contains(supplementary) ? 2 : -2;
+            }
+        }
+        return set.contains(c) ? 1 : -1;
+    }
+
+    static int spanOneBack(final UnicodeSet set, CharSequence s, int length) {
+        char c = s.charAt(length - 1);
+        if (c >= 0xdc00 && c <= 0xdfff && length >= 2) {
+            char c2 = s.charAt(length - 2);
+            if (UTF16.isLeadSurrogate(c2)) {
+                int supplementary = UCharacterProperty.getRawSupplementary(c2, c);
+                return set.contains(supplementary) ? 2 : -2;
+            }
+        }
+        return set.contains(c) ? 1 : -1;
+    }
+
+    /**
+     * Helper class for UnicodeSetStringSpan.
+     *
+     * <p>List of offsets from the current position from where to try matching
+     * a code point or a string.
+     * Stores offsets rather than indexes to simplify the code and use the same list
+     * for both increments (in span()) and decrements (in spanBack()).
+     *
+     * <p>Assumption: The maximum offset is limited, and the offsets that are stored at any one time
+     * are relatively dense, that is,
+     * there are normally no gaps of hundreds or thousands of offset values.
+     *
+     * <p>This class optionally also tracks the minimum non-negative count for each position,
+     * intended to count the smallest number of elements of any path leading to that position.
+     *
+     * <p>The implementation uses a circular buffer of count integers,
+     * each indicating whether the corresponding offset is in the list,
+     * and its path element count.
+     * This avoids inserting into a sorted list of offsets (or absolute indexes)
+     * and physically moving part of the list.
+     *
+     * <p>Note: In principle, the caller should setMaxLength() to
+     * the maximum of the max string length and U16_LENGTH/U8_LENGTH
+     * to account for "long" single code points.
+     *
+     * <p>Note: An earlier version did not track counts and stored only byte flags.
+     * With boolean flags, if maxLength were guaranteed to be no more than 32 or 64,
+     * the list could be stored as bit flags in a single integer.
+     * Rather than handling a circular buffer with a start list index,
+     * the integer would simply be shifted when lower offsets are removed.
+     * UnicodeSet does not have a limit on the lengths of strings.
+     */
+    private static final class OffsetList {
+        private int[] list;
+        private int length;
+        private int start;
+
+        public OffsetList() {
+            list = new int[16];  // default size
+        }
+
+        public void setMaxLength(int maxLength) {
+            if (maxLength > list.length) {
+                list = new int[maxLength];
+            }
+            clear();
+        }
+
+        public void clear() {
+            for (int i = list.length; i-- > 0;) {
+                list[i] = 0;
+            }
+            start = length = 0;
+        }
+
+        public boolean isEmpty() {
+            return (length == 0);
+        }
+
+        /**
+         * Reduces all stored offsets by delta, used when the current position moves by delta.
+         * There must not be any offsets lower than delta.
+         * If there is an offset equal to delta, it is removed.
+         *
+         * @param delta [1..maxLength]
+         */
+        public void shift(int delta) {
+            int i = start + delta;
+            if (i >= list.length) {
+                i -= list.length;
+            }
+            if (list[i] != 0) {
+                list[i] = 0;
+                --length;
+            }
+            start = i;
+        }
+
+        /**
+         * Adds an offset. The list must not contain it yet.
+         * @param offset [1..maxLength]
+         */
+        public void addOffset(int offset) {
+            int i = start + offset;
+            if (i >= list.length) {
+                i -= list.length;
+            }
+            assert list[i] == 0;
+            list[i] = 1;
+            ++length;
+        }
+
+        /**
+         * Adds an offset and updates its count.
+         * The list may already contain the offset.
+         * @param offset [1..maxLength]
+         */
+        public void addOffsetAndCount(int offset, int count) {
+            assert count > 0;
+            int i = start + offset;
+            if (i >= list.length) {
+                i -= list.length;
+            }
+            if (list[i] == 0) {
+                list[i] = count;
+                ++length;
+            } else if (count < list[i]) {
+                list[i] = count;
+            }
+        }
+
+        /**
+         * @param offset [1..maxLength]
+         */
+        public boolean containsOffset(int offset) {
+            int i = start + offset;
+            if (i >= list.length) {
+                i -= list.length;
+            }
+            return list[i] != 0;
+        }
+
+        /**
+         * @param offset [1..maxLength]
+         */
+        public boolean hasCountAtOffset(int offset, int count) {
+            int i = start + offset;
+            if (i >= list.length) {
+                i -= list.length;
+            }
+            int oldCount = list[i];
+            return oldCount != 0 && oldCount <= count;
+        }
+
+        /**
+         * Finds the lowest stored offset from a non-empty list, removes it,
+         * and reduces all other offsets by this minimum.
+         * @return min=[1..maxLength]
+         */
+        public int popMinimum(OutputInt outCount) {
+            // Look for the next offset in list[start+1..list.length-1].
+            int i = start, result;
+            while (++i < list.length) {
+                int count = list[i];
+                if (count != 0) {
+                    list[i] = 0;
+                    --length;
+                    result = i - start;
+                    start = i;
+                    if (outCount != null) { outCount.value = count; }
+                    return result;
+                }
+            }
+            // i==list.length
+
+            // Wrap around and look for the next offset in list[0..start].
+            // Since the list is not empty, there will be one.
+            result = list.length - start;
+            i = 0;
+            int count;
+            while ((count = list[i]) == 0) {
+                ++i;
+            }
+            list[i] = 0;
+            --length;
+            start = i;
+            if (outCount != null) { outCount.value = count; }
+            return result + i;
+        }
+    }
+}
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/Utility.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/Utility.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2009, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -24,47 +24,26 @@
  */
 /*
  *******************************************************************************
- * (C) Copyright IBM Corp. and others, 1996-2009 - All Rights Reserved         *
- *                                                                             *
- * The original version of this source code and documentation is copyrighted   *
- * and owned by IBM, These materials are provided under terms of a License     *
- * Agreement between IBM and Sun. This technology is protected by multiple     *
- * US and International patents. This notice and attribution to IBM may not    *
- * to removed.                                                                 *
+ * Copyright (C) 1996-2011, International Business Machines Corporation and    *
+ * others. All Rights Reserved.                                                *
  *******************************************************************************
  */
 
 package sun.text.normalizer;
 
-public final class Utility {
+import java.io.IOException;
+import java.util.Locale;
 
-    /**
-     * Convenience utility to compare two Object[]s
-     * Ought to be in System.
-     * @param len the length to compare.
-     * The start indices and start+len must be valid.
-     */
-    public final static boolean arrayRegionMatches(char[] source, int sourceStart,
-                                            char[] target, int targetStart,
-                                            int len)
-    {
-        int sourceEnd = sourceStart + len;
-        int delta = targetStart - sourceStart;
-        for (int i = sourceStart; i < sourceEnd; i++) {
-            if (source[i]!=target[i + delta])
-            return false;
-        }
-        return true;
-    }
+final class Utility {
 
     /**
      * Convert characters outside the range U+0020 to U+007F to
      * Unicode escapes, and convert backslash to a double backslash.
      */
     public static final String escape(String s) {
-        StringBuffer buf = new StringBuffer();
+        StringBuilder buf = new StringBuilder();
         for (int i=0; i<s.length(); ) {
-            int c = UTF16.charAt(s, i);
+            int c = Character.codePointAt(s, i);
             i += UTF16.getCharCount(c);
             if (c >= ' ' && c <= 0x007F) {
                 if (c == '\\') {
@@ -75,7 +54,7 @@
             } else {
                 boolean four = c <= 0xFFFF;
                 buf.append(four ? "\\u" : "\\U");
-                hex(c, four ? 4 : 8, buf);
+                buf.append(hex(c, four ? 4 : 8));
             }
         }
         return buf.toString();
@@ -124,7 +103,7 @@
         }
 
         /* Fetch first UChar after '\\' */
-        c = UTF16.charAt(s, offset);
+        c = Character.codePointAt(s, offset);
         offset += UTF16.getCharCount(c);
 
         /* Convert hexadecimal and octal escapes */
@@ -143,7 +122,7 @@
                 maxDig = 8;
             } else {
                 maxDig = 2;
-            }
+          }
             break;
         default:
             dig = UCharacter.digit(c, 8);
@@ -175,7 +154,7 @@
                     return -1;
                 }
                 ++offset;
-            }
+          }
             if (result < 0 || result >= 0x110000) {
                 return -1;
             }
@@ -184,7 +163,7 @@
             // escape or as a literal.  If so, join them up into a
             // supplementary.
             if (offset < length &&
-                UTF16.isLeadSurrogate((char) result)) {
+                    UTF16.isLeadSurrogate((char) result)) {
                 int ahead = offset+1;
                 c = s.charAt(offset); // [sic] get 16-bit code unit
                 if (c == '\\' && ahead < length) {
@@ -194,8 +173,8 @@
                 }
                 if (UTF16.isTrailSurrogate((char) c)) {
                     offset = ahead;
-                result = UCharacterProperty.getRawSupplementary(
-                                  (char) result, (char) c);
+                    result = UCharacterProperty.getRawSupplementary(
+                            (char) result, (char) c);
                 }
             }
             offset16[0] = offset;
@@ -226,39 +205,22 @@
     }
 
     /**
-     * Convert a integer to size width hex uppercase digits.
-     * E.g., {@code hex('a', 4, str) => "0041"}.
-     * Append the output to the given StringBuffer.
-     * If width is too small to fit, nothing will be appended to output.
-     */
-    public static StringBuffer hex(int ch, int width, StringBuffer output) {
-        return appendNumber(output, ch, 16, width);
-    }
-
-    /**
-     * Convert a integer to size width (minimum) hex uppercase digits.
-     * E.g., {@code hex('a', 4, str) => "0041"}.  If the integer requires more
-     * than width digits, more will be used.
+     * Supplies a zero-padded hex representation of an integer (without 0x)
      */
-    public static String hex(int ch, int width) {
-        StringBuffer buf = new StringBuffer();
-        return appendNumber(buf, ch, 16, width).toString();
-    }
-
-    /**
-     * Skip over a sequence of zero or more white space characters
-     * at pos.  Return the index of the first non-white-space character
-     * at or after pos, or str.length(), if there is none.
-     */
-    public static int skipWhitespace(String str, int pos) {
-        while (pos < str.length()) {
-            int c = UTF16.charAt(str, pos);
-            if (!UCharacterProperty.isRuleWhiteSpace(c)) {
-                break;
-            }
-            pos += UTF16.getCharCount(c);
+    static public String hex(long i, int places) {
+        if (i == Long.MIN_VALUE) return "-8000000000000000";
+        boolean negative = i < 0;
+        if (negative) {
+            i = -i;
         }
-        return pos;
+        String result = Long.toString(i, 16).toUpperCase(Locale.ENGLISH);
+        if (result.length() < places) {
+            result = "0000000000000000".substring(result.length(),places) + result;
+        }
+        if (negative) {
+            return '-' + result;
+        }
+        return result;
     }
 
     static final char DIGITS[] = {
@@ -269,117 +231,43 @@
     };
 
     /**
-     * Append the digits of a positive integer to the given
-     * <code>StringBuffer</code> in the given radix. This is
-     * done recursively since it is easiest to generate the low-
-     * order digit first, but it must be appended last.
-     *
-     * @param result is the <code>StringBuffer</code> to append to
-     * @param n is the positive integer
-     * @param radix is the radix, from 2 to 36 inclusive
-     * @param minDigits is the minimum number of digits to append.
-     */
-    private static void recursiveAppendNumber(StringBuffer result, int n,
-                                                int radix, int minDigits)
-    {
-        int digit = n % radix;
-
-        if (n >= radix || minDigits > 1) {
-            recursiveAppendNumber(result, n / radix, radix, minDigits - 1);
-        }
-
-        result.append(DIGITS[digit]);
-    }
-
-    /**
-     * Append a number to the given StringBuffer in the given radix.
-     * Standard digits '0'-'9' are used and letters 'A'-'Z' for
-     * radices 11 through 36.
-     * @param result the digits of the number are appended here
-     * @param n the number to be converted to digits; may be negative.
-     * If negative, a '-' is prepended to the digits.
-     * @param radix a radix from 2 to 36 inclusive.
-     * @param minDigits the minimum number of digits, not including
-     * any '-', to produce.  Values less than 2 have no effect.  One
-     * digit is always emitted regardless of this parameter.
-     * @return a reference to result
-     */
-    public static StringBuffer appendNumber(StringBuffer result, int n,
-                                             int radix, int minDigits)
-        throws IllegalArgumentException
-    {
-        if (radix < 2 || radix > 36) {
-            throw new IllegalArgumentException("Illegal radix " + radix);
-        }
-
-
-        int abs = n;
-
-        if (n < 0) {
-            abs = -n;
-            result.append("-");
-        }
-
-        recursiveAppendNumber(result, abs, radix, minDigits);
-
-        return result;
-    }
-
-    /**
      * Return true if the character is NOT printable ASCII.  The tab,
      * newline and linefeed characters are considered unprintable.
      */
     public static boolean isUnprintable(int c) {
+        //0x20 = 32 and 0x7E = 126
         return !(c >= 0x20 && c <= 0x7E);
     }
 
     /**
-     * Escape unprintable characters using {@code <backslash>uxxxx} notation
-     * for U+0000 to U+FFFF and {@code <backslash>Uxxxxxxxx} for U+10000 and
+     * Escape unprintable characters using <backslash>uxxxx notation
+     * for U+0000 to U+FFFF and <backslash>Uxxxxxxxx for U+10000 and
      * above.  If the character is printable ASCII, then do nothing
      * and return FALSE.  Otherwise, append the escaped notation and
      * return TRUE.
      */
-    public static boolean escapeUnprintable(StringBuffer result, int c) {
-        if (isUnprintable(c)) {
-            result.append('\\');
-            if ((c & ~0xFFFF) != 0) {
-                result.append('U');
-                result.append(DIGITS[0xF&(c>>28)]);
-                result.append(DIGITS[0xF&(c>>24)]);
-                result.append(DIGITS[0xF&(c>>20)]);
-                result.append(DIGITS[0xF&(c>>16)]);
-            } else {
-                result.append('u');
+    public static <T extends Appendable> boolean escapeUnprintable(T result, int c) {
+        try {
+            if (isUnprintable(c)) {
+                result.append('\\');
+                if ((c & ~0xFFFF) != 0) {
+                    result.append('U');
+                    result.append(DIGITS[0xF&(c>>28)]);
+                    result.append(DIGITS[0xF&(c>>24)]);
+                    result.append(DIGITS[0xF&(c>>20)]);
+                    result.append(DIGITS[0xF&(c>>16)]);
+                } else {
+                    result.append('u');
+                }
+                result.append(DIGITS[0xF&(c>>12)]);
+                result.append(DIGITS[0xF&(c>>8)]);
+                result.append(DIGITS[0xF&(c>>4)]);
+                result.append(DIGITS[0xF&c]);
+                return true;
             }
-            result.append(DIGITS[0xF&(c>>12)]);
-            result.append(DIGITS[0xF&(c>>8)]);
-            result.append(DIGITS[0xF&(c>>4)]);
-            result.append(DIGITS[0xF&c]);
-            return true;
+            return false;
+        } catch (IOException e) {
+            throw new IllegalArgumentException(e);
         }
-        return false;
     }
-
-    /**
-    * Similar to StringBuffer.getChars, version 1.3.
-    * Since JDK 1.2 implements StringBuffer.getChars differently, this method
-    * is here to provide consistent results.
-    * To be removed after JDK 1.2 ceased to be the reference platform.
-    * @param src source string buffer
-    * @param srcBegin offset to the start of the src to retrieve from
-    * @param srcEnd offset to the end of the src to retrieve from
-    * @param dst char array to store the retrieved chars
-    * @param dstBegin offset to the start of the destination char array to
-    *                 store the retrieved chars
-    */
-    public static void getChars(StringBuffer src, int srcBegin, int srcEnd,
-                                char dst[], int dstBegin)
-    {
-        if (srcBegin == srcEnd) {
-            return;
-        }
-        src.getChars(srcBegin, srcEnd, dst, dstBegin);
-    }
-
 }
Binary file jdk/src/java.base/share/classes/sun/text/resources/nfc.icu has changed
Binary file jdk/src/java.base/share/classes/sun/text/resources/nfkc.icu has changed
Binary file jdk/src/java.base/share/classes/sun/text/resources/nfkc_cf.icu has changed
Binary file jdk/src/java.base/share/classes/sun/text/resources/ubidi.icu has changed
Binary file jdk/src/java.base/share/classes/sun/text/resources/unorm.icu has changed
Binary file jdk/src/java.base/share/classes/sun/text/resources/uprops.icu has changed
--- a/jdk/src/java.base/share/conf/security/java.security	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/conf/security/java.security	Wed Jul 05 20:42:36 2017 +0200
@@ -541,4 +541,61 @@
 #
 # Example:
 #   jdk.tls.disabledAlgorithms=MD5, SSLv3, DSA, RSA keySize < 2048
-jdk.tls.disabledAlgorithms=SSLv3, RC4
+jdk.tls.disabledAlgorithms=SSLv3, RC4, DH keySize < 768
+
+# Legacy algorithms for Secure Socket Layer/Transport Layer Security (SSL/TLS)
+# processing in JSSE implementation.
+#
+# In some environments, a certain algorithm may be undesirable but it
+# cannot be disabled because of its use in legacy applications.  Legacy
+# algorithms may still be supported, but applications should not use them
+# as the security strength of legacy algorithms are usually not strong enough
+# in practice.
+#
+# During SSL/TLS security parameters negotiation, legacy algorithms will
+# not be negotiated unless there are no other candidates.
+#
+# The syntax of the disabled algorithm string is described as this Java
+# BNF-style:
+#   LegacyAlgorithms:
+#       " LegacyAlgorithm { , LegacyAlgorithm } "
+#
+#   LegacyAlgorithm:
+#       AlgorithmName (standard JSSE algorithm name)
+#
+# See the specification of security property "jdk.certpath.disabledAlgorithms"
+# for the syntax and description of the "AlgorithmName" notation.
+#
+# Per SSL/TLS specifications, cipher suites have the form:
+#       SSL_KeyExchangeAlg_WITH_CipherAlg_MacAlg
+# or
+#       TLS_KeyExchangeAlg_WITH_CipherAlg_MacAlg
+#
+# For example, the cipher suite TLS_RSA_WITH_AES_128_CBC_SHA uses RSA as the
+# key exchange algorithm, AES_128_CBC (128 bits AES cipher algorithm in CBC
+# mode) as the cipher (encryption) algorithm, and SHA-1 as the message digest
+# algorithm for HMAC.
+#
+# The LegacyAlgorithm can be one of the following standard algorithm names:
+#     1. JSSE cipher suite name, e.g., TLS_RSA_WITH_AES_128_CBC_SHA
+#     2. JSSE key exchange algorithm name, e.g., RSA
+#     3. JSSE cipher (encryption) algorithm name, e.g., AES_128_CBC
+#     4. JSSE message digest algorithm name, e.g., SHA
+#
+# See SSL/TLS specifications and "Java Cryptography Architecture Standard
+# Algorithm Name Documentation" for information about the algorithm names.
+#
+# Note: This property is currently used by Oracle's JSSE implementation.
+# It is not guaranteed to be examined and used by other implementations.
+# There is no guarantee the property will continue to exist or be of the
+# same syntax in future releases.
+#
+# Example:
+#   jdk.tls.legacyAlgorithms=DH_anon, DES_CBC, SSL_RSA_WITH_RC4_128_MD5
+#
+jdk.tls.legacyAlgorithms= \
+        K_NULL, C_NULL, M_NULL, \
+        DHE_DSS_EXPORT, DHE_RSA_EXPORT, DH_anon_EXPORT, DH_DSS_EXPORT, \
+        DH_RSA_EXPORT, RSA_EXPORT, \
+        DH_anon, ECDH_anon, \
+        RC4_128, RC4_40, DES_CBC, DES40_CBC
--- a/jdk/src/java.base/share/native/include/jvm.h	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/native/include/jvm.h	Wed Jul 05 20:42:36 2017 +0200
@@ -557,6 +557,48 @@
 JVM_SupportsCX8(void);
 
 /*
+ * jdk.internal.jimage
+ */
+
+JNIEXPORT jlong JNICALL
+JVM_ImageOpen(JNIEnv *env, const char *nativePath, jboolean big_endian);
+
+JNIEXPORT void JNICALL
+JVM_ImageClose(JNIEnv *env, jlong id);
+
+JNIEXPORT jlong JNICALL
+JVM_ImageGetIndexAddress(JNIEnv *env, jlong id);
+
+JNIEXPORT jlong JNICALL
+JVM_ImageGetDataAddress(JNIEnv *env,jlong id);
+
+JNIEXPORT jboolean JNICALL
+JVM_ImageRead(JNIEnv *env, jlong id, jlong offset,
+            unsigned char* uncompressedAddress, jlong uncompressed_size);
+
+JNIEXPORT jboolean JNICALL
+JVM_ImageReadCompressed(JNIEnv *env, jlong id, jlong offset,
+            unsigned char* compressedBuffer, jlong compressed_size,
+            unsigned char* uncompressedBuffer, jlong uncompressed_size);
+
+JNIEXPORT const char* JNICALL
+JVM_ImageGetStringBytes(JNIEnv *env, jlong id, jint offset);
+
+JNIEXPORT jlong* JNICALL
+JVM_ImageGetAttributes(JNIEnv *env, jlong* rawAttributes, jlong id, jint offset);
+
+JNIEXPORT jsize JNICALL
+JVM_ImageGetAttributesCount(JNIEnv *env);
+
+JNIEXPORT jlong* JNICALL
+JVM_ImageFindAttributes(JNIEnv *env, jlong* rawAttributes, jbyte* rawBytes, jsize size, jlong id);
+
+JNIEXPORT jint* JNICALL
+JVM_ImageAttributeOffsets(JNIEnv *env, jint* rawOffsets, unsigned int length, jlong id);
+
+JNIEXPORT unsigned int JNICALL
+JVM_ImageAttributeOffsetsLength(JNIEnv *env, jlong id);
+/*
  * com.sun.dtrace.jsdt support
  */
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.base/share/native/libjava/Image.c	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,177 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+#include <string.h>
+
+#include "jni.h"
+#include "jvm.h"
+#include "jdk_internal_jimage_ImageNativeSubstrate.h"
+
+JNIEXPORT jlong JNICALL
+Java_jdk_internal_jimage_ImageNativeSubstrate_openImage(JNIEnv *env,
+        jclass cls, jstring path, jboolean big_endian) {
+    const char *nativePath;
+    jlong ret;
+
+    nativePath = (*env)->GetStringUTFChars(env, path, NULL);
+    ret = JVM_ImageOpen(env, nativePath, big_endian);
+    (*env)->ReleaseStringUTFChars(env, path, nativePath);
+    return ret;
+}
+
+JNIEXPORT void JNICALL
+Java_jdk_internal_jimage_ImageNativeSubstrate_closeImage(JNIEnv *env,
+                                        jclass cls, jlong id) {
+    JVM_ImageClose(env, id);
+}
+
+JNIEXPORT jlong JNICALL
+Java_jdk_internal_jimage_ImageNativeSubstrate_getIndexAddress(JNIEnv *env,
+                jclass cls, jlong id) {
+ return JVM_ImageGetIndexAddress(env, id);
+}
+
+JNIEXPORT jlong JNICALL
+Java_jdk_internal_jimage_ImageNativeSubstrate_getDataAddress(JNIEnv *env,
+                jclass cls, jlong id) {
+ return JVM_ImageGetDataAddress(env, id);
+}
+
+JNIEXPORT jboolean JNICALL
+Java_jdk_internal_jimage_ImageNativeSubstrate_read(JNIEnv *env,
+                                        jclass cls, jlong id, jlong offset,
+        jobject uncompressedBuffer, jlong uncompressed_size) {
+    unsigned char* uncompressedAddress;
+
+    uncompressedAddress = (unsigned char*) (*env)->GetDirectBufferAddress(env, uncompressedBuffer);
+    if (uncompressedBuffer == NULL) {
+      return JNI_FALSE;
+    }
+    return JVM_ImageRead(env, id, offset, uncompressedAddress, uncompressed_size);
+}
+
+JNIEXPORT jboolean JNICALL
+Java_jdk_internal_jimage_ImageNativeSubstrate_readCompressed(JNIEnv *env,
+                                        jclass cls, jlong id, jlong offset,
+                                        jobject compressedBuffer, jlong compressed_size,
+        jobject uncompressedBuffer, jlong uncompressed_size) {
+    // Get address of read direct buffer.
+    unsigned char* compressedAddress;
+    unsigned char* uncompressedAddress;
+
+    compressedAddress = (unsigned char*) (*env)->GetDirectBufferAddress(env, compressedBuffer);
+    // Get address of decompression direct buffer.
+    uncompressedAddress = (unsigned char*) (*env)->GetDirectBufferAddress(env, uncompressedBuffer);
+    if (uncompressedBuffer == NULL || compressedBuffer == NULL) {
+      return JNI_FALSE;
+    }
+    return JVM_ImageReadCompressed(env, id, offset, compressedAddress, compressed_size,
+            uncompressedAddress, uncompressed_size);
+}
+
+JNIEXPORT jbyteArray JNICALL
+Java_jdk_internal_jimage_ImageNativeSubstrate_getStringBytes(JNIEnv *env,
+                                        jclass cls, jlong id, jint offset) {
+    const char* data;
+    size_t size;
+    jbyteArray byteArray;
+    jbyte* rawBytes;
+
+    data = JVM_ImageGetStringBytes(env, id, offset);
+    // Determine String length.
+    size = strlen(data);
+    // Allocate byte array.
+    byteArray = (*env)->NewByteArray(env, (jsize) size);
+    // Get array base address.
+    rawBytes = (*env)->GetByteArrayElements(env, byteArray, NULL);
+    // Copy bytes from image string table.
+    memcpy(rawBytes, data, size);
+    // Release byte array base address.
+    (*env)->ReleaseByteArrayElements(env, byteArray, rawBytes, 0);
+    return byteArray;
+}
+
+JNIEXPORT jlongArray JNICALL
+Java_jdk_internal_jimage_ImageNativeSubstrate_getAttributes(JNIEnv *env,
+        jclass cls, jlong id, jint offset) {
+    // Allocate a jlong large enough for all location attributes.
+    jlongArray attributes;
+    jlong* rawAttributes;
+    jlong* ret;
+
+    attributes = (*env)->NewLongArray(env, JVM_ImageGetAttributesCount(env));
+    // Get base address for jlong array.
+    rawAttributes = (*env)->GetLongArrayElements(env, attributes, NULL);
+    ret = JVM_ImageGetAttributes(env, rawAttributes, id, offset);
+    // Release jlong array base address.
+    (*env)->ReleaseLongArrayElements(env, attributes, rawAttributes, 0);
+    return ret == NULL ? NULL : attributes;
+}
+
+JNIEXPORT jlongArray JNICALL
+Java_jdk_internal_jimage_ImageNativeSubstrate_findAttributes(JNIEnv *env,
+        jclass cls, jlong id, jbyteArray utf8) {
+    // Allocate a jlong large enough for all location attributes.
+    jsize count;
+    jlongArray attributes;
+    jlong* rawAttributes;
+    jsize size;
+    jbyte* rawBytes;
+    jlong* ret;
+
+    count = JVM_ImageGetAttributesCount(env);
+    attributes = (*env)->NewLongArray(env, JVM_ImageGetAttributesCount(env));
+    // Get base address for jlong array.
+    rawAttributes = (*env)->GetLongArrayElements(env, attributes, NULL);
+    size = (*env)->GetArrayLength(env, utf8);
+    rawBytes = (*env)->GetByteArrayElements(env, utf8, NULL);
+    ret = JVM_ImageFindAttributes(env, rawAttributes, rawBytes, size, id);
+    (*env)->ReleaseByteArrayElements(env, utf8, rawBytes, 0);
+    // Release jlong array base address.
+    (*env)->ReleaseLongArrayElements(env, attributes, rawAttributes, 0);
+    return ret == NULL ? NULL : attributes;
+
+}
+
+JNIEXPORT jintArray JNICALL
+Java_jdk_internal_jimage_ImageNativeSubstrate_attributeOffsets(JNIEnv *env,
+        jclass cls, jlong id) {
+    unsigned int length;
+    jintArray offsets;
+    jint* rawOffsets;
+    jint* ret;
+
+    length = JVM_ImageAttributeOffsetsLength(env, id);
+    offsets = (*env)->NewIntArray(env, length);
+    // Get base address of result.
+    rawOffsets = (*env)->GetIntArrayElements(env, offsets, NULL);
+    ret = JVM_ImageAttributeOffsets(env, rawOffsets, length, id);
+    if (length == 0) {
+        return NULL;
+    }
+    // Release result base address.
+    (*env)->ReleaseIntArrayElements(env, offsets, rawOffsets, 0);
+    return ret == NULL ? NULL : offsets;
+}
--- a/jdk/src/java.base/share/native/libzip/CRC32.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/share/native/libzip/CRC32.c	Wed Jul 05 20:42:36 2017 +0200
@@ -43,8 +43,8 @@
 }
 
 JNIEXPORT jint JNICALL
-Java_java_util_zip_CRC32_updateBytes(JNIEnv *env, jclass cls, jint crc,
-                                     jarray b, jint off, jint len)
+Java_java_util_zip_CRC32_updateBytes0(JNIEnv *env, jclass cls, jint crc,
+                                         jarray b, jint off, jint len)
 {
     Bytef *buf = (*env)->GetPrimitiveArrayCritical(env, b, 0);
     if (buf) {
@@ -61,8 +61,8 @@
 }
 
 JNIEXPORT jint JNICALL
-Java_java_util_zip_CRC32_updateByteBuffer(JNIEnv *env, jclass cls, jint crc,
-                                          jlong address, jint off, jint len)
+Java_java_util_zip_CRC32_updateByteBuffer0(JNIEnv *env, jclass cls, jint crc,
+                                              jlong address, jint off, jint len)
 {
     Bytef *buf = (Bytef *)jlong_to_ptr(address);
     if (buf) {
--- a/jdk/src/java.base/solaris/native/libjava/ProcessHandleImpl_solaris.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/solaris/native/libjava/ProcessHandleImpl_solaris.c	Wed Jul 05 20:42:36 2017 +0200
@@ -38,6 +38,7 @@
 #include <signal.h>
 #include <stdlib.h>
 #include <sys/stat.h>
+#include <sys/types.h>
 #include <unistd.h>
 #include <limits.h>
 
@@ -55,8 +56,9 @@
 /*
  * Signatures for internal OS specific functions.
  */
-static pid_t parentPid(JNIEnv *env, pid_t pid);
-static void getStatInfo(JNIEnv *env, jobject jinfo, pid_t pid);
+static pid_t getStatInfo(JNIEnv *env, pid_t pid,
+                                     jlong *totalTime, jlong* startTime,
+                                     uid_t *uid);
 static void getCmdlineInfo(JNIEnv *env, jobject jinfo, pid_t pid);
 
 extern jstring uidToUser(JNIEnv* env, uid_t uid);
@@ -86,9 +88,8 @@
  * Method:    initIDs
  * Signature: ()V
  */
-JNIEXPORT void JNICALL Java_java_lang_ProcessHandleImpl_00024Info_initIDs
-  (JNIEnv *env, jclass clazz) {
-
+JNIEXPORT void JNICALL
+Java_java_lang_ProcessHandleImpl_00024Info_initIDs(JNIEnv *env, jclass clazz) {
     CHECK_NULL(ProcessHandleImpl_Info_commandID = (*env)->GetFieldID(env,
         clazz, "command", "Ljava/lang/String;"));
     CHECK_NULL(ProcessHandleImpl_Info_argumentsID = (*env)->GetFieldID(env,
@@ -99,25 +100,68 @@
         clazz, "startTime", "J"));
     CHECK_NULL(ProcessHandleImpl_Info_userID = (*env)->GetFieldID(env,
         clazz, "user", "Ljava/lang/String;"));
+}
+
+/**************************************************************
+ * Static method to initialize the ticks per second rate.
+ *
+ * Class:     java_lang_ProcessHandleImpl
+ * Method:    initNative
+ * Signature: ()V
+ */
+JNIEXPORT void JNICALL
+Java_java_lang_ProcessHandleImpl_initNative(JNIEnv *env, jclass clazz) {
     clock_ticks_per_second = sysconf(_SC_CLK_TCK);
 }
 
 /*
+ * Check if a process is alive.
+ * Return the start time (ms since 1970) if it is available.
+ * If the start time is not available return 0.
+ * If the pid is invalid, return -1.
+ *
+ * Class:     java_lang_ProcessHandleImpl
+ * Method:    isAlive0
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL
+Java_java_lang_ProcessHandleImpl_isAlive0(JNIEnv *env, jobject obj, jlong jpid) {
+    pid_t pid = (pid_t) jpid;
+    jlong startTime = 0L;
+    jlong totalTime = 0L;
+    uid_t uid = -1;
+    pid_t ppid = getStatInfo(env, pid, &totalTime, &startTime, &uid);
+    return (ppid < 0) ? -1 : startTime;
+}
+
+/*
  * Returns the parent pid of the requested pid.
  *
  * Class:     java_lang_ProcessHandleImpl
  * Method:    parent0
  * Signature: (J)J
  */
-JNIEXPORT jlong JNICALL Java_java_lang_ProcessHandleImpl_parent0
-(JNIEnv *env, jobject obj, jlong jpid) {
+JNIEXPORT jlong JNICALL
+Java_java_lang_ProcessHandleImpl_parent0(JNIEnv *env,
+                                         jobject obj,
+                                         jlong jpid,
+                                         jlong startTime) {
     pid_t pid = (pid_t) jpid;
     pid_t ppid = -1;
 
     if (pid == getpid()) {
         ppid = getppid();
     } else {
-        ppid = parentPid(env, pid);
+        jlong start = 0L;
+        jlong total = 0L;
+        uid_t uid = -1;
+
+        pid_t ppid = getStatInfo(env, pid, &total, &start, &uid);
+        if (start != startTime
+            && start != 0
+            && startTime != 0) {
+            ppid = -1;
+        }
     }
     return (jlong) ppid;
 }
@@ -134,18 +178,24 @@
  * The number of pids is returned if they all fit.
  * If the array is too short, the desired length is returned.
  */
-JNIEXPORT jint JNICALL Java_java_lang_ProcessHandleImpl_getProcessPids0
-(JNIEnv *env, jclass clazz, jlong jpid,
-    jlongArray jarray, jlongArray jparentArray)
-{
+JNIEXPORT jint JNICALL
+Java_java_lang_ProcessHandleImpl_getProcessPids0(JNIEnv *env,
+                                                 jclass clazz,
+                                                 jlong jpid,
+                                                 jlongArray jarray,
+                                                 jlongArray jparentArray,
+                                                 jlongArray jstimesArray) {
     DIR* dir;
     struct dirent* ptr;
     pid_t pid = (pid_t) jpid;
-    size_t count = 0;
     jlong* pids = NULL;
     jlong* ppids = NULL;
-    size_t parentArraySize = 0;
-    size_t arraySize = 0;
+    jlong* stimes = NULL;
+    jsize parentArraySize = 0;
+    jsize arraySize = 0;
+    jsize stimesSize = 0;
+    jsize count = 0;
+    char procname[32];
 
     arraySize = (*env)->GetArrayLength(env, jarray);
     JNU_CHECK_EXCEPTION_RETURN(env, 0);
@@ -158,6 +208,15 @@
             return 0;
         }
     }
+    if (jstimesArray != NULL) {
+        stimesSize = (*env)->GetArrayLength(env, jstimesArray);
+        JNU_CHECK_EXCEPTION_RETURN(env, -1);
+
+        if (arraySize != stimesSize) {
+            JNU_ThrowIllegalArgumentException(env, "array sizes not equal");
+            return 0;
+        }
+    }
 
     /*
      * To locate the children we scan /proc looking for files that have a
@@ -180,9 +239,18 @@
                 break;
             }
         }
+        if (jstimesArray != NULL) {
+            stimes  = (*env)->GetLongArrayElements(env, jstimesArray, NULL);
+            if (stimes == NULL) {
+                break;
+            }
+        }
 
         while ((ptr = readdir(dir)) != NULL) {
-            pid_t ppid;
+            pid_t ppid = 0;
+            jlong totalTime = 0L;
+            jlong startTime = 0L;
+            uid_t uid; // value unused
 
             /* skip files that aren't numbers */
             pid_t childpid = (pid_t) atoi(ptr->d_name);
@@ -190,20 +258,21 @@
                 continue;
             }
 
-            ppid = 0;
-            if (pid != 0 || jparentArray != NULL) {
-                // parentPid opens and reads /proc/pid/stat
-                ppid = parentPid(env, childpid);
-            }
-            if (pid == 0 || ppid == pid) {
+            // Read /proc/pid/stat and get the parent pid, and start time
+            ppid = getStatInfo(env, childpid, &totalTime, &startTime, &uid);
+            if (ppid >= 0 && (pid == 0 || ppid == pid)) {
                 if (count < arraySize) {
                     // Only store if it fits
                     pids[count] = (jlong) childpid;
 
                     if (ppids != NULL) {
-                        // Store the parentPid
+                        // Store the parent Pid
                         ppids[count] = (jlong) ppid;
                     }
+                    if (stimes != NULL) {
+                        // Store the process start time
+                        stimes[count] = startTime;
+                    }
                 }
                 count++; // Count to tabulate size needed
             }
@@ -216,45 +285,15 @@
     if (ppids != NULL) {
         (*env)->ReleaseLongArrayElements(env, jparentArray, ppids, 0);
     }
+    if (stimes != NULL) {
+        (*env)->ReleaseLongArrayElements(env, jstimesArray, stimes, 0);
+    }
 
     closedir(dir);
     // If more pids than array had size for; count will be greater than array size
     return count;
 }
 
-/*
- * Returns the parent pid of a given pid, or -1 if not found
- */
-static pid_t parentPid(JNIEnv *env, pid_t pid) {
-    FILE* fp;
-    pstatus_t pstatus;
-    int statlen;
-    char fn[32];
-    int i, p;
-    char* s;
-
-    /*
-     * Try to open /proc/%d/status
-     */
-    snprintf(fn, sizeof fn, "/proc/%d/status", pid);
-    fp = fopen(fn, "r");
-    if (fp == NULL) {
-        return -1;
-    }
-
-    /*
-     * The format is: pid (command) state ppid ...
-     * As the command could be anything we must find the right most
-     * ")" and then skip the white spaces that follow it.
-     */
-    statlen = fread(&pstatus, 1, (sizeof pstatus), fp);
-    fclose(fp);
-    if (statlen < 0) {
-        return -1;
-    }
-    return (pid_t) pstatus.pr_ppid;
-}
-
 /**************************************************************
  * Implementation of ProcessHandleImpl_Info native methods.
  */
@@ -266,93 +305,74 @@
  * Method:    info0
  * Signature: (J)V
  */
-JNIEXPORT void JNICALL Java_java_lang_ProcessHandleImpl_00024Info_info0
-  (JNIEnv *env, jobject jinfo, jlong jpid) {
+JNIEXPORT void JNICALL
+Java_java_lang_ProcessHandleImpl_00024Info_info0(JNIEnv *env,
+                                                 jobject jinfo,
+                                                  jlong jpid) {
     pid_t pid = (pid_t) jpid;
-    getStatInfo(env, jinfo, pid);
+    jlong startTime = 0L;
+    jlong totalTime = 0L;
+    uid_t uid = -1;
+    pid_t ppid = getStatInfo(env, pid, &totalTime, &startTime, &uid);
+
     getCmdlineInfo(env, jinfo, pid);
+
+    if (ppid > 0) {
+        jstring str;
+        (*env)->SetLongField(env, jinfo, ProcessHandleImpl_Info_startTimeID, startTime);
+        JNU_CHECK_EXCEPTION(env);
+
+        (*env)->SetLongField(env, jinfo, ProcessHandleImpl_Info_totalTimeID, totalTime);
+        JNU_CHECK_EXCEPTION(env);
+
+        CHECK_NULL((str = uidToUser(env, uid)));
+        (*env)->SetObjectField(env, jinfo, ProcessHandleImpl_Info_userID, str);
+        JNU_CHECK_EXCEPTION(env);
+    }
 }
 
 /**
- * Read /proc/<pid>/stat and fill in the fields of the Info object.
- * Gather the user and system times.
+ * Read /proc/<pid>/status and return the ppid, total cputime and start time.
+ * Return: -1 is fail;  zero is unknown; >  0 is parent pid
  */
-static void getStatInfo(JNIEnv *env, jobject jinfo, pid_t pid) {
+static pid_t getStatInfo(JNIEnv *env, pid_t pid,
+                                      jlong *totalTime, jlong* startTime,
+                                      uid_t* uid) {
     FILE* fp;
-    pstatus_t pstatus;
-    struct stat stat_buf;
-    int ret;
+    psinfo_t psinfo;
     char fn[32];
-    int i, p;
-    char* s;
-    jlong totalTime;
+    int ret;
 
     /*
      * Try to open /proc/%d/status
      */
-    snprintf(fn, sizeof fn, "/proc/%d/status", pid);
-
-    if (stat(fn, &stat_buf) < 0) {
-        return;
-    }
-
+    snprintf(fn, sizeof fn, "/proc/%d/psinfo", pid);
     fp = fopen(fn, "r");
     if (fp == NULL) {
-        return;
+        return -1;
     }
 
-    ret = fread(&pstatus, 1, (sizeof pstatus), fp);
+    ret = fread(&psinfo, 1, (sizeof psinfo), fp);
     fclose(fp);
-    if (ret < 0) {
-        return;
+    if (ret < (sizeof psinfo)) {
+        return -1;
     }
 
-    totalTime = pstatus.pr_utime.tv_sec * 1000000000L + pstatus.pr_utime.tv_nsec +
-                pstatus.pr_stime.tv_sec * 1000000000L + pstatus.pr_stime.tv_nsec;
+    *totalTime = psinfo.pr_time.tv_sec * 1000000000L + psinfo.pr_time.tv_nsec;
 
-    (*env)->SetLongField(env, jinfo, ProcessHandleImpl_Info_totalTimeID, totalTime);
-    JNU_CHECK_EXCEPTION(env);
+    *startTime = psinfo.pr_start.tv_sec * (jlong)1000 +
+                 psinfo.pr_start.tv_nsec / 1000000;
+
+    *uid = psinfo.pr_uid;
+
+    return (pid_t) psinfo.pr_ppid;
 }
 
 static void getCmdlineInfo(JNIEnv *env, jobject jinfo, pid_t pid) {
-    FILE* fp;
-    psinfo_t psinfo;
-    int ret;
     char fn[32];
     char exePath[PATH_MAX];
-    int i, p;
-    jlong startTime;
-    jobjectArray cmdArray;
     jstring str = NULL;
-
-    /*
-     * try to open /proc/%d/psinfo
-     */
-    snprintf(fn, sizeof fn, "/proc/%d/psinfo", pid);
-    fp = fopen(fn, "r");
-    if (fp == NULL) {
-        return;
-    }
-
-    /*
-     * The format is: pid (command) state ppid ...
-     * As the command could be anything we must find the right most
-     * ")" and then skip the white spaces that follow it.
-     */
-    ret = fread(&psinfo, 1, (sizeof psinfo), fp);
-    fclose(fp);
-    if (ret < 0) {
-        return;
-    }
-
-    CHECK_NULL((str = uidToUser(env, psinfo.pr_uid)));
-    (*env)->SetObjectField(env, jinfo, ProcessHandleImpl_Info_userID, str);
-    JNU_CHECK_EXCEPTION(env);
-
-    startTime = (jlong)psinfo.pr_start.tv_sec * (jlong)1000 +
-                (jlong)psinfo.pr_start.tv_nsec / 1000000;
-    (*env)->SetLongField(env, jinfo, ProcessHandleImpl_Info_startTimeID, startTime);
-    JNU_CHECK_EXCEPTION(env);
+    int ret;
 
     /*
      * The path to the executable command is the link in /proc/<pid>/paths/a.out.
--- a/jdk/src/java.base/unix/classes/java/lang/ProcessImpl.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/unix/classes/java/lang/ProcessImpl.java	Wed Jul 05 20:42:36 2017 +0200
@@ -64,7 +64,7 @@
     static final boolean SUPPORTS_NORMAL_TERMINATION = true;
 
     private final int pid;
-    private final ProcessHandle processHandle;
+    private final ProcessHandleImpl processHandle;
     private int exitcode;
     private boolean hasExited;
 
@@ -320,7 +320,7 @@
                           dir,
                           fds,
                           redirectErrorStream);
-        processHandle = ProcessHandleImpl.getUnchecked(pid);
+        processHandle = ProcessHandleImpl.getInternal(pid);
 
         try {
             doPrivileged((PrivilegedExceptionAction<Void>) () -> {
@@ -505,7 +505,7 @@
                 // soon, so this is quite safe.
                 synchronized (this) {
                     if (!hasExited)
-                        ProcessHandleImpl.destroyProcess(pid, force);
+                        processHandle.destroyProcess(force);
                 }
                 try { stdin.close();  } catch (IOException ignored) {}
                 try { stdout.close(); } catch (IOException ignored) {}
@@ -521,7 +521,7 @@
                 // soon, so this is quite safe.
                 synchronized (this) {
                     if (!hasExited)
-                        ProcessHandleImpl.destroyProcess(pid, force);
+                        processHandle.destroyProcess(force);
                     try {
                         stdin.close();
                         if (stdout_inner_stream != null)
@@ -542,7 +542,7 @@
     @Override
     public CompletableFuture<Process> onExit() {
         return ProcessHandleImpl.completion(pid, false)
-                .handleAsync((exitStatus, unusedThrowable) -> {
+                .handleAsync((unusedExitStatus, unusedThrowable) -> {
                     boolean interrupted = false;
                     while (true) {
                         // Ensure that the concurrent task setting the exit status has completed
--- a/jdk/src/java.base/unix/native/libjava/ConcurrentPReader_md.c	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,66 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.  Oracle designates this
- * particular file as subject to the "Classpath" exception as provided
- * by Oracle in the LICENSE file that accompanied this code.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-#include <unistd.h>
-#include <errno.h>
-
-#include "jni.h"
-#include "jni_util.h"
-#include "jlong.h"
-#include "jdk_internal_jimage_concurrent_ConcurrentPReader.h"
-
-#ifdef _ALLBSD_SOURCE
-  #define pread64 pread
-#endif
-
-#define RESTARTABLE(_cmd, _result) do { \
-  do { \
-    _result = _cmd; \
-  } while((_result == -1) && (errno == EINTR)); \
-} while(0)
-
-static jfieldID fd_fdID;
-
-JNIEXPORT void JNICALL
-Java_jdk_internal_jimage_concurrent_ConcurrentPReader_initIDs(JNIEnv *env, jclass clazz)
-{
-    CHECK_NULL(clazz = (*env)->FindClass(env, "java/io/FileDescriptor"));
-    CHECK_NULL(fd_fdID = (*env)->GetFieldID(env, clazz, "fd", "I"));
-}
-
-JNIEXPORT jint JNICALL
-Java_jdk_internal_jimage_concurrent_ConcurrentPReader_pread(JNIEnv *env, jclass clazz,
-                                                            jobject fdo, jlong address,
-                                                            jint len, jlong offset)
-{
-    jint fd = (*env)->GetIntField(env, fdo, fd_fdID);
-    void *buf = (void *)jlong_to_ptr(address);
-    int res;
-    RESTARTABLE(pread64(fd, buf, len, offset), res);
-    if (res == -1) {
-        JNU_ThrowIOExceptionWithLastError(env, "pread failed");
-    }
-    return res;
-}
--- a/jdk/src/java.base/unix/native/libjava/ProcessHandleImpl_unix.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/unix/native/libjava/ProcessHandleImpl_unix.c	Wed Jul 05 20:42:36 2017 +0200
@@ -53,7 +53,6 @@
  * - destroy0(pid, force)
  */
 
-
 #ifndef WIFEXITED
 #define WIFEXITED(status) (((status)&0xFF) == 0)
 #endif
@@ -82,15 +81,20 @@
   } while((_result == NULL) && (errno == EINTR)); \
 } while(0)
 
+#ifdef __solaris__
+    #define STAT_FILE "/proc/%d/status"
+#else
+    #define STAT_FILE "/proc/%d/stat"
+#endif
 
 /* Block until a child process exits and return its exit code.
  * Note, can only be called once for any given pid if reapStatus = true.
  */
 JNIEXPORT jint JNICALL
 Java_java_lang_ProcessHandleImpl_waitForProcessExit0(JNIEnv* env,
-                                              jclass junk,
-                                              jlong jpid,
-                                              jboolean reapStatus)
+                                                     jclass junk,
+                                                     jlong jpid,
+                                                     jboolean reapStatus)
 {
     pid_t pid = (pid_t)jpid;
     errno = 0;
@@ -178,34 +182,32 @@
  * Method:    getCurrentPid0
  * Signature: ()J
  */
-JNIEXPORT jlong JNICALL Java_java_lang_ProcessHandleImpl_getCurrentPid0
-(JNIEnv *env, jclass clazz) {
+JNIEXPORT jlong JNICALL
+Java_java_lang_ProcessHandleImpl_getCurrentPid0(JNIEnv *env, jclass clazz) {
     pid_t pid = getpid();
     return (jlong) pid;
 }
 
 /*
  * Class:     java_lang_ProcessHandleImpl
- * Method:    isAlive0
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_java_lang_ProcessHandleImpl_isAlive0
-(JNIEnv *env, jobject obj, jlong jpid) {
-    pid_t pid = (pid_t) jpid;
-    return (kill(pid, 0) < 0) ? JNI_FALSE : JNI_TRUE;
-}
-
-/*
- * Class:     java_lang_ProcessHandleImpl
  * Method:    destroy0
  * Signature: (Z)Z
  */
-JNIEXPORT jboolean JNICALL Java_java_lang_ProcessHandleImpl_destroy0
-(JNIEnv *env, jobject obj, jlong jpid, jboolean force) {
+JNIEXPORT jboolean JNICALL
+Java_java_lang_ProcessHandleImpl_destroy0(JNIEnv *env,
+                                          jobject obj,
+                                          jlong jpid,
+                                          jlong startTime,
+                                          jboolean force) {
     pid_t pid = (pid_t) jpid;
     int sig = (force == JNI_TRUE) ? SIGKILL : SIGTERM;
-    return (kill(pid, sig) >= 0);
+    jlong start = Java_java_lang_ProcessHandleImpl_isAlive0(env, obj, jpid);
 
+    if (start == startTime || start == 0 || startTime == 0) {
+        return (kill(pid, sig) < 0) ? JNI_FALSE : JNI_TRUE;
+    } else {
+        return JNI_FALSE;
+    }
 }
 
 /**
@@ -260,11 +262,8 @@
 /*
  * Signatures for internal OS specific functions.
  */
-static pid_t parentPid(JNIEnv *env, pid_t pid);
-static jint getChildren(JNIEnv *env, jlong jpid,
-                        jlongArray array, jlongArray jparentArray);
-
-static void getStatInfo(JNIEnv *env, jobject jinfo, pid_t pid);
+static pid_t getStatInfo(JNIEnv *env, pid_t pid,
+                                     jlong *totalTime, jlong* startTime);
 static void getCmdlineInfo(JNIEnv *env, pid_t pid, jobject jinfo);
 static long long getBoottime(JNIEnv *env);
 
@@ -298,8 +297,8 @@
  * Method:    initIDs
  * Signature: ()V
  */
-JNIEXPORT void JNICALL Java_java_lang_ProcessHandleImpl_00024Info_initIDs
-  (JNIEnv *env, jclass clazz) {
+JNIEXPORT void JNICALL
+Java_java_lang_ProcessHandleImpl_00024Info_initIDs(JNIEnv *env, jclass clazz) {
 
     CHECK_NULL(ProcessHandleImpl_Info_commandID = (*env)->GetFieldID(env,
         clazz, "command", "Ljava/lang/String;"));
@@ -311,61 +310,98 @@
         clazz, "startTime", "J"));
     CHECK_NULL(ProcessHandleImpl_Info_userID = (*env)->GetFieldID(env,
         clazz, "user", "Ljava/lang/String;"));
+}
+
+/**************************************************************
+ * Static method to initialize the ticks per second rate.
+ *
+ * Class:     java_lang_ProcessHandleImpl
+ * Method:    initNative
+ * Signature: ()V
+ */
+JNIEXPORT void JNICALL
+Java_java_lang_ProcessHandleImpl_initNative(JNIEnv *env, jclass clazz) {
     clock_ticks_per_second = sysconf(_SC_CLK_TCK);
     bootTime_ms = getBoottime(env);
 }
 
 /*
+ * Check if a process is alive.
+ * Return the start time (ms since 1970) if it is available.
+ * If the start time is not available return 0.
+ * If the pid is invalid, return -1.
+ *
+ * Class:     java_lang_ProcessHandleImpl
+ * Method:    isAlive0
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL
+Java_java_lang_ProcessHandleImpl_isAlive0(JNIEnv *env, jobject obj, jlong jpid) {
+    pid_t pid = (pid_t) jpid;
+    jlong startTime = 0L;
+    jlong totalTime = 0L;
+    pid_t ppid = getStatInfo(env, pid, &totalTime, &startTime);
+    return (ppid <= 0) ? -1 : startTime;
+}
+
+/*
  * Returns the parent pid of the requested pid.
+ * The start time of the process must match (or be ANY).
  *
  * Class:     java_lang_ProcessHandleImpl
  * Method:    parent0
  * Signature: (J)J
  */
-JNIEXPORT jlong JNICALL Java_java_lang_ProcessHandleImpl_parent0
-(JNIEnv *env, jobject obj, jlong jpid) {
+JNIEXPORT jlong JNICALL
+Java_java_lang_ProcessHandleImpl_parent0(JNIEnv *env,
+                                        jobject obj,
+                                        jlong jpid,
+                                        jlong startTime) {
     pid_t pid = (pid_t) jpid;
-    pid_t ppid = -1;
+    pid_t ppid;
 
     pid_t mypid = getpid();
     if (pid == mypid) {
         ppid = getppid();
     } else {
-        ppid = parentPid(env, pid);
+        jlong start = 0L;;
+        jlong total = 0L;        // unused
+        ppid = getStatInfo(env, pid, &total, &start);
+        if (start != startTime && start != 0 && startTime != 0) {
+            ppid = -1;
+        }
     }
     return (jlong) ppid;
 }
 
 /*
  * Returns the children of the requested pid and optionally each parent.
- *
+ * Reads /proc and accumulates any process who parent pid matches.
+ * The resulting pids are stored into the array of longs.
+ * The number of pids is returned if they all fit.
+ * If the array is too short, the negative of the desired length is returned. *
  * Class:     java_lang_ProcessHandleImpl
  * Method:    getChildPids
  * Signature: (J[J[J)I
  */
-JNIEXPORT jint JNICALL Java_java_lang_ProcessHandleImpl_getProcessPids0
-(JNIEnv *env, jclass clazz, jlong jpid,
-    jlongArray jarray, jlongArray jparentArray) {
-    return getChildren(env, jpid, jarray, jparentArray);
-}
+JNIEXPORT jint JNICALL
+Java_java_lang_ProcessHandleImpl_getProcessPids0(JNIEnv *env,
+                                                 jclass clazz,
+                                                 jlong jpid,
+                                                 jlongArray jarray,
+                                                 jlongArray jparentArray,
+                                                 jlongArray jstimesArray) {
 
-/*
- * Reads /proc and accumulates any process who parent pid matches.
- * The resulting pids are stored into the array of longs.
- * The number of pids is returned if they all fit.
- * If the array is too short, the negative of the desired length is returned.
- */
-static jint getChildren(JNIEnv *env, jlong jpid,
-    jlongArray jarray, jlongArray jparentArray) {
     DIR* dir;
     struct dirent* ptr;
     pid_t pid = (pid_t) jpid;
-    pid_t ppid = 0;
-    size_t count = 0;
     jlong* pids = NULL;
     jlong* ppids = NULL;
-    size_t parentArraySize = 0;
-    size_t arraySize = 0;
+    jlong* stimes = NULL;
+    jsize parentArraySize = 0;
+    jsize arraySize = 0;
+    jsize stimesSize = 0;
+    jsize count = 0;
 
     arraySize = (*env)->GetArrayLength(env, jarray);
     JNU_CHECK_EXCEPTION_RETURN(env, -1);
@@ -378,6 +414,15 @@
             return 0;
         }
     }
+    if (jstimesArray != NULL) {
+        stimesSize = (*env)->GetArrayLength(env, jstimesArray);
+        JNU_CHECK_EXCEPTION_RETURN(env, -1);
+
+        if (arraySize != stimesSize) {
+            JNU_ThrowIllegalArgumentException(env, "array sizes not equal");
+            return 0;
+        }
+    }
 
     /*
      * To locate the children we scan /proc looking for files that have a
@@ -385,7 +430,7 @@
      */
     if ((dir = opendir("/proc")) == NULL) {
         JNU_ThrowByNameWithLastError(env,
-            "java/lang/Runtime", "Unable to open /proc");
+            "java/lang/RuntimeException", "Unable to open /proc");
         return -1;
     }
 
@@ -400,20 +445,26 @@
                 break;
             }
         }
+        if (jstimesArray != NULL) {
+            stimes  = (*env)->GetLongArrayElements(env, jstimesArray, NULL);
+            if (stimes == NULL) {
+                break;
+            }
+        }
 
         while ((ptr = readdir(dir)) != NULL) {
+            pid_t ppid = 0;
+            jlong totalTime = 0L;
+            jlong startTime = 0L;
+
             /* skip files that aren't numbers */
             pid_t childpid = (pid_t) atoi(ptr->d_name);
             if ((int) childpid <= 0) {
                 continue;
             }
-
-            ppid = 0;
-            if (pid != 0 || jparentArray != NULL) {
-                // parentPid opens and reads /proc/pid/stat
-                ppid = parentPid(env, childpid);
-            }
-            if (pid == 0 || ppid == pid) {
+            // Read /proc/pid/stat and get the parent pid, and start time
+            ppid = getStatInfo(env, childpid, &totalTime, &startTime);
+            if (ppid > 0 && (pid == 0 || ppid == pid)) {
                 if (count < arraySize) {
                     // Only store if it fits
                     pids[count] = (jlong) childpid;
@@ -422,6 +473,10 @@
                         // Store the parentPid
                         ppids[count] = (jlong) ppid;
                     }
+                    if (stimes != NULL) {
+                        // Store the process start time
+                        stimes[count] = startTime;
+                    }
                 }
                 count++; // Count to tabulate size needed
             }
@@ -434,56 +489,15 @@
     if (ppids != NULL) {
         (*env)->ReleaseLongArrayElements(env, jparentArray, ppids, 0);
     }
+    if (stimes != NULL) {
+        (*env)->ReleaseLongArrayElements(env, jstimesArray, stimes, 0);
+    }
 
     closedir(dir);
     // If more pids than array had size for; count will be greater than array size
     return count;
 }
 
-/*
- * Returns the parent pid of a given pid, or -1 if not found
- */
-static pid_t parentPid(JNIEnv *env, pid_t pid) {
-    char state;
-    FILE* fp;
-    char stat[2048];
-    int statlen;
-    char fn[32];
-    int i, p;
-    char* s;
-
-    /*
-     * try to open /proc/%d/stat
-     */
-    snprintf(fn, sizeof fn, "/proc/%d/stat", pid);
-    fp = fopen(fn, "r");
-    if (fp == NULL) {
-        return -1;
-    }
-
-    /*
-     * The format is: pid (command) state ppid ...
-     * As the command could be anything we must find the right most
-     * ")" and then skip the white spaces that follow it.
-     */
-    statlen = fread(stat, 1, (sizeof stat - 1), fp);
-    fclose(fp);
-    if (statlen < 0) {
-        return -1;
-    }
-
-    stat[statlen] = '\0';
-    s = strrchr(stat, ')');
-    if (s == NULL) {
-        return -1;
-    }
-    do s++; while (isspace(*s));
-    i = sscanf(s, "%c %d", &state, &p);
-    if (i != 2) {
-        return (pid_t)-1;
-    }
-    return (pid_t) p;
-}
 
 /**************************************************************
  * Implementation of ProcessHandleImpl_Info native methods.
@@ -496,49 +510,51 @@
  * Method:    info0
  * Signature: (JLjava/lang/ProcessHandle/Info;)I
  */
-JNIEXPORT void JNICALL Java_java_lang_ProcessHandleImpl_00024Info_info0
-  (JNIEnv *env, jobject jinfo, jlong jpid) {
+JNIEXPORT void JNICALL
+Java_java_lang_ProcessHandleImpl_00024Info_info0(JNIEnv *env,
+                                                 jobject jinfo,
+                                                 jlong jpid) {
     pid_t pid = (pid_t) jpid;
-    getStatInfo(env, jinfo, (pid_t)pid);
-    getCmdlineInfo(env, pid, jinfo);
+    pid_t ppid;
+    jlong totalTime = 0L;
+    jlong startTime = -1L;
+
+    ppid = getStatInfo(env, pid,  &totalTime, &startTime);
+    if (ppid > 0) {
+        (*env)->SetLongField(env, jinfo, ProcessHandleImpl_Info_totalTimeID, totalTime);
+        JNU_CHECK_EXCEPTION(env);
+
+        (*env)->SetLongField(env, jinfo, ProcessHandleImpl_Info_startTimeID, startTime);
+        JNU_CHECK_EXCEPTION(env);
+
+        getCmdlineInfo(env, pid, jinfo);
+    }
 }
 
 /**
- * Read /proc/<pid>/stat and fill in the fields of the Info object.
- * The executable name, plus the user, system, and start times are gathered.
+ * Read /proc/<pid>/stat and return the ppid, total cputime and start time.
+ * -1 is fail;  zero is unknown; >  0 is parent pid
  */
-static void getStatInfo(JNIEnv *env, jobject jinfo, pid_t pid) {
-    char state;
+static pid_t getStatInfo(JNIEnv *env, pid_t pid,
+                                     jlong *totalTime, jlong* startTime) {
     FILE* fp;
     char buffer[2048];
-    struct stat stat_buf;
     int statlen;
     char fn[32];
-    int i, ppid = -2;
     char* s;
-    char *cmd;
-    jstring name = NULL;
-    unsigned long userTime = 0;             // clock tics
-    unsigned long totalTime = 0;            // clock tics
-    jlong total = 0;                        // nano seconds
-    unsigned long long startTime = 0;       // microseconds
+    int parentPid;
+    long unsigned int utime = 0;      // clock tics
+    long unsigned int stime = 0;      // clock tics
+    long long unsigned int start = 0; // microseconds
 
     /*
      * Try to stat and then open /proc/%d/stat
      */
-    snprintf(fn, sizeof fn, "/proc/%d/stat", pid);
-
-    if (stat(fn, &stat_buf) < 0) {
-        return;
-    }
-
-    CHECK_NULL((name = uidToUser(env, stat_buf.st_uid)));
-    (*env)->SetObjectField(env, jinfo, ProcessHandleImpl_Info_userID, name);
-    JNU_CHECK_EXCEPTION(env);
+    snprintf(fn, sizeof fn, STAT_FILE, pid);
 
     fp = fopen(fn, "r");
     if (fp == NULL) {
-        return;
+        return -1;              // fail, no such /proc/pid/stat
     }
 
     /*
@@ -549,38 +565,34 @@
     statlen = fread(buffer, 1, (sizeof buffer - 1), fp);
     fclose(fp);
     if (statlen < 0) {
-        return;
+        return 0;               // parent pid is not available
     }
 
     buffer[statlen] = '\0';
     s = strchr(buffer, '(');
     if (s == NULL) {
-        return;
+        return 0;               // parent pid is not available
     }
     // Found start of command, skip to end
     s++;
     s = strrchr(s, ')');
     if (s == NULL) {
-        return;
+        return 0;               // parent pid is not available
     }
     s++;
 
     // Scan the needed fields from status, retaining only ppid(4),
     // utime (14), stime(15), starttime(22)
-    i = sscanf(s, " %c %d %*d %*d %*d %*d %*d %*u %*u %*u %*u %lu %lu %*d %*d %*d %*d %*d %*d %llu",
-            &state, &ppid, &userTime, &totalTime, &startTime);
-    if (i != 5) {
-        return;              // not all values parsed; return error
+    if (4 != sscanf(s, " %*c %d %*d %*d %*d %*d %*d %*u %*u %*u %*u %lu %lu %*d %*d %*d %*d %*d %*d %llu",
+            &parentPid, &utime, &stime, &start)) {
+        return 0;              // not all values parsed; return error
     }
 
-    total = (userTime + totalTime) * (jlong)(1000000000 / clock_ticks_per_second);
-
-    startTime = bootTime_ms + ((startTime * 1000) / clock_ticks_per_second);
+    *totalTime = (utime + stime) * (jlong)(1000000000 / clock_ticks_per_second);
 
-    (*env)->SetLongField(env, jinfo, ProcessHandleImpl_Info_totalTimeID, total);
-    JNU_CHECK_EXCEPTION(env);
-    (*env)->SetLongField(env, jinfo, ProcessHandleImpl_Info_startTimeID, startTime);
-    JNU_CHECK_EXCEPTION(env);
+    *startTime = bootTime_ms + ((start * 1000) / clock_ticks_per_second);
+
+    return parentPid;
 }
 
 /**
@@ -632,6 +644,7 @@
     char *cmdline = NULL, *cmdEnd;  // used for command line args and exe
     jstring cmdexe = NULL;
     char fn[32];
+    struct stat stat_buf;
 
     /*
      * Try to open /proc/%d/cmdline
@@ -679,6 +692,14 @@
         if (fillArgArray(env, jinfo, i, cmdline, cmdEnd, cmdexe) < 0) {
             break;
         }
+
+        // Get and store the user name
+        if (fstat(fd, &stat_buf) == 0) {
+            jstring name = uidToUser(env, stat_buf.st_uid);
+            if (name != NULL) {
+                (*env)->SetObjectField(env, jinfo, ProcessHandleImpl_Info_userID, name);
+            }
+        }
     } while (0);
 
     if (cmdline != NULL) {
--- a/jdk/src/java.base/unix/native/libjli/java_md_solinux.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/unix/native/libjli/java_md_solinux.c	Wed Jul 05 20:42:36 2017 +0200
@@ -340,6 +340,7 @@
       char* newpath     = NULL; /* path on new LD_LIBRARY_PATH */
       char* lastslash   = NULL;
       char** newenvp    = NULL; /* current environment */
+      size_t new_runpath_size;
 #ifdef __solaris__
       char*  dmpath     = NULL;  /* data model specific LD_LIBRARY_PATH,
                                     Solaris only */
@@ -516,13 +517,14 @@
             /* runpath contains current effective LD_LIBRARY_PATH setting */
 
             jvmpath = JLI_StringDup(jvmpath);
-            new_runpath = JLI_MemAlloc(((runpath != NULL) ? JLI_StrLen(runpath) : 0) +
+            new_runpath_size = ((runpath != NULL) ? JLI_StrLen(runpath) : 0) +
                     2 * JLI_StrLen(jrepath) + 2 * JLI_StrLen(arch) +
 #ifdef AIX
                     /* On AIX we additionally need 'jli' in the path because ld doesn't support $ORIGIN. */
                     JLI_StrLen(jrepath) + JLI_StrLen(arch) + JLI_StrLen("/lib//jli:") +
 #endif
-                    JLI_StrLen(jvmpath) + 52);
+                    JLI_StrLen(jvmpath) + 52;
+            new_runpath = JLI_MemAlloc(new_runpath_size);
             newpath = new_runpath + JLI_StrLen(LD_LIBRARY_PATH "=");
 
 
@@ -577,6 +579,11 @@
              * loop of execv() because we test for the prefix, above.
              */
             if (runpath != 0) {
+                /* ensure storage for runpath + colon + NULL */
+                if ((JLI_StrLen(runpath) + 1 + 1) > new_runpath_size) {
+                    JLI_ReportErrorMessageSys(JRE_ERROR11);
+                    exit(1);
+                }
                 JLI_StrCat(new_runpath, ":");
                 JLI_StrCat(new_runpath, runpath);
             }
@@ -667,7 +674,11 @@
             JLI_TraceLauncher("JRE path is %s\n", path);
             return JNI_TRUE;
         }
-
+        /* ensure storage for path + /jre + NULL */
+        if ((JLI_StrLen(path) + 4  + 1) > (size_t) pathsize) {
+            JLI_TraceLauncher("Insufficient space to store JRE path\n");
+            return JNI_FALSE;
+        }
         /* Does the app ship a private JRE in <apphome>/jre directory? */
         JLI_Snprintf(libjava, sizeof(libjava), "%s/jre/lib/%s/" JAVA_DLL, path, arch);
         if (access(libjava, F_OK) == 0) {
--- a/jdk/src/java.base/unix/native/libnet/net_util_md.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/unix/native/libnet/net_util_md.c	Wed Jul 05 20:42:36 2017 +0200
@@ -1524,6 +1524,7 @@
     int exclbind = -1;
 #endif
     int rv;
+    int arg, alen;
 
 #ifdef __linux__
     /*
@@ -1540,7 +1541,7 @@
     }
 #endif
 
-#if defined(__solaris__) && defined(AF_INET6)
+#if defined(__solaris__)
     /*
      * Solaris has separate IPv4 and IPv6 port spaces so we
      * use an exclusive bind when SO_REUSEADDR is not used to
@@ -1550,35 +1551,31 @@
      * results in a late bind that fails because the
      * corresponding IPv4 port is in use.
      */
-    if (ipv6_available()) {
-        int arg;
-        socklen_t len;
+    alen = sizeof(arg);
 
-        len = sizeof(arg);
-        if (useExclBind || getsockopt(fd, SOL_SOCKET, SO_REUSEADDR,
-                       (char *)&arg, &len) == 0) {
-            if (useExclBind || arg == 0) {
-                /*
-                 * SO_REUSEADDR is disabled or sun.net.useExclusiveBind
-                 * property is true so enable TCP_EXCLBIND or
-                 * UDP_EXCLBIND
-                 */
-                len = sizeof(arg);
-                if (getsockopt(fd, SOL_SOCKET, SO_TYPE, (char *)&arg,
-                               &len) == 0) {
-                    if (arg == SOCK_STREAM) {
-                        level = IPPROTO_TCP;
-                        exclbind = TCP_EXCLBIND;
-                    } else {
-                        level = IPPROTO_UDP;
-                        exclbind = UDP_EXCLBIND;
-                    }
+    if (useExclBind || getsockopt(fd, SOL_SOCKET, SO_REUSEADDR,
+                   (char *)&arg, &alen) == 0) {
+        if (useExclBind || arg == 0) {
+            /*
+             * SO_REUSEADDR is disabled or sun.net.useExclusiveBind
+             * property is true so enable TCP_EXCLBIND or
+             * UDP_EXCLBIND
+             */
+            alen = sizeof(arg);
+            if (getsockopt(fd, SOL_SOCKET, SO_TYPE, (char *)&arg,
+                           &alen) == 0) {
+                if (arg == SOCK_STREAM) {
+                    level = IPPROTO_TCP;
+                    exclbind = TCP_EXCLBIND;
+                } else {
+                    level = IPPROTO_UDP;
+                    exclbind = UDP_EXCLBIND;
                 }
+            }
 
-                arg = 1;
-                setsockopt(fd, level, exclbind, (char *)&arg,
-                           sizeof(arg));
-            }
+            arg = 1;
+            setsockopt(fd, level, exclbind, (char *)&arg,
+                       sizeof(arg));
         }
     }
 
--- a/jdk/src/java.base/windows/classes/java/lang/ProcessImpl.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/windows/classes/java/lang/ProcessImpl.java	Wed Jul 05 20:42:36 2017 +0200
@@ -34,7 +34,6 @@
 import java.io.IOException;
 import java.io.InputStream;
 import java.io.OutputStream;
-import java.lang.Override;
 import java.lang.ProcessBuilder.Redirect;
 import java.security.AccessController;
 import java.security.PrivilegedAction;
@@ -391,7 +390,7 @@
 
         handle = create(cmdstr, envblock, path,
                         stdHandles, redirectErrorStream);
-        processHandle = ProcessHandleImpl.getUnchecked(getProcessId0(handle));
+        processHandle = ProcessHandleImpl.getInternal(getProcessId0(handle));
 
         java.security.AccessController.doPrivileged(
         new java.security.PrivilegedAction<Void>() {
--- a/jdk/src/java.base/windows/native/libjava/ConcurrentPReader_md.c	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,64 +0,0 @@
-/*
- * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.  Oracle designates this
- * particular file as subject to the "Classpath" exception as provided
- * by Oracle in the LICENSE file that accompanied this code.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-#include <windows.h>
-
-#include "jni_util.h"
-#include "jlong.h"
-#include "jdk_internal_jimage_concurrent_ConcurrentPReader.h"
-
-static jfieldID handle_fdID;
-
-JNIEXPORT void JNICALL
-Java_jdk_internal_jimage_concurrent_ConcurrentPReader_initIDs(JNIEnv *env, jclass clazz)
-{
-    CHECK_NULL(clazz = (*env)->FindClass(env, "java/io/FileDescriptor"));
-    CHECK_NULL(handle_fdID = (*env)->GetFieldID(env, clazz, "handle", "J"));
-}
-
-JNIEXPORT jint JNICALL
-Java_jdk_internal_jimage_concurrent_ConcurrentPReader_pread(JNIEnv *env, jclass clazz,
-                                                            jobject fdo, jlong address,
-                                                            jint len, jlong offset)
-{
-    OVERLAPPED ov;
-    DWORD nread;
-    BOOL result;
-
-    HANDLE handle = (HANDLE)(*env)->GetLongField(env, fdo, handle_fdID);
-    void *buf = (void *)jlong_to_ptr(address);
-
-    ZeroMemory(&ov, sizeof(ov));
-    ov.Offset = (DWORD)offset;
-    ov.OffsetHigh = (DWORD)(offset >> 32);
-
-    result = ReadFile(handle, (LPVOID)buf, len, &nread, &ov);
-    if (result == 0) {
-        JNU_ThrowIOExceptionWithLastError(env, "ReadFile failed");
-    }
-
-    return nread;
-}
-
--- a/jdk/src/java.base/windows/native/libjava/ProcessHandleImpl_win.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/windows/native/libjava/ProcessHandleImpl_win.c	Wed Jul 05 20:42:36 2017 +0200
@@ -64,8 +64,8 @@
  * Method:    initIDs
  * Signature: ()V
  */
-JNIEXPORT void JNICALL Java_java_lang_ProcessHandleImpl_00024Info_initIDs
-  (JNIEnv *env, jclass clazz) {
+JNIEXPORT void JNICALL
+Java_java_lang_ProcessHandleImpl_00024Info_initIDs(JNIEnv *env, jclass clazz) {
 
     CHECK_NULL(ProcessHandleImpl_Info_commandID = (*env)->GetFieldID(env,
         clazz, "command", "Ljava/lang/String;"));
@@ -78,15 +78,25 @@
     CHECK_NULL(ProcessHandleImpl_Info_userID = (*env)->GetFieldID(env,
         clazz, "user", "Ljava/lang/String;"));
 }
+/**************************************************************
+ * Static method to initialize native.
+ *
+ * Class:     java_lang_ProcessHandleImpl
+ * Method:    initNative
+ * Signature: ()V
+ */
+JNIEXPORT void JNICALL
+Java_java_lang_ProcessHandleImpl_initNative(JNIEnv *env, jclass clazz) {
+}
 
 /*
  * Block until a child process exits and return its exit code.
  */
 JNIEXPORT jint JNICALL
 Java_java_lang_ProcessHandleImpl_waitForProcessExit0(JNIEnv* env,
-                                              jclass junk,
-                                              jlong jpid,
-                                              jboolean reapStatus) {
+                                                     jclass junk,
+                                                     jlong jpid,
+                                                     jboolean reapStatus) {
     DWORD pid = (DWORD)jpid;
     DWORD exitValue = -1;
     HANDLE handle = OpenProcess(SYNCHRONIZE | PROCESS_QUERY_LIMITED_INFORMATION,
@@ -97,7 +107,7 @@
     do {
         if (!GetExitCodeProcess(handle, &exitValue)) {
             JNU_ThrowByNameWithLastError(env,
-                "java/lang/Runtime", "GetExitCodeProcess");
+                "java/lang/RuntimeException", "GetExitCodeProcess");
             break;
         }
         if (exitValue == STILL_ACTIVE) {
@@ -110,7 +120,7 @@
                                        INFINITE) /* Wait forever */
                 == WAIT_FAILED) {
                 JNU_ThrowByNameWithLastError(env,
-                    "java/lang/Runtime", "WaitForMultipleObjects");
+                    "java/lang/RuntimeException", "WaitForMultipleObjects");
                 break;
             }
         }
@@ -126,8 +136,8 @@
  * Method:    getCurrentPid0
  * Signature: ()J
  */
-JNIEXPORT jlong JNICALL Java_java_lang_ProcessHandleImpl_getCurrentPid0
-(JNIEnv *env, jclass clazz) {
+JNIEXPORT jlong JNICALL
+Java_java_lang_ProcessHandleImpl_getCurrentPid0(JNIEnv *env, jclass clazz) {
     DWORD  pid = GetCurrentProcessId();
     return (jlong)pid;
 }
@@ -139,13 +149,21 @@
  * Method:    parent0
  * Signature: (J)J
  */
-JNIEXPORT jlong JNICALL Java_java_lang_ProcessHandleImpl_parent0
-(JNIEnv *env, jclass clazz, jlong jpid) {
-
-    DWORD ppid = -1;
+JNIEXPORT jlong JNICALL
+Java_java_lang_ProcessHandleImpl_parent0(JNIEnv *env,
+                                         jclass clazz,
+                                         jlong jpid,
+                                         jlong startTime) {
+    DWORD ppid = 0;
     DWORD wpid = (DWORD)jpid;
     PROCESSENTRY32 pe32;
     HANDLE hProcessSnap;
+    jlong start;
+
+    start = Java_java_lang_ProcessHandleImpl_isAlive0(env, clazz, jpid);
+    if (start != startTime && start != 0 && startTime != 0) {
+        return -1;
+    }
 
     // Take a snapshot of all processes in the system.
     hProcessSnap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
@@ -181,18 +199,23 @@
  * Method:    getChildPids
  * Signature: (J[J[J)I
  */
-JNIEXPORT jint JNICALL Java_java_lang_ProcessHandleImpl_getProcessPids0
-(JNIEnv *env, jclass clazz, jlong jpid,
-    jlongArray jarray, jlongArray jparentArray) {
-
+JNIEXPORT jint JNICALL
+Java_java_lang_ProcessHandleImpl_getProcessPids0(JNIEnv *env,
+                                                 jclass clazz,
+                                                 jlong jpid,
+                                                 jlongArray jarray,
+                                                 jlongArray jparentArray,
+                                                 jlongArray jstimesArray) {
     HANDLE hProcessSnap;
     PROCESSENTRY32 pe32;
     DWORD ppid = (DWORD)jpid;
-    size_t count = 0;
     jlong* pids = NULL;
     jlong* ppids = NULL;
-    size_t parentArraySize = 0;
-    size_t arraySize = 0;
+    jlong* stimes = NULL;
+    jsize parentArraySize = 0;
+    jsize arraySize = 0;
+    jsize stimesSize = 0;
+    jsize count = 0;
 
     arraySize = (*env)->GetArrayLength(env, jarray);
     JNU_CHECK_EXCEPTION_RETURN(env, -1);
@@ -205,6 +228,15 @@
             return 0;
         }
     }
+    if (jstimesArray != NULL) {
+        stimesSize = (*env)->GetArrayLength(env, jstimesArray);
+        JNU_CHECK_EXCEPTION_RETURN(env, -1);
+
+        if (arraySize != stimesSize) {
+            JNU_ThrowIllegalArgumentException(env, "array sizes not equal");
+            return 0;
+        }
+    }
 
     // Take a snapshot of all processes in the system.
     hProcessSnap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
@@ -228,6 +260,12 @@
                     break;
                 }
             }
+            if (jstimesArray != NULL) {
+                stimes  = (*env)->GetLongArrayElements(env, jstimesArray, NULL);
+                if (stimes == NULL) {
+                    break;
+                }
+            }
             // Now walk the snapshot of processes, and
             // save information about each process in turn
             do {
@@ -236,11 +274,17 @@
                     && (pe32.th32ParentProcessID == ppid))) {
                     if (count < arraySize) {
                         // Only store if it fits
-                        pids[count] = (jlong)pe32.th32ProcessID;
+                        pids[count] = (jlong) pe32.th32ProcessID;
                         if (ppids != NULL) {
                             // Store the parentPid
                             ppids[count] = (jlong) pe32.th32ParentProcessID;
                         }
+                        if (stimes != NULL) {
+                            // Store the process start time
+                            stimes[count] =
+                                    Java_java_lang_ProcessHandleImpl_isAlive0(env,
+                                            clazz, (jlong) pe32.th32ProcessID);
+                        }
                     }
                     count++;    // Count to tabulate size needed
                 }
@@ -253,6 +297,9 @@
         if (ppids != NULL) {
             (*env)->ReleaseLongArrayElements(env, jparentArray, ppids, 0);
         }
+        if (stimes != NULL) {
+            (*env)->ReleaseLongArrayElements(env, jstimesArray, stimes, 0);
+        }
     } else {
         JNU_ThrowByName(env,
             "java/lang/RuntimeException", "snapshot not available");
@@ -263,48 +310,6 @@
     return (jint)count;
 }
 
-/*
- * Destroy the process.
- *
- * Class:     java_lang_ProcessHandleImpl
- * Method:    destroy0
- * Signature: (Z)V
- */
-JNIEXPORT jboolean JNICALL Java_java_lang_ProcessHandleImpl_destroy0
-(JNIEnv *env, jclass clazz, jlong jpid, jboolean force) {
-    DWORD pid = (DWORD)jpid;
-    HANDLE handle = OpenProcess(PROCESS_TERMINATE, FALSE, pid);
-    if (handle != NULL) {
-        TerminateProcess(handle, 1);
-        CloseHandle(handle);         // Ignore return code
-        return JNI_TRUE;
-    }
-    return JNI_FALSE;
-}
-
-/*
- * Class:     java_lang_ProcessHandleImpl
- * Method:    isAlive0
- * Signature: (J)Z
- */
-JNIEXPORT jboolean JNICALL Java_java_lang_ProcessHandleImpl_isAlive0
-(JNIEnv *env, jclass clazz, jlong jpid) {
-    DWORD pid = (DWORD)jpid;
-
-    jboolean ret = JNI_FALSE;
-    HANDLE handle =
-        OpenProcess(THREAD_QUERY_INFORMATION | PROCESS_QUERY_LIMITED_INFORMATION,
-                    FALSE, pid);
-    if (handle != NULL) {
-        DWORD dwExitStatus;
-
-        GetExitCodeProcess(handle, &dwExitStatus);
-        CloseHandle(handle); // Ignore return code
-        ret = (dwExitStatus == STILL_ACTIVE);
-    }
-    return ret;
-}
-
 /**
  * Assemble a 64 bit value from two 32 bit values.
  */
@@ -315,14 +320,90 @@
 }
 
 /*
+ * Get the start time in ms from 1970 from the handle.
+ */
+static jlong getStartTime(HANDLE handle) {
+    FILETIME CreationTime, ExitTime, KernelTime, UserTime;
+    if (GetProcessTimes(handle, &CreationTime, &ExitTime, &KernelTime, &UserTime)) {
+        jlong start = jlong_from(CreationTime.dwHighDateTime,
+                                 CreationTime.dwLowDateTime) / 10000;
+        start -= 11644473600000L; // Rebase Epoch from 1601 to 1970
+        return start;
+    } else {
+        return 0;
+    }
+}
+
+/*
+ * Destroy the process.
+ *
+ * Class:     java_lang_ProcessHandleImpl
+ * Method:    destroy0
+ * Signature: (Z)V
+ */
+JNIEXPORT jboolean JNICALL
+Java_java_lang_ProcessHandleImpl_destroy0(JNIEnv *env,
+                                          jclass clazz,
+                                          jlong jpid,
+                                          jlong startTime,
+                                          jboolean force) {
+    DWORD pid = (DWORD)jpid;
+    jboolean ret = JNI_FALSE;
+    HANDLE handle = OpenProcess(PROCESS_TERMINATE | THREAD_QUERY_INFORMATION
+                                | PROCESS_QUERY_LIMITED_INFORMATION, FALSE, pid);
+    if (handle != NULL) {
+        jlong start = getStartTime(handle);
+        if (start == startTime || startTime == 0) {
+            ret = TerminateProcess(handle, 1) ? JNI_TRUE : JNI_FALSE;
+        }
+        CloseHandle(handle);         // Ignore return code
+    }
+    return ret;
+}
+
+ /*
+ * Check if a process is alive.
+ * Return the start time (ms since 1970) if it is available.
+ * If the start time is not available return 0.
+ * If the pid is invalid, return -1.
+ *
+ * Class:     java_lang_ProcessHandleImpl
+ * Method:    isAlive0
+ * Signature: (J)J
+ */
+JNIEXPORT jlong JNICALL
+Java_java_lang_ProcessHandleImpl_isAlive0(JNIEnv *env, jclass clazz, jlong jpid) {
+    DWORD pid = (DWORD)jpid;
+
+    jlong ret = -1;
+    HANDLE handle =
+        OpenProcess(THREAD_QUERY_INFORMATION | PROCESS_QUERY_LIMITED_INFORMATION,
+                    FALSE, pid);
+    if (handle != NULL) {
+        DWORD dwExitStatus;
+
+        GetExitCodeProcess(handle, &dwExitStatus);
+        if (dwExitStatus == STILL_ACTIVE) {
+            ret = getStartTime(handle);
+        } else {
+            ret = -1;
+        }
+        CloseHandle(handle); // Ignore return code
+   }
+   return ret;
+}
+
+/*
  * Fill in the Info object from the OS information about the process.
  *
  * Class:     java_lang_ProcessHandleImpl
  * Method:    info0
  * Signature: (J)V
  */
-JNIEXPORT void JNICALL Java_java_lang_ProcessHandleImpl_00024Info_info0
-  (JNIEnv *env, jobject jinfo, jlong jpid) {
+JNIEXPORT void JNICALL
+Java_java_lang_ProcessHandleImpl_00024Info_info0(JNIEnv *env,
+                                                 jobject jinfo,
+                                                 jlong jpid) {
     DWORD pid = (DWORD)jpid;
     int ret = 0;
     HANDLE handle =
--- a/jdk/src/java.base/windows/native/libjli/java_md.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.base/windows/native/libjli/java_md.c	Wed Jul 05 20:42:36 2017 +0200
@@ -323,7 +323,11 @@
             JLI_TraceLauncher("JRE path is %s\n", path);
             return JNI_TRUE;
         }
-
+        /* ensure storage for path + \jre + NULL */
+        if ((JLI_StrLen(path) + 4 + 1) > (size_t) pathsize) {
+            JLI_TraceLauncher("Insufficient space to store JRE path\n");
+            return JNI_FALSE;
+        }
         /* Does this app ship a private JRE in <apphome>\jre directory? */
         JLI_Snprintf(javadll, sizeof (javadll), "%s\\jre\\bin\\" JAVA_DLL, path);
         if (stat(javadll, &s) == 0) {
--- a/jdk/src/java.desktop/macosx/classes/com/apple/laf/AquaFileSystemModel.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/macosx/classes/com/apple/laf/AquaFileSystemModel.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2011, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011, 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
@@ -383,11 +383,7 @@
             this.currentDirectory = currentDirectory;
             this.fid = fid;
             String name = "Aqua L&F File Loading Thread";
-            if (System.getSecurityManager() == null) {
-                this.loadThread = new Thread(FilesLoader.this, name);
-            } else {
-                this.loadThread = new ManagedLocalsThread(FilesLoader.this, name);
-            }
+            this.loadThread = new ManagedLocalsThread(this, name);
             this.loadThread.start();
         }
 
--- a/jdk/src/java.desktop/macosx/classes/sun/font/CFontManager.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/macosx/classes/sun/font/CFontManager.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2011, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011, 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
@@ -42,7 +42,7 @@
 import sun.awt.HeadlessToolkit;
 import sun.awt.util.ThreadGroupUtils;
 import sun.lwawt.macosx.*;
-import sun.misc.InnocuousThread;
+import sun.misc.ManagedLocalsThread;
 
 public final class CFontManager extends SunFontManager {
     private static Hashtable<String, Font2D> genericFonts = new Hashtable<String, Font2D>();
@@ -213,17 +213,12 @@
                     }
                 };
                 AccessController.doPrivileged((PrivilegedAction<Void>) () -> {
-                            if (System.getSecurityManager() == null) {
-                                /* The thread must be a member of a thread group
-                                 * which will not get GCed before VM exit.
-                                 * Make its parent the top-level thread group.
-                                 */
-                                ThreadGroup rootTG = ThreadGroupUtils.getRootThreadGroup();
-                                fileCloser = new Thread(rootTG, fileCloserRunnable);
-                            } else {
-                                /* InnocuousThread is a member of a correct TG by default */
-                                fileCloser = new InnocuousThread(fileCloserRunnable);
-                            }
+                            /* The thread must be a member of a thread group
+                             * which will not get GCed before VM exit.
+                             * Make its parent the top-level thread group.
+                             */
+                            ThreadGroup rootTG = ThreadGroupUtils.getRootThreadGroup();
+                            fileCloser = new ManagedLocalsThread(rootTG, fileCloserRunnable);
                             fileCloser.setContextClassLoader(null);
                             Runtime.getRuntime().addShutdownHook(fileCloser);
                             return null;
--- a/jdk/src/java.desktop/macosx/classes/sun/java2d/opengl/CGLGraphicsConfig.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/macosx/classes/sun/java2d/opengl/CGLGraphicsConfig.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2011, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011, 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
@@ -379,23 +379,11 @@
     public VolatileImage createCompatibleVolatileImage(int width, int height,
                                                        int transparency,
                                                        int type) {
-        if (type == FLIP_BACKBUFFER || type == WINDOW || type == UNDEFINED ||
-            transparency == Transparency.BITMASK)
-        {
+        if ((type != FBOBJECT && type != TEXTURE)
+                || transparency == Transparency.BITMASK
+                || type == FBOBJECT && !isCapPresent(CAPS_EXT_FBOBJECT)) {
             return null;
         }
-
-        if (type == FBOBJECT) {
-            if (!isCapPresent(CAPS_EXT_FBOBJECT)) {
-                return null;
-            }
-        } else if (type == PBUFFER) {
-            boolean isOpaque = transparency == Transparency.OPAQUE;
-            if (!isOpaque && !isCapPresent(CAPS_STORED_ALPHA)) {
-                return null;
-            }
-        }
-
         SunVolatileImage vi = new AccelTypedVolatileImage(this, width, height,
                                                           transparency, type);
         Surface sd = vi.getDestSurface();
--- a/jdk/src/java.desktop/macosx/classes/sun/java2d/opengl/CGLSurfaceData.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/macosx/classes/sun/java2d/opengl/CGLSurfaceData.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2011, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011, 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
@@ -51,9 +51,6 @@
     private native void initOps(long pConfigInfo, long pPeerData, long layerPtr,
                                 int xoff, int yoff, boolean isOpaque);
 
-    protected native boolean initPbuffer(long pData, long pConfigInfo,
-            boolean isOpaque, int width, int height);
-
     protected CGLSurfaceData(CGLGraphicsConfig gc, ColorModel cm, int type,
                              int width, int height) {
         super(gc, cm, type);
@@ -139,7 +136,7 @@
 
     /**
      * Creates a SurfaceData object representing an off-screen buffer (either a
-     * Pbuffer or Texture).
+     * FBO or Texture).
      */
     public static CGLOffScreenSurfaceData createData(CGLGraphicsConfig gc,
             int width, int height, ColorModel cm, Image image, int type) {
--- a/jdk/src/java.desktop/macosx/classes/sun/java2d/opengl/CGLVolatileSurfaceManager.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/macosx/classes/sun/java2d/opengl/CGLVolatileSurfaceManager.java	Wed Jul 05 20:42:36 2017 +0200
@@ -45,7 +45,7 @@
 
 public class CGLVolatileSurfaceManager extends VolatileSurfaceManager {
 
-    private boolean accelerationEnabled;
+    private final boolean accelerationEnabled;
 
     public CGLVolatileSurfaceManager(SunVolatileImage vImg, Object context) {
         super(vImg, context);
@@ -53,18 +53,13 @@
         /*
          * We will attempt to accelerate this image only under the
          * following conditions:
-         *   - the image is opaque OR
-         *   - the image is translucent AND
-         *       - the GraphicsConfig supports the FBO extension OR
-         *       - the GraphicsConfig has a stored alpha channel
+         *   - the image is not bitmask AND the GraphicsConfig supports the FBO
+         *     extension
          */
         int transparency = vImg.getTransparency();
-        CGLGraphicsConfig gc = (CGLGraphicsConfig)vImg.getGraphicsConfig();
-        accelerationEnabled =
-            (transparency == Transparency.OPAQUE) ||
-            ((transparency == Transparency.TRANSLUCENT) &&
-             (gc.isCapPresent(CAPS_EXT_FBOBJECT) ||
-              gc.isCapPresent(CAPS_STORED_ALPHA)));
+        CGLGraphicsConfig gc = (CGLGraphicsConfig) vImg.getGraphicsConfig();
+        accelerationEnabled = gc.isCapPresent(CAPS_EXT_FBOBJECT)
+                && transparency != Transparency.BITMASK;
     }
 
     protected boolean isAccelerationEnabled() {
@@ -72,7 +67,7 @@
     }
 
     /**
-     * Create a pbuffer-based SurfaceData object (or init the backbuffer
+     * Create a FBO-based SurfaceData object (or init the backbuffer
      * of an existing window if this is a double buffered GraphicsConfig)
      */
     protected SurfaceData initAcceleratedSurface() {
@@ -113,10 +108,9 @@
                 ColorModel cm = gc.getColorModel(vImg.getTransparency());
                 int type = vImg.getForcedAccelSurfaceType();
                 // if acceleration type is forced (type != UNDEFINED) then
-                // use the forced type, otherwise choose one based on caps
+                // use the forced type, otherwise choose FBOBJECT
                 if (type == OGLSurfaceData.UNDEFINED) {
-                    type = gc.isCapPresent(CAPS_EXT_FBOBJECT) ?
-                        OGLSurfaceData.FBOBJECT : OGLSurfaceData.PBUFFER;
+                    type = OGLSurfaceData.FBOBJECT;
                 }
                 if (createVSynced) {
                     // TODO: modify parameter to delegate
--- a/jdk/src/java.desktop/macosx/classes/sun/lwawt/LWToolkit.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/macosx/classes/sun/lwawt/LWToolkit.java	Wed Jul 05 20:42:36 2017 +0200
@@ -35,7 +35,7 @@
 import java.util.*;
 
 import sun.awt.*;
-import sun.misc.InnocuousThread;
+import sun.misc.ManagedLocalsThread;
 import sun.print.*;
 import sun.awt.util.ThreadGroupUtils;
 
@@ -77,22 +77,13 @@
                 shutdown();
                 waitForRunState(STATE_CLEANUP);
             };
-            Thread shutdown;
-            if (System.getSecurityManager() == null) {
-                shutdown = new Thread(ThreadGroupUtils.getRootThreadGroup(), shutdownRunnable);
-            } else {
-                shutdown = new InnocuousThread(shutdownRunnable);
-            }
+            Thread shutdown = new ManagedLocalsThread(
+                    ThreadGroupUtils.getRootThreadGroup(), shutdownRunnable);
             shutdown.setContextClassLoader(null);
             Runtime.getRuntime().addShutdownHook(shutdown);
-
             String name = "AWT-LW";
-            Thread toolkitThread;
-            if (System.getSecurityManager() == null) {
-                toolkitThread = new Thread(ThreadGroupUtils.getRootThreadGroup(), LWToolkit.this, name);
-            } else {
-                toolkitThread = new InnocuousThread(LWToolkit.this, name);
-            }
+            Thread toolkitThread = new ManagedLocalsThread(
+                    ThreadGroupUtils.getRootThreadGroup(), this, name);
             toolkitThread.setDaemon(true);
             toolkitThread.setPriority(Thread.NORM_PRIORITY + 1);
             toolkitThread.start();
--- a/jdk/src/java.desktop/macosx/classes/sun/lwawt/macosx/CDragSourceContextPeer.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/macosx/classes/sun/lwawt/macosx/CDragSourceContextPeer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -181,13 +181,7 @@
                     }
                 }
             };
-            Thread dragThread;
-            if (System.getSecurityManager() == null) {
-                dragThread = new Thread(dragRunnable);
-            } else {
-                dragThread = new ManagedLocalsThread(dragRunnable);
-            }
-            dragThread.start();
+            new ManagedLocalsThread(dragRunnable).start();
         } catch (Exception e) {
             final long nativeDragSource = getNativeContext();
             setNativeContext(0);
--- a/jdk/src/java.desktop/macosx/classes/sun/lwawt/macosx/CFileDialog.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/macosx/classes/sun/lwawt/macosx/CFileDialog.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2011, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011, 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
@@ -120,11 +120,7 @@
         if (visible) {
             // Java2 Dialog class requires peer to run code in a separate thread
             // and handles keeping the call modal
-            if (System.getSecurityManager() == null) {
-                new Thread(new Task()).start();
-            } else {
-                new ManagedLocalsThread(new Task()).start();
-            }
+            new ManagedLocalsThread(new Task()).start();
         }
         // We hide ourself before "show" returns - setVisible(false)
         // doesn't apply
--- a/jdk/src/java.desktop/macosx/classes/sun/lwawt/macosx/CPrinterDialogPeer.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/macosx/classes/sun/lwawt/macosx/CPrinterDialogPeer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -59,11 +59,7 @@
                 printerDialog.setRetVal(printerDialog.showDialog());
                 printerDialog.setVisible(false);
             };
-            if (System.getSecurityManager() == null) {
-                new Thread(task).start();
-            } else {
-                new ManagedLocalsThread(task).start();
-            }
+            new ManagedLocalsThread(task).start();
         }
     }
 
--- a/jdk/src/java.desktop/macosx/classes/sun/lwawt/macosx/CPrinterJob.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/macosx/classes/sun/lwawt/macosx/CPrinterJob.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2011, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011, 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
@@ -736,12 +736,7 @@
 
     // upcall from native
     private static void detachPrintLoop(final long target, final long arg) {
-        Runnable task = () -> _safePrintLoop(target, arg);
-        if (System.getSecurityManager() == null) {
-            new Thread(task).start();
-        } else {
-            new ManagedLocalsThread(task).start();
-        }
+        new ManagedLocalsThread(() -> _safePrintLoop(target, arg)).start();
     }
     private static native void _safePrintLoop(long target, long arg);
 
@@ -779,4 +774,4 @@
                 (float) (paper.getImageableHeight() / dpi),
                 MediaPrintableArea.INCH);
     }
-}
\ No newline at end of file
+}
--- a/jdk/src/java.desktop/macosx/native/libawt_lwawt/awt/LWCToolkit.m	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/macosx/native/libawt_lwawt/awt/LWCToolkit.m	Wed Jul 05 20:42:36 2017 +0200
@@ -376,7 +376,7 @@
     if ([sharedApp isKindOfClass:[NSApplicationAWT class]]) {
         NSApplicationAWT* theApp = (NSApplicationAWT*)sharedApp;
         [theApp postDummyEvent];
-        [theApp waitForDummyEvent];
+        [theApp waitForDummyEvent:timeout];
     } else {
         // could happen if we are embedded inside SWT application,
         // in this case just spin a single empty block through 
--- a/jdk/src/java.desktop/macosx/native/libawt_lwawt/java2d/opengl/CGLGraphicsConfig.m	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/macosx/native/libawt_lwawt/java2d/opengl/CGLGraphicsConfig.m	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2011, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011, 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
@@ -63,7 +63,7 @@
 
         CGLCtxInfo *ctxinfo = (CGLCtxInfo *)oglc->ctxInfo;
         if (ctxinfo != NULL) {
-            NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];        
+            NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
             [NSOpenGLContext clearCurrentContext];
             [ctxinfo->context clearDrawable];
             [ctxinfo->context release];
@@ -342,18 +342,10 @@
     if (value != 0) {
         caps |= CAPS_DOUBLEBUFFERED;
     }
-    [sharedPixelFormat
-        getValues: &value
-        forAttribute: NSOpenGLPFAAlphaSize
-        forVirtualScreen: contextVirtualScreen];
-    if (value != 0) {
-        caps |= CAPS_STORED_ALPHA;
-    }
 
-    J2dRlsTraceLn2(J2D_TRACE_INFO,
-                   "CGLGraphicsConfig_getCGLConfigInfo: db=%d alpha=%d",
-                   (caps & CAPS_DOUBLEBUFFERED) != 0,
-                   (caps & CAPS_STORED_ALPHA) != 0);
+    J2dRlsTraceLn1(J2D_TRACE_INFO,
+                   "CGLGraphicsConfig_getCGLConfigInfo: db=%d",
+                   (caps & CAPS_DOUBLEBUFFERED) != 0);
 
     // remove before shipping (?)
 #if 1
--- a/jdk/src/java.desktop/macosx/native/libawt_lwawt/java2d/opengl/CGLSurfaceData.h	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/macosx/native/libawt_lwawt/java2d/opengl/CGLSurfaceData.h	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2011, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011, 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
@@ -39,7 +39,6 @@
     AWTView               *peerData;
     CGLLayer              *layer;
     GLclampf              argb[4]; // background clear color
-    NSOpenGLPixelBuffer   *pbuffer;
     CGLGraphicsConfigInfo *configInfo;
 } CGLSDOps;
 
--- a/jdk/src/java.desktop/macosx/native/libawt_lwawt/java2d/opengl/CGLSurfaceData.m	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/macosx/native/libawt_lwawt/java2d/opengl/CGLSurfaceData.m	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2011, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011, 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
@@ -110,9 +110,7 @@
 
 /**
  * This function disposes of any native windowing system resources associated
- * with this surface.  For instance, if the given OGLSDOps is of type
- * OGLSD_PBUFFER, this method implementation will destroy the actual pbuffer
- * surface.
+ * with this surface.
  */
 void
 OGLSD_DestroyOGLSurface(JNIEnv *env, OGLSDOps *oglsdo)
@@ -122,16 +120,7 @@
 JNF_COCOA_ENTER(env);
 
     CGLSDOps *cglsdo = (CGLSDOps *)oglsdo->privOps;
-    if (oglsdo->drawableType == OGLSD_PBUFFER) {
-        if (oglsdo->textureID != 0) {
-            j2d_glDeleteTextures(1, &oglsdo->textureID);
-            oglsdo->textureID = 0;
-        }
-        if (cglsdo->pbuffer != NULL) {
-            [cglsdo->pbuffer release];
-            cglsdo->pbuffer = NULL;
-        }
-    } else if (oglsdo->drawableType == OGLSD_WINDOW) {
+    if (oglsdo->drawableType == OGLSD_WINDOW) {
         // detach the NSView from the NSOpenGLContext
         CGLGraphicsConfigInfo *cglInfo = cglsdo->configInfo;
         OGLContext *oglc = cglInfo->context;
@@ -277,23 +266,12 @@
 
 JNF_COCOA_ENTER(env);
 
-    // set the current surface
-    if (dstOps->drawableType == OGLSD_PBUFFER) {
-        // REMIND: pbuffers are not fully tested yet...
-        [ctxinfo->context clearDrawable];
+    CGLSDOps *cglsdo = (CGLSDOps *)dstOps->privOps;
+    NSView *nsView = (NSView *)cglsdo->peerData;
+
+    if ([ctxinfo->context view] != nsView) {
         [ctxinfo->context makeCurrentContext];
-        [ctxinfo->context setPixelBuffer: dstCGLOps->pbuffer
-                cubeMapFace: 0
-                mipMapLevel: 0
-                currentVirtualScreen: [ctxinfo->context currentVirtualScreen]];
-    } else {
-        CGLSDOps *cglsdo = (CGLSDOps *)dstOps->privOps;
-        NSView *nsView = (NSView *)cglsdo->peerData;
-
-        if ([ctxinfo->context view] != nsView) {
-            [ctxinfo->context makeCurrentContext];
-            [ctxinfo->context setView: nsView];
-        }
+        [ctxinfo->context setView: nsView];
     }
 
     if (OGLC_IS_CAP_PRESENT(oglc, CAPS_EXT_FBOBJECT)) {
@@ -303,16 +281,6 @@
         j2d_glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0);
     }
 
-    if ((srcOps != dstOps) && (srcOps->drawableType == OGLSD_PBUFFER)) {
-        // bind pbuffer to the render texture object (since we are preparing
-        // to copy from the pbuffer)
-        CGLSDOps *srcCGLOps = (CGLSDOps *)srcOps->privOps;
-        j2d_glBindTexture(GL_TEXTURE_2D, srcOps->textureID);
-        [ctxinfo->context
-                setTextureImageToPixelBuffer: srcCGLOps->pbuffer
-                colorBuffer: GL_FRONT];
-    }
-
 JNF_COCOA_EXIT(env);
 
     return oglc;
@@ -464,105 +432,6 @@
     cglsdo->layer = NULL;
 }
 
-JNIEXPORT jboolean JNICALL
-Java_sun_java2d_opengl_CGLSurfaceData_initPbuffer
-    (JNIEnv *env, jobject cglsd,
-     jlong pData, jlong pConfigInfo, jboolean isOpaque,
-     jint width, jint height)
-{
-    J2dTraceLn3(J2D_TRACE_INFO, "CGLSurfaceData_initPbuffer: w=%d h=%d opq=%d", width, height, isOpaque);
-
-    OGLSDOps *oglsdo = (OGLSDOps *)jlong_to_ptr(pData);
-    if (oglsdo == NULL) {
-        J2dRlsTraceLn(J2D_TRACE_ERROR, "CGLSurfaceData_initPbuffer: ops are null");
-        return JNI_FALSE;
-    }
-
-    CGLSDOps *cglsdo = (CGLSDOps *)oglsdo->privOps;
-    if (cglsdo == NULL) {
-        J2dRlsTraceLn(J2D_TRACE_ERROR, "CGLSurfaceData_initPbuffer: cgl ops are null");
-        return JNI_FALSE;
-    }
-
-    CGLGraphicsConfigInfo *cglInfo = (CGLGraphicsConfigInfo *)
-        jlong_to_ptr(pConfigInfo);
-    if (cglInfo == NULL) {
-        J2dRlsTraceLn(J2D_TRACE_ERROR, "CGLSurfaceData_initPbuffer: cgl config info is null");
-        return JNI_FALSE;
-    }
-
-    // find the maximum allowable texture dimensions (this value ultimately
-    // determines our maximum pbuffer size)
-    int pbMax = 0;
-    j2d_glGetIntegerv(GL_MAX_TEXTURE_SIZE, &pbMax);
-
-    int pbWidth = 0;
-    int pbHeight = 0;
-    if (OGLC_IS_CAP_PRESENT(cglInfo->context, CAPS_TEXNONPOW2)) {
-        // use non-power-of-two dimensions directly
-        pbWidth = (width <= pbMax) ? width : 0;
-        pbHeight = (height <= pbMax) ? height : 0;
-    } else {
-        // find the appropriate power-of-two dimensions
-        pbWidth = OGLSD_NextPowerOfTwo(width, pbMax);
-        pbHeight = OGLSD_NextPowerOfTwo(height, pbMax);
-    }
-
-    J2dTraceLn3(J2D_TRACE_VERBOSE, "  desired pbuffer dimensions: w=%d h=%d max=%d", pbWidth, pbHeight, pbMax);
-
-    // if either dimension is 0, we cannot allocate a pbuffer/texture with the
-    // requested dimensions
-    if (pbWidth == 0 || pbHeight == 0) {
-        J2dRlsTraceLn(J2D_TRACE_ERROR, "CGLSurfaceData_initPbuffer: dimensions too large");
-        return JNI_FALSE;
-    }
-
-    int format = isOpaque ? GL_RGB : GL_RGBA;
-
-JNF_COCOA_ENTER(env);
-
-    cglsdo->pbuffer =
-        [[NSOpenGLPixelBuffer alloc]
-            initWithTextureTarget: GL_TEXTURE_2D
-            textureInternalFormat: format
-            textureMaxMipMapLevel: 0
-            pixelsWide: pbWidth
-            pixelsHigh: pbHeight];
-    if (cglsdo->pbuffer == nil) {
-        J2dRlsTraceLn(J2D_TRACE_ERROR, "CGLSurfaceData_initPbuffer: could not create pbuffer");
-        return JNI_FALSE;
-    }
-
-    // make sure the actual dimensions match those that we requested
-    GLsizei actualWidth  = [cglsdo->pbuffer pixelsWide];
-    GLsizei actualHeight = [cglsdo->pbuffer pixelsHigh];
-    if (actualWidth != pbWidth || actualHeight != pbHeight) {
-        J2dRlsTraceLn2(J2D_TRACE_ERROR, "CGLSurfaceData_initPbuffer: actual (w=%d h=%d) != requested", actualWidth, actualHeight);
-        [cglsdo->pbuffer release];
-        return JNI_FALSE;
-    }
-
-    GLuint texID = 0;
-    j2d_glGenTextures(1, &texID);
-    j2d_glBindTexture(GL_TEXTURE_2D, texID);
-
-    oglsdo->drawableType = OGLSD_PBUFFER;
-    oglsdo->isOpaque = isOpaque;
-    oglsdo->width = width;
-    oglsdo->height = height;
-    oglsdo->textureID = texID;
-    oglsdo->textureWidth = pbWidth;
-    oglsdo->textureHeight = pbHeight;
-    oglsdo->activeBuffer = GL_FRONT;
-    oglsdo->needsInit = JNI_TRUE;
-
-    OGLSD_INIT_TEXTURE_FILTER(oglsdo, GL_NEAREST);
-
-JNF_COCOA_EXIT(env);
-
-    return JNI_TRUE;
-}
-
 #pragma mark -
 #pragma mark "--- CGLSurfaceData methods - Mac OS X specific ---"
 
--- a/jdk/src/java.desktop/macosx/native/libosxapp/NSApplicationAWT.h	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/macosx/native/libosxapp/NSApplicationAWT.h	Wed Jul 05 20:42:36 2017 +0200
@@ -38,7 +38,7 @@
 - (void) setDockIconWithEnv:(JNIEnv *)env;
 - (void) postDummyEvent;
 - (void) postRunnableEvent:(void (^)())block;
-- (void) waitForDummyEvent;
+- (void) waitForDummyEvent:(long long) timeout;
 
 + (void) runAWTLoopWithApp:(NSApplication*)app;
 
--- a/jdk/src/java.desktop/macosx/native/libosxapp/NSApplicationAWT.m	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/macosx/native/libosxapp/NSApplicationAWT.m	Wed Jul 05 20:42:36 2017 +0200
@@ -398,8 +398,14 @@
     [pool drain];
 }
 
-- (void)waitForDummyEvent {
-    [seenDummyEventLock lockWhenCondition:YES];
+- (void)waitForDummyEvent:(long long) timeout {
+    if (timeout >= 0) {
+        double sec = ((double) timeout)/1000;
+        [seenDummyEventLock lockWhenCondition:YES
+                               beforeDate:[NSDate dateWithTimeIntervalSinceNow:sec]];
+    } else {
+        [seenDummyEventLock lockWhenCondition:YES];
+    }
     [seenDummyEventLock unlock];
     [seenDummyEventLock release];
 
--- a/jdk/src/java.desktop/macosx/native/libsplashscreen/splashscreen_sys.m	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/macosx/native/libsplashscreen/splashscreen_sys.m	Wed Jul 05 20:42:36 2017 +0200
@@ -275,7 +275,6 @@
         [image addRepresentation: rep];
         float scaleFactor = splash->scaleFactor;
         if (scaleFactor > 0 && scaleFactor != 1) {
-            [image setScalesWhenResized:YES];
             NSSize size = [image size];
             size.width /= scaleFactor;
             size.height /= scaleFactor;
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.desktop/share/classes/META-INF/services/java.net.ContentHandlerFactory	Wed Jul 05 20:42:36 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.  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.
+#
+
+# Provider for content handlers
+sun.awt.www.content.MultimediaContentHandlers
--- a/jdk/src/java.desktop/share/classes/com/sun/imageio/stream/StreamCloser.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/com/sun/imageio/stream/StreamCloser.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -26,7 +26,7 @@
 package com.sun.imageio.stream;
 
 import sun.awt.util.ThreadGroupUtils;
-import sun.misc.InnocuousThread;
+import sun.misc.ManagedLocalsThread;
 
 import java.io.IOException;
 import java.security.AccessController;
@@ -87,17 +87,13 @@
                 };
 
                 AccessController.doPrivileged((PrivilegedAction<Object>) () -> {
-                    if (System.getSecurityManager() == null) {
-                        /* The thread must be a member of a thread group
-                         * which will not get GCed before VM exit.
-                         * Make its parent the top-level thread group.
-                         */
-                        ThreadGroup tg = ThreadGroupUtils.getRootThreadGroup();
-                        streamCloser = new Thread(tg, streamCloserRunnable);
-                    } else {
-                        /* InnocuousThread is a member of a correct TG by default */
-                        streamCloser = new InnocuousThread(streamCloserRunnable);
-                    }
+                    /* The thread must be a member of a thread group
+                     * which will not get GCed before VM exit.
+                     * Make its parent the top-level thread group.
+                     */
+                    ThreadGroup tg = ThreadGroupUtils.getRootThreadGroup();
+                    streamCloser = new ManagedLocalsThread(tg,
+                                                           streamCloserRunnable);
                     /* Set context class loader to null in order to avoid
                      * keeping a strong reference to an application classloader.
                      */
--- a/jdk/src/java.desktop/share/classes/com/sun/java/swing/plaf/windows/WindowsLookAndFeel.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/com/sun/java/swing/plaf/windows/WindowsLookAndFeel.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 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
@@ -2038,11 +2038,7 @@
             if (audioRunnable != null) {
                 // Runnable appears to block until completed playing, hence
                 // start up another thread to handle playing.
-                if (System.getSecurityManager() == null) {
-                    new Thread(audioRunnable).start();
-                } else {
-                    new ManagedLocalsThread(audioRunnable).start();
-                }
+                new ManagedLocalsThread(audioRunnable).start();
             }
         }
     }
--- a/jdk/src/java.desktop/share/classes/com/sun/media/sound/JSSecurityManager.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/com/sun/media/sound/JSSecurityManager.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1999, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1999, 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
@@ -25,7 +25,6 @@
 
 package com.sun.media.sound;
 
-import sun.misc.InnocuousThread;
 import sun.misc.ManagedLocalsThread;
 
 import java.io.BufferedInputStream;
@@ -147,12 +146,7 @@
                                final String threadName,
                                final boolean isDaemon, final int priority,
                                final boolean doStart) {
-        Thread thread;
-        if (System.getSecurityManager() == null) {
-            thread = new Thread(runnable);
-        } else {
-            thread = new ManagedLocalsThread(runnable);
-        }
+        Thread thread = new ManagedLocalsThread(runnable);
 
         if (threadName != null) {
             thread.setName(threadName);
--- a/jdk/src/java.desktop/share/classes/com/sun/media/sound/SoftAudioPusher.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/com/sun/media/sound/SoftAudioPusher.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2007, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2007, 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
@@ -55,11 +55,7 @@
         if (active)
             return;
         active = true;
-        if (System.getSecurityManager() == null) {
-            audiothread = new Thread(this);
-        } else {
-            audiothread = new ManagedLocalsThread(this);
-        }
+        audiothread = new ManagedLocalsThread(this);
         audiothread.setDaemon(true);
         audiothread.setPriority(Thread.MAX_PRIORITY);
         audiothread.start();
--- a/jdk/src/java.desktop/share/classes/com/sun/media/sound/SoftJitterCorrector.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/com/sun/media/sound/SoftJitterCorrector.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2007, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2007, 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
@@ -216,11 +216,7 @@
                 }
             };
 
-            if (System.getSecurityManager() == null) {
-                thread = new Thread(runnable);
-            } else {
-                thread = new ManagedLocalsThread(runnable);
-            }
+            thread = new ManagedLocalsThread(runnable);
             thread.setDaemon(true);
             thread.setPriority(Thread.MAX_PRIORITY);
             thread.start();
--- a/jdk/src/java.desktop/share/classes/com/sun/media/sound/SoftSynthesizer.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/com/sun/media/sound/SoftSynthesizer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2008, 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
@@ -141,11 +141,7 @@
                      pusher = null;
                      jitter_stream = null;
                      sourceDataLine = null;
-                     if (System.getSecurityManager() == null) {
-                        new Thread(runnable).start();
-                     } else {
-                         new ManagedLocalsThread(runnable).start();
-                     }
+                     new ManagedLocalsThread(runnable).start();
                  }
                  return len;
              }
--- a/jdk/src/java.desktop/share/classes/java/awt/EventDispatchThread.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/java/awt/EventDispatchThread.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1996, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1996, 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
@@ -67,7 +67,7 @@
     private ArrayList<EventFilter> eventFilters = new ArrayList<EventFilter>();
 
     EventDispatchThread(ThreadGroup group, String name, EventQueue queue) {
-        super(group, null, name);
+        super(group, name);
         setEventQueue(queue);
     }
 
--- a/jdk/src/java.desktop/share/classes/java/awt/font/NumericShaper.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/java/awt/font/NumericShaper.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 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
@@ -318,7 +318,17 @@
         /**
          * The Meetei Mayek range with the Meetei Mayek digits.
          */
-        MEETEI_MAYEK    ('\uabf0', '\uabc0', '\uac00');
+        MEETEI_MAYEK    ('\uabf0', '\uabc0', '\uac00'),
+        /**
+         * The Sinhala range with the Sinhala digits.
+         * @since 1.9
+         */
+        SINHALA         ('\u0de6', '\u0d80', '\u0e00'),
+        /**
+         * The Myanmar Extended-B range with the Myanmar Tai Laing digits.
+         * @since 1.9
+         */
+        MYANMAR_TAI_LAING ('\ua9f0', '\ua9e0', '\uaa00');
 
         private static int toRangeIndex(Range script) {
             int index = script.ordinal();
@@ -624,15 +634,25 @@
         0x02e5, 0x02ee,
         0x02ef, 0x0370,
         0x0374, 0x0376,
-        0x037e, 0x0386,
+        0x0378, 0x037a,
+        0x037e, 0x037f,
+        0x0380, 0x0386,
         0x0387, 0x0388,
+        0x038b, 0x038c,
+        0x038d, 0x038e,
+        0x03a2, 0x03a3,
         0x03f6, 0x03f7,
         0x0483, 0x048a,
-        0x058a, 0x05be,
+        0x0530, 0x0531,
+        0x0557, 0x0559,
+        0x0560, 0x0561,
+        0x0588, 0x0589,
+        0x058a, 0x0590,
+        0x0591, 0x05be,
         0x05bf, 0x05c0,
         0x05c1, 0x05c3,
         0x05c4, 0x05c6,
-        0x05c7, 0x05d0,
+        0x05c7, 0x05c8,
         0x0600, 0x0608,
         0x0609, 0x060b,
         0x060c, 0x060d,
@@ -643,15 +663,15 @@
         0x06e7, 0x06ee,
         0x06f0, 0x06fa,
         0x0711, 0x0712,
-        0x0730, 0x074d,
+        0x0730, 0x074b,
         0x07a6, 0x07b1,
         0x07eb, 0x07f4,
         0x07f6, 0x07fa,
         0x0816, 0x081a,
         0x081b, 0x0824,
         0x0825, 0x0828,
-        0x0829, 0x0830,
-        0x0859, 0x085e,
+        0x0829, 0x082e,
+        0x0859, 0x085c,
         0x08e4, 0x0903,
         0x093a, 0x093b,
         0x093c, 0x093d,
@@ -660,57 +680,161 @@
         0x0951, 0x0958,
         0x0962, 0x0964,
         0x0981, 0x0982,
-        0x09bc, 0x09bd,
+        0x0984, 0x0985,
+        0x098d, 0x098f,
+        0x0991, 0x0993,
+        0x09a9, 0x09aa,
+        0x09b1, 0x09b2,
+        0x09b3, 0x09b6,
+        0x09ba, 0x09bd,
         0x09c1, 0x09c7,
+        0x09c9, 0x09cb,
         0x09cd, 0x09ce,
+        0x09cf, 0x09d7,
+        0x09d8, 0x09dc,
+        0x09de, 0x09df,
         0x09e2, 0x09e6,
         0x09f2, 0x09f4,
         0x09fb, 0x0a03,
-        0x0a3c, 0x0a3e,
+        0x0a04, 0x0a05,
+        0x0a0b, 0x0a0f,
+        0x0a11, 0x0a13,
+        0x0a29, 0x0a2a,
+        0x0a31, 0x0a32,
+        0x0a34, 0x0a35,
+        0x0a37, 0x0a38,
+        0x0a3a, 0x0a3e,
         0x0a41, 0x0a59,
+        0x0a5d, 0x0a5e,
+        0x0a5f, 0x0a66,
         0x0a70, 0x0a72,
         0x0a75, 0x0a83,
-        0x0abc, 0x0abd,
+        0x0a84, 0x0a85,
+        0x0a8e, 0x0a8f,
+        0x0a92, 0x0a93,
+        0x0aa9, 0x0aaa,
+        0x0ab1, 0x0ab2,
+        0x0ab4, 0x0ab5,
+        0x0aba, 0x0abd,
         0x0ac1, 0x0ac9,
+        0x0aca, 0x0acb,
         0x0acd, 0x0ad0,
+        0x0ad1, 0x0ae0,
         0x0ae2, 0x0ae6,
         0x0af1, 0x0b02,
-        0x0b3c, 0x0b3d,
+        0x0b04, 0x0b05,
+        0x0b0d, 0x0b0f,
+        0x0b11, 0x0b13,
+        0x0b29, 0x0b2a,
+        0x0b31, 0x0b32,
+        0x0b34, 0x0b35,
+        0x0b3a, 0x0b3d,
         0x0b3f, 0x0b40,
         0x0b41, 0x0b47,
+        0x0b49, 0x0b4b,
         0x0b4d, 0x0b57,
+        0x0b58, 0x0b5c,
+        0x0b5e, 0x0b5f,
         0x0b62, 0x0b66,
-        0x0b82, 0x0b83,
+        0x0b78, 0x0b83,
+        0x0b84, 0x0b85,
+        0x0b8b, 0x0b8e,
+        0x0b91, 0x0b92,
+        0x0b96, 0x0b99,
+        0x0b9b, 0x0b9c,
+        0x0b9d, 0x0b9e,
+        0x0ba0, 0x0ba3,
+        0x0ba5, 0x0ba8,
+        0x0bab, 0x0bae,
+        0x0bba, 0x0bbe,
         0x0bc0, 0x0bc1,
+        0x0bc3, 0x0bc6,
+        0x0bc9, 0x0bca,
         0x0bcd, 0x0bd0,
+        0x0bd1, 0x0bd7,
+        0x0bd8, 0x0be6,
         0x0bf3, 0x0c01,
+        0x0c04, 0x0c05,
+        0x0c0d, 0x0c0e,
+        0x0c11, 0x0c12,
+        0x0c29, 0x0c2a,
+        0x0c3a, 0x0c3d,
         0x0c3e, 0x0c41,
-        0x0c46, 0x0c58,
+        0x0c45, 0x0c58,
+        0x0c5a, 0x0c60,
         0x0c62, 0x0c66,
-        0x0c78, 0x0c7f,
-        0x0cbc, 0x0cbd,
+        0x0c70, 0x0c7f,
+        0x0c80, 0x0c82,
+        0x0c84, 0x0c85,
+        0x0c8d, 0x0c8e,
+        0x0c91, 0x0c92,
+        0x0ca9, 0x0caa,
+        0x0cb4, 0x0cb5,
+        0x0cba, 0x0cbd,
+        0x0cc5, 0x0cc6,
+        0x0cc9, 0x0cca,
         0x0ccc, 0x0cd5,
+        0x0cd7, 0x0cde,
+        0x0cdf, 0x0ce0,
         0x0ce2, 0x0ce6,
+        0x0cf0, 0x0cf1,
+        0x0cf3, 0x0d02,
+        0x0d04, 0x0d05,
+        0x0d0d, 0x0d0e,
+        0x0d11, 0x0d12,
+        0x0d3b, 0x0d3d,
         0x0d41, 0x0d46,
+        0x0d49, 0x0d4a,
         0x0d4d, 0x0d4e,
+        0x0d4f, 0x0d57,
+        0x0d58, 0x0d60,
         0x0d62, 0x0d66,
-        0x0dca, 0x0dcf,
+        0x0d76, 0x0d79,
+        0x0d80, 0x0d82,
+        0x0d84, 0x0d85,
+        0x0d97, 0x0d9a,
+        0x0db2, 0x0db3,
+        0x0dbc, 0x0dbd,
+        0x0dbe, 0x0dc0,
+        0x0dc7, 0x0dcf,
         0x0dd2, 0x0dd8,
+        0x0de0, 0x0de6,
+        0x0df0, 0x0df2,
+        0x0df5, 0x0e01,
         0x0e31, 0x0e32,
         0x0e34, 0x0e40,
         0x0e47, 0x0e4f,
+        0x0e5c, 0x0e81,
+        0x0e83, 0x0e84,
+        0x0e85, 0x0e87,
+        0x0e89, 0x0e8a,
+        0x0e8b, 0x0e8d,
+        0x0e8e, 0x0e94,
+        0x0e98, 0x0e99,
+        0x0ea0, 0x0ea1,
+        0x0ea4, 0x0ea5,
+        0x0ea6, 0x0ea7,
+        0x0ea8, 0x0eaa,
+        0x0eac, 0x0ead,
         0x0eb1, 0x0eb2,
         0x0eb4, 0x0ebd,
-        0x0ec8, 0x0ed0,
+        0x0ebe, 0x0ec0,
+        0x0ec5, 0x0ec6,
+        0x0ec7, 0x0ed0,
+        0x0eda, 0x0edc,
+        0x0ee0, 0x0f00,
         0x0f18, 0x0f1a,
         0x0f35, 0x0f36,
         0x0f37, 0x0f38,
         0x0f39, 0x0f3e,
-        0x0f71, 0x0f7f,
+        0x0f48, 0x0f49,
+        0x0f6d, 0x0f7f,
         0x0f80, 0x0f85,
         0x0f86, 0x0f88,
         0x0f8d, 0x0fbe,
         0x0fc6, 0x0fc7,
+        0x0fcd, 0x0fce,
+        0x0fdb, 0x1000,
         0x102d, 0x1031,
         0x1032, 0x1038,
         0x1039, 0x103b,
@@ -722,66 +846,119 @@
         0x1085, 0x1087,
         0x108d, 0x108e,
         0x109d, 0x109e,
-        0x135d, 0x1360,
+        0x10c6, 0x10c7,
+        0x10c8, 0x10cd,
+        0x10ce, 0x10d0,
+        0x1249, 0x124a,
+        0x124e, 0x1250,
+        0x1257, 0x1258,
+        0x1259, 0x125a,
+        0x125e, 0x1260,
+        0x1289, 0x128a,
+        0x128e, 0x1290,
+        0x12b1, 0x12b2,
+        0x12b6, 0x12b8,
+        0x12bf, 0x12c0,
+        0x12c1, 0x12c2,
+        0x12c6, 0x12c8,
+        0x12d7, 0x12d8,
+        0x1311, 0x1312,
+        0x1316, 0x1318,
+        0x135b, 0x1360,
+        0x137d, 0x1380,
         0x1390, 0x13a0,
-        0x1400, 0x1401,
+        0x13f5, 0x1401,
         0x1680, 0x1681,
         0x169b, 0x16a0,
+        0x16f9, 0x1700,
+        0x170d, 0x170e,
         0x1712, 0x1720,
         0x1732, 0x1735,
+        0x1737, 0x1740,
         0x1752, 0x1760,
-        0x1772, 0x1780,
+        0x176d, 0x176e,
+        0x1771, 0x1780,
         0x17b4, 0x17b6,
         0x17b7, 0x17be,
         0x17c6, 0x17c7,
         0x17c9, 0x17d4,
         0x17db, 0x17dc,
         0x17dd, 0x17e0,
-        0x17f0, 0x1810,
+        0x17ea, 0x1810,
+        0x181a, 0x1820,
+        0x1878, 0x1880,
         0x18a9, 0x18aa,
-        0x1920, 0x1923,
+        0x18ab, 0x18b0,
+        0x18f6, 0x1900,
+        0x191f, 0x1923,
         0x1927, 0x1929,
+        0x192c, 0x1930,
         0x1932, 0x1933,
         0x1939, 0x1946,
-        0x19de, 0x1a00,
+        0x196e, 0x1970,
+        0x1975, 0x1980,
+        0x19ac, 0x19b0,
+        0x19ca, 0x19d0,
+        0x19db, 0x1a00,
         0x1a17, 0x1a19,
+        0x1a1b, 0x1a1e,
         0x1a56, 0x1a57,
         0x1a58, 0x1a61,
         0x1a62, 0x1a63,
         0x1a65, 0x1a6d,
         0x1a73, 0x1a80,
-        0x1b00, 0x1b04,
+        0x1a8a, 0x1a90,
+        0x1a9a, 0x1aa0,
+        0x1aae, 0x1b04,
         0x1b34, 0x1b35,
         0x1b36, 0x1b3b,
         0x1b3c, 0x1b3d,
         0x1b42, 0x1b43,
+        0x1b4c, 0x1b50,
         0x1b6b, 0x1b74,
-        0x1b80, 0x1b82,
+        0x1b7d, 0x1b82,
         0x1ba2, 0x1ba6,
         0x1ba8, 0x1baa,
-        0x1bab, 0x1bac,
+        0x1bab, 0x1bae,
         0x1be6, 0x1be7,
         0x1be8, 0x1bea,
         0x1bed, 0x1bee,
         0x1bef, 0x1bf2,
+        0x1bf4, 0x1bfc,
         0x1c2c, 0x1c34,
         0x1c36, 0x1c3b,
-        0x1cd0, 0x1cd3,
+        0x1c4a, 0x1c4d,
+        0x1c80, 0x1cc0,
+        0x1cc8, 0x1cd3,
         0x1cd4, 0x1ce1,
         0x1ce2, 0x1ce9,
         0x1ced, 0x1cee,
         0x1cf4, 0x1cf5,
+        0x1cf7, 0x1d00,
         0x1dc0, 0x1e00,
+        0x1f16, 0x1f18,
+        0x1f1e, 0x1f20,
+        0x1f46, 0x1f48,
+        0x1f4e, 0x1f50,
+        0x1f58, 0x1f59,
+        0x1f5a, 0x1f5b,
+        0x1f5c, 0x1f5d,
+        0x1f5e, 0x1f5f,
+        0x1f7e, 0x1f80,
+        0x1fb5, 0x1fb6,
         0x1fbd, 0x1fbe,
         0x1fbf, 0x1fc2,
+        0x1fc5, 0x1fc6,
         0x1fcd, 0x1fd0,
-        0x1fdd, 0x1fe0,
+        0x1fd4, 0x1fd6,
+        0x1fdc, 0x1fe0,
         0x1fed, 0x1ff2,
+        0x1ff5, 0x1ff6,
         0x1ffd, 0x200e,
         0x2010, 0x2071,
-        0x2074, 0x207f,
+        0x2072, 0x207f,
         0x2080, 0x2090,
-        0x20a0, 0x2102,
+        0x209d, 0x2102,
         0x2103, 0x2107,
         0x2108, 0x210a,
         0x2114, 0x2115,
@@ -801,35 +978,59 @@
         0x24ea, 0x26ac,
         0x26ad, 0x2800,
         0x2900, 0x2c00,
+        0x2c2f, 0x2c30,
+        0x2c5f, 0x2c60,
         0x2ce5, 0x2ceb,
         0x2cef, 0x2cf2,
-        0x2cf9, 0x2d00,
-        0x2d7f, 0x2d80,
-        0x2de0, 0x3005,
+        0x2cf4, 0x2d00,
+        0x2d26, 0x2d27,
+        0x2d28, 0x2d2d,
+        0x2d2e, 0x2d30,
+        0x2d68, 0x2d6f,
+        0x2d71, 0x2d80,
+        0x2d97, 0x2da0,
+        0x2da7, 0x2da8,
+        0x2daf, 0x2db0,
+        0x2db7, 0x2db8,
+        0x2dbf, 0x2dc0,
+        0x2dc7, 0x2dc8,
+        0x2dcf, 0x2dd0,
+        0x2dd7, 0x2dd8,
+        0x2ddf, 0x3005,
         0x3008, 0x3021,
-        0x302a, 0x3031,
+        0x302a, 0x302e,
+        0x3030, 0x3031,
         0x3036, 0x3038,
         0x303d, 0x3041,
-        0x3099, 0x309d,
+        0x3097, 0x309d,
         0x30a0, 0x30a1,
         0x30fb, 0x30fc,
-        0x31c0, 0x31f0,
+        0x3100, 0x3105,
+        0x312e, 0x3131,
+        0x318f, 0x3190,
+        0x31bb, 0x31f0,
         0x321d, 0x3220,
         0x3250, 0x3260,
         0x327c, 0x327f,
         0x32b1, 0x32c0,
         0x32cc, 0x32d0,
+        0x32ff, 0x3300,
         0x3377, 0x337b,
         0x33de, 0x33e0,
         0x33ff, 0x3400,
-        0x4dc0, 0x4e00,
-        0xa490, 0xa4d0,
+        0x4db6, 0x4e00,
+        0x9fcd, 0xa000,
+        0xa48d, 0xa4d0,
         0xa60d, 0xa610,
+        0xa62c, 0xa640,
         0xa66f, 0xa680,
-        0xa69f, 0xa6a0,
+        0xa69e, 0xa6a0,
         0xa6f0, 0xa6f2,
-        0xa700, 0xa722,
+        0xa6f8, 0xa722,
         0xa788, 0xa789,
+        0xa78f, 0xa790,
+        0xa7ae, 0xa7b0,
+        0xa7b2, 0xa7f7,
         0xa802, 0xa803,
         0xa806, 0xa807,
         0xa80b, 0xa80c,
@@ -838,77 +1039,241 @@
         0xa838, 0xa840,
         0xa874, 0xa880,
         0xa8c4, 0xa8ce,
-        0xa8e0, 0xa8f2,
+        0xa8da, 0xa8f2,
+        0xa8fc, 0xa900,
         0xa926, 0xa92e,
         0xa947, 0xa952,
-        0xa980, 0xa983,
+        0xa954, 0xa95f,
+        0xa97d, 0xa983,
         0xa9b3, 0xa9b4,
         0xa9b6, 0xa9ba,
         0xa9bc, 0xa9bd,
+        0xa9ce, 0xa9cf,
+        0xa9da, 0xa9de,
+        0xa9e5, 0xa9e6,
+        0xa9ff, 0xaa00,
         0xaa29, 0xaa2f,
         0xaa31, 0xaa33,
         0xaa35, 0xaa40,
         0xaa43, 0xaa44,
         0xaa4c, 0xaa4d,
+        0xaa4e, 0xaa50,
+        0xaa5a, 0xaa5c,
+        0xaa7c, 0xaa7d,
         0xaab0, 0xaab1,
         0xaab2, 0xaab5,
         0xaab7, 0xaab9,
         0xaabe, 0xaac0,
         0xaac1, 0xaac2,
+        0xaac3, 0xaadb,
         0xaaec, 0xaaee,
         0xaaf6, 0xab01,
+        0xab07, 0xab09,
+        0xab0f, 0xab11,
+        0xab17, 0xab20,
+        0xab27, 0xab28,
+        0xab2f, 0xab30,
+        0xab60, 0xab64,
+        0xab66, 0xabc0,
         0xabe5, 0xabe6,
         0xabe8, 0xabe9,
         0xabed, 0xabf0,
+        0xabfa, 0xac00,
+        0xd7a4, 0xd7b0,
+        0xd7c7, 0xd7cb,
+        0xd7fc, 0xe000,
+        0xfa6e, 0xfa70,
+        0xfada, 0xfb00,
+        0xfb07, 0xfb13,
+        0xfb18, 0xfb1d,
         0xfb1e, 0xfb1f,
         0xfb29, 0xfb2a,
-        0xfd3e, 0xfd50,
-        0xfdfd, 0xfe70,
+        0xfd3e, 0xfd40,
+        0xfdd0, 0xfdf0,
+        0xfdfd, 0xfdfe,
+        0xfe00, 0xfe70,
         0xfeff, 0xff21,
         0xff3b, 0xff41,
         0xff5b, 0xff66,
-        0xffe0, 0x10000,
+        0xffbf, 0xffc2,
+        0xffc8, 0xffca,
+        0xffd0, 0xffd2,
+        0xffd8, 0xffda,
+        0xffdd, 0x10000,
+        0x1000c, 0x1000d,
+        0x10027, 0x10028,
+        0x1003b, 0x1003c,
+        0x1003e, 0x1003f,
+        0x1004e, 0x10050,
+        0x1005e, 0x10080,
+        0x100fb, 0x10100,
         0x10101, 0x10102,
+        0x10103, 0x10107,
+        0x10134, 0x10137,
         0x10140, 0x101d0,
         0x101fd, 0x10280,
+        0x1029d, 0x102a0,
+        0x102d1, 0x10300,
+        0x10324, 0x10330,
+        0x1034b, 0x10350,
+        0x10376, 0x10380,
+        0x1039e, 0x1039f,
+        0x103c4, 0x103c8,
+        0x103d6, 0x10400,
+        0x1049e, 0x104a0,
+        0x104aa, 0x10500,
+        0x10528, 0x10530,
+        0x10564, 0x1056f,
+        0x10570, 0x10600,
+        0x10737, 0x10740,
+        0x10756, 0x10760,
+        0x10768, 0x10800,
         0x1091f, 0x10920,
-        0x10a01, 0x10a10,
-        0x10a38, 0x10a40,
+        0x10a01, 0x10a04,
+        0x10a05, 0x10a07,
+        0x10a0c, 0x10a10,
+        0x10a38, 0x10a3b,
+        0x10a3f, 0x10a40,
+        0x10ae5, 0x10ae7,
         0x10b39, 0x10b40,
-        0x10e60, 0x11000,
+        0x10e60, 0x10e7f,
         0x11001, 0x11002,
         0x11038, 0x11047,
-        0x11052, 0x11066,
-        0x11080, 0x11082,
+        0x1104e, 0x11066,
+        0x11070, 0x11082,
         0x110b3, 0x110b7,
         0x110b9, 0x110bb,
-        0x11100, 0x11103,
+        0x110c2, 0x110d0,
+        0x110e9, 0x110f0,
+        0x110fa, 0x11103,
         0x11127, 0x1112c,
         0x1112d, 0x11136,
-        0x11180, 0x11182,
+        0x11144, 0x11150,
+        0x11173, 0x11174,
+        0x11177, 0x11182,
         0x111b6, 0x111bf,
+        0x111c9, 0x111cd,
+        0x111ce, 0x111d0,
+        0x111db, 0x111e1,
+        0x111f5, 0x11200,
+        0x11212, 0x11213,
+        0x1122f, 0x11232,
+        0x11234, 0x11235,
+        0x11236, 0x11238,
+        0x1123e, 0x112b0,
+        0x112df, 0x112e0,
+        0x112e3, 0x112f0,
+        0x112fa, 0x11302,
+        0x11304, 0x11305,
+        0x1130d, 0x1130f,
+        0x11311, 0x11313,
+        0x11329, 0x1132a,
+        0x11331, 0x11332,
+        0x11334, 0x11335,
+        0x1133a, 0x1133d,
+        0x11340, 0x11341,
+        0x11345, 0x11347,
+        0x11349, 0x1134b,
+        0x1134e, 0x11357,
+        0x11358, 0x1135d,
+        0x11364, 0x11480,
+        0x114b3, 0x114b9,
+        0x114ba, 0x114bb,
+        0x114bf, 0x114c1,
+        0x114c2, 0x114c4,
+        0x114c8, 0x114d0,
+        0x114da, 0x11580,
+        0x115b2, 0x115b8,
+        0x115bc, 0x115be,
+        0x115bf, 0x115c1,
+        0x115ca, 0x11600,
+        0x11633, 0x1163b,
+        0x1163d, 0x1163e,
+        0x1163f, 0x11641,
+        0x11645, 0x11650,
+        0x1165a, 0x11680,
         0x116ab, 0x116ac,
         0x116ad, 0x116ae,
         0x116b0, 0x116b6,
         0x116b7, 0x116c0,
-        0x16f8f, 0x16f93,
+        0x116ca, 0x118a0,
+        0x118f3, 0x118ff,
+        0x11900, 0x11ac0,
+        0x11af9, 0x12000,
+        0x12399, 0x12400,
+        0x1246f, 0x12470,
+        0x12475, 0x13000,
+        0x1342f, 0x16800,
+        0x16a39, 0x16a40,
+        0x16a5f, 0x16a60,
+        0x16a6a, 0x16a6e,
+        0x16a70, 0x16ad0,
+        0x16aee, 0x16af5,
+        0x16af6, 0x16b00,
+        0x16b30, 0x16b37,
+        0x16b46, 0x16b50,
+        0x16b5a, 0x16b5b,
+        0x16b62, 0x16b63,
+        0x16b78, 0x16b7d,
+        0x16b90, 0x16f00,
+        0x16f45, 0x16f50,
+        0x16f7f, 0x16f93,
+        0x16fa0, 0x1b000,
+        0x1b002, 0x1bc00,
+        0x1bc6b, 0x1bc70,
+        0x1bc7d, 0x1bc80,
+        0x1bc89, 0x1bc90,
+        0x1bc9a, 0x1bc9c,
+        0x1bc9d, 0x1bc9f,
+        0x1bca0, 0x1d000,
+        0x1d0f6, 0x1d100,
+        0x1d127, 0x1d129,
         0x1d167, 0x1d16a,
         0x1d173, 0x1d183,
         0x1d185, 0x1d18c,
         0x1d1aa, 0x1d1ae,
-        0x1d200, 0x1d360,
+        0x1d1de, 0x1d360,
+        0x1d372, 0x1d400,
+        0x1d455, 0x1d456,
+        0x1d49d, 0x1d49e,
+        0x1d4a0, 0x1d4a2,
+        0x1d4a3, 0x1d4a5,
+        0x1d4a7, 0x1d4a9,
+        0x1d4ad, 0x1d4ae,
+        0x1d4ba, 0x1d4bb,
+        0x1d4bc, 0x1d4bd,
+        0x1d4c4, 0x1d4c5,
+        0x1d506, 0x1d507,
+        0x1d50b, 0x1d50d,
+        0x1d515, 0x1d516,
+        0x1d51d, 0x1d51e,
+        0x1d53a, 0x1d53b,
+        0x1d53f, 0x1d540,
+        0x1d545, 0x1d546,
+        0x1d547, 0x1d54a,
+        0x1d551, 0x1d552,
+        0x1d6a6, 0x1d6a8,
         0x1d6db, 0x1d6dc,
         0x1d715, 0x1d716,
         0x1d74f, 0x1d750,
         0x1d789, 0x1d78a,
         0x1d7c3, 0x1d7c4,
-        0x1d7ce, 0x1ee00,
-        0x1eef0, 0x1f110,
+        0x1d7cc, 0x1e800,
+        0x1e8d0, 0x1e8d7,
+        0x1eef0, 0x1eef2,
+        0x1f000, 0x1f110,
+        0x1f12f, 0x1f130,
         0x1f16a, 0x1f170,
-        0x1f300, 0x1f48c,
-        0x1f48d, 0x1f524,
-        0x1f525, 0x20000,
-        0xe0001, 0xf0000,
+        0x1f19b, 0x1f1e6,
+        0x1f203, 0x1f210,
+        0x1f23b, 0x1f240,
+        0x1f249, 0x1f250,
+        0x1f252, 0x20000,
+        0x2a6d7, 0x2a700,
+        0x2b735, 0x2b740,
+        0x2b81e, 0x2f800,
+        0x2fa1e, 0xf0000,
+        0xffffe, 0x100000,
         0x10fffe, 0x10ffff // sentinel
     };
 
--- a/jdk/src/java.desktop/share/classes/java/awt/image/ComponentSampleModel.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/java/awt/image/ComponentSampleModel.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 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
@@ -104,12 +104,6 @@
      */
     protected int pixelStride;
 
-    static private native void initIDs();
-    static {
-        ColorModel.loadLibraries();
-        initIDs();
-    }
-
     /**
      * Constructs a ComponentSampleModel with the specified parameters.
      * The number of bands will be given by the length of the bandOffsets array.
--- a/jdk/src/java.desktop/share/classes/java/awt/image/renderable/RenderableImageProducer.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/java/awt/image/renderable/RenderableImageProducer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1998, 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
@@ -137,12 +137,7 @@
         addConsumer(ic);
         // Need to build a runnable object for the Thread.
         String name = "RenderableImageProducer Thread";
-        Thread thread;
-        if (System.getSecurityManager() == null) {
-            thread = new Thread(this, name);
-        } else {
-            thread = new ManagedLocalsThread(this);
-        }
+        Thread thread = new ManagedLocalsThread(this, name);
         thread.start();
     }
 
--- a/jdk/src/java.desktop/share/classes/javax/swing/JTable.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/javax/swing/JTable.java	Wed Jul 05 20:42:36 2017 +0200
@@ -6402,12 +6402,7 @@
         };
 
         // start printing on another thread
-        Thread th;
-        if  (System.getSecurityManager() == null) {
-            th = new Thread(runnable);
-        } else {
-            th = new ManagedLocalsThread(runnable);
-        }
+        Thread th = new ManagedLocalsThread(runnable);
         th.start();
 
         printingStatus.showModal(true);
--- a/jdk/src/java.desktop/share/classes/javax/swing/JTree.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/javax/swing/JTree.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1365,6 +1365,13 @@
 
                     child = getPathForRow(index);
                     parent = child.getParentPath();
+                    TreePath prev = getPathForRow(row).getParentPath();
+                    if (prev != null && !prev.equals(parent)) {
+                        location = new DropLocation(p, prev,
+                              model.getChildCount(prev.getLastPathComponent()));
+                        break;
+                    }
+
                 } else {
                     assert checkOn;
                     location = new DropLocation(p, getPathForRow(row), -1);
--- a/jdk/src/java.desktop/share/classes/javax/swing/TimerQueue.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/javax/swing/TimerQueue.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 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
@@ -36,8 +36,7 @@
 import java.util.concurrent.locks.*;
 import java.util.concurrent.atomic.AtomicLong;
 import sun.awt.AppContext;
-import sun.misc.InnocuousThread;
-
+import sun.misc.ManagedLocalsThread;
 
 /**
  * Internal class to manage all Timers using one thread.
@@ -99,12 +98,8 @@
                 final ThreadGroup threadGroup = AppContext.getAppContext().getThreadGroup();
                 AccessController.doPrivileged((PrivilegedAction<Object>) () -> {
                     String name = "TimerQueue";
-                    Thread timerThread;
-                    if (System.getSecurityManager() == null) {
-                        timerThread = new Thread(threadGroup, TimerQueue.this, name);
-                    } else {
-                        timerThread = new InnocuousThread(threadGroup, TimerQueue.this, name);
-                    }
+                    Thread timerThread = new ManagedLocalsThread(threadGroup,
+                                                                 this, name);
                     timerThread.setDaemon(true);
                     timerThread.setPriority(Thread.NORM_PRIORITY);
                     timerThread.start();
--- a/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicDirectoryModel.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicDirectoryModel.java	Wed Jul 05 20:42:36 2017 +0200
@@ -271,11 +271,7 @@
             this.currentDirectory = currentDirectory;
             this.fid = fid;
             String name = "Basic L&F File Loading Thread";
-            if (System.getSecurityManager() == null) {
-                this.loadThread = new Thread(this, name);
-            } else {
-                this.loadThread = new ManagedLocalsThread(this, name);
-            }
+            this.loadThread = new ManagedLocalsThread(this, name);
             this.loadThread.start();
         }
 
--- a/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicRadioButtonUI.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicRadioButtonUI.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 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
@@ -35,6 +35,7 @@
 import sun.awt.AppContext;
 import java.util.Enumeration;
 import java.util.HashSet;
+import java.util.Set;
 
 /**
  * RadioButtonUI implementation for BasicRadioButtonUI
@@ -582,23 +583,32 @@
      */
     private class KeyHandler implements KeyListener {
 
-        // This listener checks if the key event is a KeyEvent.VK_TAB
-        // or shift + KeyEvent.VK_TAB event on a radio button, consume the event
-        // if so and move the focus to next/previous component
+        // This listener checks if the key event is a focus traversal key event
+        // on a radio button, consume the event if so and move the focus
+        // to next/previous component
         public void keyPressed(KeyEvent e) {
-            if (e.getKeyCode() == KeyEvent.VK_TAB) {
-                 // Get the source of the event.
-                Object eventSrc = e.getSource();
-
-                // Check whether the source is a visible and enabled JRadioButton
-                if (isValidRadioButtonObj(eventSrc)) {
+            AWTKeyStroke stroke = AWTKeyStroke.getAWTKeyStrokeForEvent(e);
+            if (stroke != null && e.getSource() instanceof JRadioButton) {
+                JRadioButton source = (JRadioButton) e.getSource();
+                boolean next = isFocusTraversalKey(source,
+                        KeyboardFocusManager.FORWARD_TRAVERSAL_KEYS,
+                        stroke);
+                if (next || isFocusTraversalKey(source,
+                        KeyboardFocusManager.BACKWARD_TRAVERSAL_KEYS,
+                        stroke)) {
                     e.consume();
-                    ButtonGroupInfo btnGroupInfo = new ButtonGroupInfo((JRadioButton)eventSrc);
-                    btnGroupInfo.jumpToNextComponent(!e.isShiftDown());
+                    ButtonGroupInfo btnGroupInfo = new ButtonGroupInfo(source);
+                    btnGroupInfo.jumpToNextComponent(next);
                 }
             }
         }
 
+        private boolean isFocusTraversalKey(JComponent c, int id,
+                                            AWTKeyStroke stroke) {
+            Set<AWTKeyStroke> keys = c.getFocusTraversalKeys(id);
+            return keys != null && keys.contains(stroke);
+        }
+
         public void keyReleased(KeyEvent e) {
         }
 
--- a/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicTreeUI.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/javax/swing/plaf/basic/BasicTreeUI.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 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
@@ -1497,8 +1497,16 @@
                 rect.x = xRect.x;
                 rect.width = xRect.width;
             } else {
-                rect = tree.getPathBounds(path.pathByAddingChild(
-                    model.getChild(path.getLastPathComponent(), index)));
+                if (index >= model.getChildCount(path.getLastPathComponent())) {
+                    rect = tree.getPathBounds(path.pathByAddingChild(
+                            model.getChild(path.getLastPathComponent(),
+                                    index - 1)));
+                    rect.y = rect.y + rect.height;
+                } else {
+                    rect = tree.getPathBounds(path.pathByAddingChild(
+                            model.getChild(path.getLastPathComponent(),
+                                    index)));
+                }
             }
         }
 
--- a/jdk/src/java.desktop/share/classes/javax/swing/text/JTextComponent.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/javax/swing/text/JTextComponent.java	Wed Jul 05 20:42:36 2017 +0200
@@ -2365,11 +2365,7 @@
             runnablePrinting.run();
         } else {
             if (isEventDispatchThread) {
-                if (System.getSecurityManager() == null) {
-                    new Thread(runnablePrinting).start();
-                } else {
-                    new ManagedLocalsThread(runnablePrinting).start();
-                }
+                new ManagedLocalsThread(runnablePrinting).start();
                 printingStatus.showModal(true);
             } else {
                 printingStatus.showModal(false);
--- a/jdk/src/java.desktop/share/classes/javax/swing/text/LayoutQueue.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/javax/swing/text/LayoutQueue.java	Wed Jul 05 20:42:36 2017 +0200
@@ -92,12 +92,7 @@
                     }
                 } while (work != null);
             };
-            String name =  "text-layout";
-            if (System.getSecurityManager() == null) {
-                worker = new Thread(workerRunnable, name);
-            } else {
-                worker = new ManagedLocalsThread(workerRunnable, name);
-            }
+            worker = new ManagedLocalsThread(workerRunnable, "text-layout");
             worker.setPriority(Thread.MIN_PRIORITY);
             worker.start();
         }
--- a/jdk/src/java.desktop/share/classes/sun/applet/AppletClassLoader.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/sun/applet/AppletClassLoader.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1995, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1995, 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
@@ -862,7 +862,7 @@
     volatile boolean created = false;
 
     AppContextCreator(ThreadGroup group)  {
-        super(group, null, "AppContextCreator");
+        super(group, "AppContextCreator");
     }
 
     public void run()  {
--- a/jdk/src/java.desktop/share/classes/sun/awt/AWTAutoShutdown.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/sun/awt/AWTAutoShutdown.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 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
@@ -34,7 +34,7 @@
 import java.util.Set;
 
 import sun.awt.util.ThreadGroupUtils;
-import sun.misc.InnocuousThread;
+import sun.misc.ManagedLocalsThread;
 import sun.util.logging.PlatformLogger;
 
 /**
@@ -336,14 +336,9 @@
      */
     private void activateBlockerThread() {
         AccessController.doPrivileged((PrivilegedAction<Thread>) () -> {
-            Thread thread;
             String name = "AWT-Shutdown";
-            if (System.getSecurityManager() == null) {
-                thread = new Thread(ThreadGroupUtils.getRootThreadGroup(), this,
-                                    name);
-            } else {
-                thread = new InnocuousThread(this, name);
-            }
+            Thread thread = new ManagedLocalsThread(
+                    ThreadGroupUtils.getRootThreadGroup(), this, name);
             thread.setContextClassLoader(null);
             thread.setDaemon(false);
             blockerThread = thread;
--- a/jdk/src/java.desktop/share/classes/sun/awt/AppContext.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/sun/awt/AppContext.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1998, 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
@@ -44,7 +44,7 @@
 import java.beans.PropertyChangeListener;
 import java.lang.ref.SoftReference;
 
-import sun.misc.InnocuousThread;
+import sun.misc.ManagedLocalsThread;
 import sun.util.logging.PlatformLogger;
 import java.util.concurrent.locks.Condition;
 import java.util.concurrent.locks.Lock;
@@ -591,13 +591,9 @@
         }
 
         public Thread run() {
-            Thread t;
-            if (System.getSecurityManager() == null) {
-                t = new Thread(appContext.getThreadGroup(), runnable);
-            } else {
-                t = new InnocuousThread(appContext.getThreadGroup(), runnable, "AppContext Disposer");
-            }
-            t.setContextClassLoader(null);
+            Thread t = new ManagedLocalsThread(appContext.getThreadGroup(),
+                                               runnable, "AppContext Disposer");
+            t.setContextClassLoader(appContext.getContextClassLoader());
             t.setPriority(Thread.NORM_PRIORITY + 1);
             t.setDaemon(true);
             return t;
--- a/jdk/src/java.desktop/share/classes/sun/awt/SunToolkit.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/sun/awt/SunToolkit.java	Wed Jul 05 20:42:36 2017 +0200
@@ -66,6 +66,7 @@
 import sun.awt.image.URLImageSource;
 import sun.font.FontDesignMetrics;
 import sun.misc.SoftCache;
+import sun.net.util.URLUtil;
 import sun.security.action.GetBooleanAction;
 import sun.security.action.GetPropertyAction;
 import sun.util.logging.PlatformLogger;
@@ -875,7 +876,7 @@
         if (sm != null) {
             try {
                 java.security.Permission perm =
-                    url.openConnection().getPermission();
+                    URLUtil.getConnectPermission(url);
                 if (perm != null) {
                     try {
                         sm.checkPermission(perm);
--- a/jdk/src/java.desktop/share/classes/sun/awt/im/InputMethodManager.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/sun/awt/im/InputMethodManager.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1998, 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
@@ -167,12 +167,7 @@
                 // to choose from. Otherwise, just keep the instance.
                 if (imm.hasMultipleInputMethods()) {
                     imm.initialize();
-                    Thread immThread;
-                    if (System.getSecurityManager() == null) {
-                        immThread = new Thread(imm, threadName);
-                    } else {
-                        immThread = new ManagedLocalsThread(imm, threadName);
-                    }
+                    Thread immThread = new ManagedLocalsThread(imm, threadName);
                     immThread.setDaemon(true);
                     immThread.setPriority(Thread.NORM_PRIORITY + 1);
                     immThread.start();
--- a/jdk/src/java.desktop/share/classes/sun/awt/image/ImageFetcher.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/sun/awt/image/ImageFetcher.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1995, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1995, 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
@@ -55,7 +55,7 @@
       * Constructor for ImageFetcher -- only called by add() below.
       */
     private ImageFetcher(ThreadGroup threadGroup, int index) {
-        super(threadGroup, null, "Image Fetcher " + index);
+        super(threadGroup, "Image Fetcher " + index);
         setDaemon(true);
     }
 
--- a/jdk/src/java.desktop/share/classes/sun/awt/image/URLImageSource.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/sun/awt/image/URLImageSource.java	Wed Jul 05 20:42:36 2017 +0200
@@ -31,6 +31,7 @@
 import java.net.URL;
 import java.net.URLConnection;
 import java.net.MalformedURLException;
+import sun.net.util.URLUtil;
 
 public class URLImageSource extends InputStreamImageSource {
     URL url;
@@ -43,7 +44,7 @@
         if (sm != null) {
             try {
                 java.security.Permission perm =
-                    u.openConnection().getPermission();
+                      URLUtil.getConnectPermission(u);
                 if (perm != null) {
                     try {
                         sm.checkPermission(perm);
--- a/jdk/src/java.desktop/share/classes/sun/awt/image/VolatileSurfaceManager.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/sun/awt/image/VolatileSurfaceManager.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 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
@@ -246,7 +246,7 @@
      * SurfaceData object, or null if the surface creation was not successful.
      *
      * Platform-specific subclasses should initialize an accelerated
-     * surface (e.g. a DirectDraw surface on Windows, an OpenGL pbuffer,
+     * surface (e.g. a DirectDraw surface on Windows, an OpenGL FBO,
      * or an X11 pixmap).
      */
     protected abstract SurfaceData initAcceleratedSurface();
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.desktop/share/classes/sun/awt/www/content/MultimediaContentHandlers.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,59 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package sun.awt.www.content;
+
+import sun.awt.www.content.audio.wav;
+import sun.awt.www.content.audio.x_aiff;
+import sun.awt.www.content.image.gif;
+import sun.awt.www.content.audio.aiff;
+import sun.awt.www.content.audio.basic;
+import sun.awt.www.content.audio.x_wav;
+import sun.awt.www.content.image.jpeg;
+import sun.awt.www.content.image.png;
+import sun.awt.www.content.image.x_xbitmap;
+import sun.awt.www.content.image.x_xpixmap;
+
+import java.net.ContentHandler;
+import java.net.ContentHandlerFactory;
+
+public final class MultimediaContentHandlers implements ContentHandlerFactory {
+
+    @Override
+    public ContentHandler createContentHandler(String mimetype) {
+        switch (mimetype) {
+            case "audio/aiff":      return new aiff();
+            case "audio/basic":     return new basic();
+            case "audio/wav":       return new wav();
+            case "audio/x-aiff":    return new x_aiff();
+            case "audio/x-wav":     return new x_wav();
+            case "image/gif":       return new gif();
+            case "image/jpeg":      return new jpeg();
+            case "image/png":       return new png();
+            case "image/x-xbitmap": return new x_xbitmap();
+            case "image/x-xpixmap": return new x_xpixmap();
+            default:                return null;
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.desktop/share/classes/sun/awt/www/content/audio/aiff.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,43 @@
+/*
+ * Copyright (c) 1999, 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.
+ */
+
+/**
+ * Basic .aiff audio handler.
+ * @author  Jeff Nisewanger
+ */
+package sun.awt.www.content.audio;
+
+import java.net.*;
+import java.io.IOException;
+import sun.applet.AppletAudioClip;
+
+/**
+ * Returns an AppletAudioClip object.
+ */
+public class aiff extends ContentHandler {
+    public Object getContent(URLConnection uc) throws IOException {
+        return new AppletAudioClip(uc);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.desktop/share/classes/sun/awt/www/content/audio/basic.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,45 @@
+/*
+ * Copyright (c) 1999, 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.
+ */
+
+/**
+ * Basic .au and .snd audio handler.
+ * @author  Jeff Nisewanger
+ */
+package sun.awt.www.content.audio;
+
+import java.net.*;
+import java.io.IOException;
+import sun.applet.AppletAudioClip;
+
+/**
+ * Returns an AppletAudioClip object.
+ * This provides backwards compatibility with the behavior
+ * of ClassLoader.getResource().getContent() on JDK1.1.
+ */
+public class basic extends ContentHandler {
+    public Object getContent(URLConnection uc) throws IOException {
+        return new AppletAudioClip(uc);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.desktop/share/classes/sun/awt/www/content/audio/wav.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,43 @@
+/*
+ * Copyright (c) 1999, 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.
+ */
+
+/**
+ * Basic .wav audio handler.
+ * @author  Jeff Nisewanger
+ */
+package sun.awt.www.content.audio;
+
+import java.net.*;
+import java.io.IOException;
+import sun.applet.AppletAudioClip;
+
+/**
+ * Returns an AppletAudioClip object.
+ */
+public class wav extends ContentHandler {
+    public Object getContent(URLConnection uc) throws IOException {
+        return new AppletAudioClip(uc);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.desktop/share/classes/sun/awt/www/content/audio/x_aiff.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,43 @@
+/*
+ * Copyright (c) 1999, 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.
+ */
+
+/**
+ * Basic .aiff audio handler.
+ * @author  Jeff Nisewanger
+ */
+package sun.awt.www.content.audio;
+
+import java.net.*;
+import java.io.IOException;
+import sun.applet.AppletAudioClip;
+
+/**
+ * Returns an AppletAudioClip object.
+ */
+public class x_aiff extends ContentHandler {
+    public Object getContent(URLConnection uc) throws IOException {
+        return new AppletAudioClip(uc);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.desktop/share/classes/sun/awt/www/content/audio/x_wav.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,43 @@
+/*
+ * Copyright (c) 1999, 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.
+ */
+
+/**
+ * Basic .wav audio handler.
+ * @author  Jeff Nisewanger
+ */
+package sun.awt.www.content.audio;
+
+import java.net.*;
+import java.io.IOException;
+import sun.applet.AppletAudioClip;
+
+/**
+ * Returns an AppletAudioClip object.
+ */
+public class x_wav extends ContentHandler {
+    public Object getContent(URLConnection uc) throws IOException {
+        return new AppletAudioClip(uc);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.desktop/share/classes/sun/awt/www/content/image/gif.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,54 @@
+/*
+ * Copyright (c) 1994, 2013, 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.awt.www.content.image;
+
+import java.net.*;
+import sun.awt.image.*;
+import java.io.IOException;
+import java.awt.Image;
+import java.awt.Toolkit;
+
+
+public class gif extends ContentHandler {
+    public Object getContent(URLConnection urlc) throws java.io.IOException {
+        return new URLImageSource(urlc);
+    }
+
+    @SuppressWarnings("rawtypes")
+    public Object getContent(URLConnection urlc, Class[] classes) throws IOException {
+        Class<?>[] cls = classes;
+        for (int i = 0; i < cls.length; i++) {
+            if (cls[i].isAssignableFrom(URLImageSource.class)) {
+                return new URLImageSource(urlc);
+            }
+            if (cls[i].isAssignableFrom(Image.class)) {
+                Toolkit tk = Toolkit.getDefaultToolkit();
+                return tk.createImage(new URLImageSource(urlc));
+            }
+        }
+        return null;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.desktop/share/classes/sun/awt/www/content/image/jpeg.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,53 @@
+/*
+ * Copyright (c) 1995, 2013, 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.awt.www.content.image;
+
+import java.net.*;
+import sun.awt.image.*;
+import java.io.IOException;
+import java.awt.Image;
+import java.awt.Toolkit;
+
+public class jpeg extends ContentHandler {
+    public Object getContent(URLConnection urlc) throws java.io.IOException {
+        return new URLImageSource(urlc);
+    }
+
+    @SuppressWarnings("rawtypes")
+    public Object getContent(URLConnection urlc, Class[] classes) throws IOException {
+        Class<?>[] cls = classes;
+        for (int i = 0; i < cls.length; i++) {
+            if (cls[i].isAssignableFrom(URLImageSource.class)) {
+                return new URLImageSource(urlc);
+            }
+            if (cls[i].isAssignableFrom(Image.class)) {
+                Toolkit tk = Toolkit.getDefaultToolkit();
+                return tk.createImage(new URLImageSource(urlc));
+            }
+        }
+        return null;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.desktop/share/classes/sun/awt/www/content/image/png.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,53 @@
+/*
+ * Copyright (c) 1999, 2013, 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.awt.www.content.image;
+
+import java.net.*;
+import java.io.IOException;
+import sun.awt.image.*;
+import java.awt.Image;
+import java.awt.Toolkit;
+
+public class png extends ContentHandler {
+    public Object getContent(URLConnection urlc) throws java.io.IOException {
+        return new URLImageSource(urlc);
+    }
+
+    @SuppressWarnings("rawtypes")
+    public Object getContent(URLConnection urlc, Class[] classes) throws IOException {
+        Class<?>[] cls = classes;
+        for (int i = 0; i < cls.length; i++) {
+            if (cls[i].isAssignableFrom(URLImageSource.class)) {
+                return new URLImageSource(urlc);
+            }
+            if (cls[i].isAssignableFrom(Image.class)) {
+                Toolkit tk = Toolkit.getDefaultToolkit();
+                return tk.createImage(new URLImageSource(urlc));
+            }
+        }
+        return null;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.desktop/share/classes/sun/awt/www/content/image/x_xbitmap.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,52 @@
+/*
+ * Copyright (c) 1994, 2013, 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.awt.www.content.image;
+
+import java.net.*;
+import sun.awt.image.*;
+import java.awt.Image;
+import java.awt.Toolkit;
+
+public class x_xbitmap extends ContentHandler {
+    public Object getContent(URLConnection urlc) throws java.io.IOException {
+        return new URLImageSource(urlc);
+    }
+
+    @SuppressWarnings("rawtypes")
+    public Object getContent(URLConnection urlc, Class[] classes) throws java.io.IOException {
+        Class<?>[] cls = classes;
+        for (int i = 0; i < cls.length; i++) {
+            if (cls[i].isAssignableFrom(URLImageSource.class)) {
+                return new URLImageSource(urlc);
+            }
+            if (cls[i].isAssignableFrom(Image.class)) {
+                Toolkit tk = Toolkit.getDefaultToolkit();
+                return tk.createImage(new URLImageSource(urlc));
+            }
+        }
+        return null;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.desktop/share/classes/sun/awt/www/content/image/x_xpixmap.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,52 @@
+/*
+ * Copyright (c) 1994, 2013, 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.awt.www.content.image;
+
+import java.net.*;
+import sun.awt.image.*;
+import java.awt.Image;
+import java.awt.Toolkit;
+
+public class x_xpixmap extends ContentHandler {
+    public Object getContent(URLConnection urlc) throws java.io.IOException {
+        return new URLImageSource(urlc);
+    }
+
+    @SuppressWarnings("rawtypes")
+    public Object getContent(URLConnection urlc, Class[] classes) throws java.io.IOException {
+        Class<?>[] cls = classes;
+        for (int i = 0; i < cls.length; i++) {
+            if (cls[i].isAssignableFrom(URLImageSource.class)) {
+                return new URLImageSource(urlc);
+            }
+            if (cls[i].isAssignableFrom(Image.class)) {
+                Toolkit tk = Toolkit.getDefaultToolkit();
+                return tk.createImage(new URLImageSource(urlc));
+            }
+        }
+        return null;
+    }
+}
--- a/jdk/src/java.desktop/share/classes/sun/font/CreatedFontTracker.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/sun/font/CreatedFontTracker.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2008, 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
@@ -36,7 +36,7 @@
 
 import sun.awt.AppContext;
 import sun.awt.util.ThreadGroupUtils;
-import sun.misc.InnocuousThread;
+import sun.misc.ManagedLocalsThread;
 
 public class CreatedFontTracker {
 
@@ -117,17 +117,13 @@
             if (t == null) {
                 // Add a shutdown hook to remove the temp file.
                 AccessController.doPrivileged((PrivilegedAction<Void>) () -> {
-                    if (System.getSecurityManager() == null) {
-                        /* The thread must be a member of a thread group
-                         * which will not get GCed before VM exit.
-                         * Make its parent the top-level thread group.
-                         */
-                        ThreadGroup rootTG = ThreadGroupUtils.getRootThreadGroup();
-                        t = new Thread(rootTG, TempFileDeletionHook::runHooks);
-                    } else {
-                        /* InnocuousThread is a member of a correct TG by default */
-                        t = new InnocuousThread(TempFileDeletionHook::runHooks);
-                    }
+                    /* The thread must be a member of a thread group
+                     * which will not get GCed before VM exit.
+                     * Make its parent the top-level thread group.
+                     */
+                    ThreadGroup rootTG = ThreadGroupUtils.getRootThreadGroup();
+                    t = new ManagedLocalsThread(rootTG,
+                                                TempFileDeletionHook::runHooks);
                     /* Set context class loader to null in order to avoid
                      * keeping a strong reference to an application classloader.
                      */
--- a/jdk/src/java.desktop/share/classes/sun/font/SunFontManager.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/sun/font/SunFontManager.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2008, 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
@@ -55,6 +55,7 @@
 import sun.awt.util.ThreadGroupUtils;
 import sun.java2d.FontSupport;
 import sun.misc.InnocuousThread;
+import sun.misc.ManagedLocalsThread;
 import sun.util.logging.PlatformLogger;
 
 /**
@@ -2501,12 +2502,9 @@
                       }
                     };
                     AccessController.doPrivileged((PrivilegedAction<Void>) () -> {
-                        if (System.getSecurityManager() == null) {
-                            ThreadGroup rootTG = ThreadGroupUtils.getRootThreadGroup();
-                            fileCloser = new Thread(rootTG, fileCloserRunnable);
-                        } else {
-                            fileCloser = new InnocuousThread(fileCloserRunnable);
-                        }
+                        ThreadGroup rootTG = ThreadGroupUtils.getRootThreadGroup();
+                        fileCloser = new ManagedLocalsThread(rootTG,
+                                                             fileCloserRunnable);
                         fileCloser.setContextClassLoader(null);
                         Runtime.getRuntime().addShutdownHook(fileCloser);
                         return null;
--- a/jdk/src/java.desktop/share/classes/sun/java2d/Disposer.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/sun/java2d/Disposer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2002, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2002, 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
@@ -26,7 +26,7 @@
 package sun.java2d;
 
 import sun.awt.util.ThreadGroupUtils;
-import sun.misc.InnocuousThread;
+import sun.misc.ManagedLocalsThread;
 
 import java.lang.ref.Reference;
 import java.lang.ref.ReferenceQueue;
@@ -84,13 +84,8 @@
         disposerInstance = new Disposer();
         AccessController.doPrivileged((PrivilegedAction<Void>) () -> {
             String name = "Java2D Disposer";
-            Thread t;
-            if (System.getSecurityManager() == null) {
-                ThreadGroup rootTG = ThreadGroupUtils.getRootThreadGroup();
-                t = new Thread(rootTG, disposerInstance, name);
-            } else {
-                t = new InnocuousThread(disposerInstance, name);
-            }
+            ThreadGroup rootTG = ThreadGroupUtils.getRootThreadGroup();
+            Thread t = new ManagedLocalsThread(rootTG, disposerInstance, name);
             t.setContextClassLoader(null);
             t.setDaemon(true);
             t.setPriority(Thread.MAX_PRIORITY);
--- a/jdk/src/java.desktop/share/classes/sun/java2d/loops/GraphicsPrimitive.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/sun/java2d/loops/GraphicsPrimitive.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 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
@@ -48,7 +48,7 @@
 import java.security.AccessController;
 import java.security.PrivilegedAction;
 
-import sun.misc.InnocuousThread;
+import sun.misc.ManagedLocalsThread;
 import sun.security.action.GetPropertyAction;
 
 /**
@@ -420,12 +420,8 @@
         public static void setShutdownHook() {
             AccessController.doPrivileged((PrivilegedAction<Void>) () -> {
                 TraceReporter t = new TraceReporter();
-                Thread thread;
-                if (System.getSecurityManager() == null) {
-                    thread = new Thread(ThreadGroupUtils.getRootThreadGroup(), t);
-                } else {
-                    thread = new InnocuousThread(t);
-                }
+                Thread thread = new ManagedLocalsThread(
+                        ThreadGroupUtils.getRootThreadGroup(), t);
                 thread.setContextClassLoader(null);
                 Runtime.getRuntime().addShutdownHook(thread);
                 return null;
--- a/jdk/src/java.desktop/share/classes/sun/java2d/opengl/OGLContext.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/sun/java2d/opengl/OGLContext.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -164,9 +164,6 @@
         @Native
         static final int CAPS_EXT_FBOBJECT     =
                 (CAPS_RT_TEXTURE_ALPHA | CAPS_RT_TEXTURE_OPAQUE);
-        /** Indicates that the context supports a stored alpha channel. */
-        @Native
-        static final int CAPS_STORED_ALPHA     = CAPS_RT_PLAIN_ALPHA;
         /** Indicates that the context is doublebuffered. */
         @Native
         static final int CAPS_DOUBLEBUFFERED   = (FIRST_PRIVATE_CAP << 0);
@@ -205,9 +202,6 @@
             if ((caps & CAPS_EXT_FBOBJECT) != 0) {
                 sb.append("CAPS_EXT_FBOBJECT|");
             }
-            if ((caps & CAPS_STORED_ALPHA) != 0) {
-                sb.append("CAPS_STORED_ALPHA|");
-            }
             if ((caps & CAPS_DOUBLEBUFFERED) != 0) {
                 sb.append("CAPS_DOUBLEBUFFERED|");
             }
--- a/jdk/src/java.desktop/share/classes/sun/java2d/opengl/OGLRenderQueue.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/sun/java2d/opengl/OGLRenderQueue.java	Wed Jul 05 20:42:36 2017 +0200
@@ -29,6 +29,7 @@
 import sun.java2d.pipe.RenderBuffer;
 import sun.java2d.pipe.RenderQueue;
 import sun.misc.InnocuousThread;
+import sun.misc.ManagedLocalsThread;
 
 import static sun.java2d.pipe.BufferedOpCodes.*;
 import java.security.AccessController;
@@ -161,11 +162,7 @@
 
         public QueueFlusher() {
             String name = "Java2D Queue Flusher";
-            if (System.getSecurityManager() == null) {
-                this.thread = new Thread(ThreadGroupUtils.getRootThreadGroup(), this, name);
-            } else {
-                this.thread = new InnocuousThread(this, name);
-            }
+            thread = new ManagedLocalsThread(ThreadGroupUtils.getRootThreadGroup(), this, name);
             thread.setDaemon(true);
             thread.setPriority(Thread.MAX_PRIORITY);
             thread.start();
--- a/jdk/src/java.desktop/share/classes/sun/java2d/opengl/OGLSurfaceData.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/sun/java2d/opengl/OGLSurfaceData.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 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
@@ -91,7 +91,6 @@
  * OGL Type          Corresponding SurfaceType
  * --------          -------------------------
  * WINDOW            OpenGLSurface
- * PBUFFER           OpenGLSurface
  * TEXTURE           OpenGLTexture
  * FLIP_BACKBUFFER   OpenGLSurface
  * FBOBJECT          OpenGLSurfaceRTT
@@ -104,7 +103,6 @@
      *
      * @see sun.java2d.pipe.hw.AccelSurface
      */
-    public static final int PBUFFER         = RT_PLAIN;
     public static final int FBOBJECT        = RT_TEXTURE;
 
     /**
@@ -172,9 +170,6 @@
                                           boolean texRect,
                                           int width, int height);
     protected native boolean initFlipBackbuffer(long pData);
-    protected abstract boolean initPbuffer(long pData, long pConfigInfo,
-                                           boolean isOpaque,
-                                           int width, int height);
 
     private native int getTextureTarget(long pData);
     private native int getTextureID(long pData);
@@ -250,7 +245,6 @@
             return OpenGLTexture;
         case FBOBJECT:
             return OpenGLSurfaceRTT;
-        case PBUFFER:
         default:
             return OpenGLSurface;
         }
@@ -266,13 +260,6 @@
         boolean success = false;
 
         switch (type) {
-        case PBUFFER:
-            success = initPbuffer(getNativeOps(),
-                                  graphicsConfig.getNativeConfigInfo(),
-                                  isOpaque,
-                                  width, height);
-            break;
-
         case TEXTURE:
             success = initTexture(getNativeOps(),
                                   isOpaque, isTexNonPow2Available(),
@@ -311,10 +298,9 @@
         try {
             switch (type) {
             case TEXTURE:
-            case PBUFFER:
             case FBOBJECT:
                 // need to make sure the context is current before
-                // creating the texture (or pbuffer, or fbobject)
+                // creating the texture or fbobject
                 OGLContext.setScratchSurface(graphicsConfig);
                 break;
             default:
--- a/jdk/src/java.desktop/share/classes/sun/java2d/opengl/OGLUtilities.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/sun/java2d/opengl/OGLUtilities.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -51,7 +51,6 @@
      */
     public static final int UNDEFINED       = OGLSurfaceData.UNDEFINED;
     public static final int WINDOW          = OGLSurfaceData.WINDOW;
-    public static final int PBUFFER         = OGLSurfaceData.PBUFFER;
     public static final int TEXTURE         = OGLSurfaceData.TEXTURE;
     public static final int FLIP_BACKBUFFER = OGLSurfaceData.FLIP_BACKBUFFER;
     public static final int FBOBJECT        = OGLSurfaceData.FBOBJECT;
--- a/jdk/src/java.desktop/share/classes/sun/java2d/pipe/hw/AccelSurface.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/sun/java2d/pipe/hw/AccelSurface.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2007, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2007, 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
@@ -43,8 +43,7 @@
      */
     @Native public static final int WINDOW          = 1;
     /**
-     * Render-To Plain surface (pbuffer for OpenGL, Render Target surface
-     * for Direct3D)
+     * Render-To Plain surface (Render Target surface for Direct3D)
      */
     @Native public static final int RT_PLAIN        = 2;
     /**
--- a/jdk/src/java.desktop/share/classes/sun/net/www/content/audio/aiff.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,43 +0,0 @@
-/*
- * Copyright (c) 1999, 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.
- */
-
-/**
- * Basic .aiff audio handler.
- * @author  Jeff Nisewanger
- */
-package sun.net.www.content.audio;
-
-import java.net.*;
-import java.io.IOException;
-import sun.applet.AppletAudioClip;
-
-/**
- * Returns an AppletAudioClip object.
- */
-public class aiff extends ContentHandler {
-    public Object getContent(URLConnection uc) throws IOException {
-        return new AppletAudioClip(uc);
-    }
-}
--- a/jdk/src/java.desktop/share/classes/sun/net/www/content/audio/basic.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,45 +0,0 @@
-/*
- * Copyright (c) 1999, 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.
- */
-
-/**
- * Basic .au and .snd audio handler.
- * @author  Jeff Nisewanger
- */
-package sun.net.www.content.audio;
-
-import java.net.*;
-import java.io.IOException;
-import sun.applet.AppletAudioClip;
-
-/**
- * Returns an AppletAudioClip object.
- * This provides backwards compatibility with the behavior
- * of ClassLoader.getResource().getContent() on JDK1.1.
- */
-public class basic extends ContentHandler {
-    public Object getContent(URLConnection uc) throws IOException {
-        return new AppletAudioClip(uc);
-    }
-}
--- a/jdk/src/java.desktop/share/classes/sun/net/www/content/audio/wav.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,43 +0,0 @@
-/*
- * Copyright (c) 1999, 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.
- */
-
-/**
- * Basic .wav audio handler.
- * @author  Jeff Nisewanger
- */
-package sun.net.www.content.audio;
-
-import java.net.*;
-import java.io.IOException;
-import sun.applet.AppletAudioClip;
-
-/**
- * Returns an AppletAudioClip object.
- */
-public class wav extends ContentHandler {
-    public Object getContent(URLConnection uc) throws IOException {
-        return new AppletAudioClip(uc);
-    }
-}
--- a/jdk/src/java.desktop/share/classes/sun/net/www/content/audio/x_aiff.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,43 +0,0 @@
-/*
- * Copyright (c) 1999, 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.
- */
-
-/**
- * Basic .aiff audio handler.
- * @author  Jeff Nisewanger
- */
-package sun.net.www.content.audio;
-
-import java.net.*;
-import java.io.IOException;
-import sun.applet.AppletAudioClip;
-
-/**
- * Returns an AppletAudioClip object.
- */
-public class x_aiff extends ContentHandler {
-    public Object getContent(URLConnection uc) throws IOException {
-        return new AppletAudioClip(uc);
-    }
-}
--- a/jdk/src/java.desktop/share/classes/sun/net/www/content/audio/x_wav.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,43 +0,0 @@
-/*
- * Copyright (c) 1999, 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.
- */
-
-/**
- * Basic .wav audio handler.
- * @author  Jeff Nisewanger
- */
-package sun.net.www.content.audio;
-
-import java.net.*;
-import java.io.IOException;
-import sun.applet.AppletAudioClip;
-
-/**
- * Returns an AppletAudioClip object.
- */
-public class x_wav extends ContentHandler {
-    public Object getContent(URLConnection uc) throws IOException {
-        return new AppletAudioClip(uc);
-    }
-}
--- a/jdk/src/java.desktop/share/classes/sun/net/www/content/image/gif.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,54 +0,0 @@
-/*
- * Copyright (c) 1994, 2013, 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.net.www.content.image;
-
-import java.net.*;
-import sun.awt.image.*;
-import java.io.IOException;
-import java.awt.Image;
-import java.awt.Toolkit;
-
-
-public class gif extends ContentHandler {
-    public Object getContent(URLConnection urlc) throws java.io.IOException {
-        return new URLImageSource(urlc);
-    }
-
-    @SuppressWarnings("rawtypes")
-    public Object getContent(URLConnection urlc, Class[] classes) throws IOException {
-        Class<?>[] cls = classes;
-        for (int i = 0; i < cls.length; i++) {
-            if (cls[i].isAssignableFrom(URLImageSource.class)) {
-                return new URLImageSource(urlc);
-            }
-            if (cls[i].isAssignableFrom(Image.class)) {
-                Toolkit tk = Toolkit.getDefaultToolkit();
-                return tk.createImage(new URLImageSource(urlc));
-            }
-        }
-        return null;
-    }
-}
--- a/jdk/src/java.desktop/share/classes/sun/net/www/content/image/jpeg.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,53 +0,0 @@
-/*
- * Copyright (c) 1995, 2013, 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.net.www.content.image;
-
-import java.net.*;
-import sun.awt.image.*;
-import java.io.IOException;
-import java.awt.Image;
-import java.awt.Toolkit;
-
-public class jpeg extends ContentHandler {
-    public Object getContent(URLConnection urlc) throws java.io.IOException {
-        return new URLImageSource(urlc);
-    }
-
-    @SuppressWarnings("rawtypes")
-    public Object getContent(URLConnection urlc, Class[] classes) throws IOException {
-        Class<?>[] cls = classes;
-        for (int i = 0; i < cls.length; i++) {
-            if (cls[i].isAssignableFrom(URLImageSource.class)) {
-                return new URLImageSource(urlc);
-            }
-            if (cls[i].isAssignableFrom(Image.class)) {
-                Toolkit tk = Toolkit.getDefaultToolkit();
-                return tk.createImage(new URLImageSource(urlc));
-            }
-        }
-        return null;
-    }
-}
--- a/jdk/src/java.desktop/share/classes/sun/net/www/content/image/png.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,53 +0,0 @@
-/*
- * Copyright (c) 1999, 2013, 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.net.www.content.image;
-
-import java.net.*;
-import java.io.IOException;
-import sun.awt.image.*;
-import java.awt.Image;
-import java.awt.Toolkit;
-
-public class png extends ContentHandler {
-    public Object getContent(URLConnection urlc) throws java.io.IOException {
-        return new URLImageSource(urlc);
-    }
-
-    @SuppressWarnings("rawtypes")
-    public Object getContent(URLConnection urlc, Class[] classes) throws IOException {
-        Class<?>[] cls = classes;
-        for (int i = 0; i < cls.length; i++) {
-            if (cls[i].isAssignableFrom(URLImageSource.class)) {
-                return new URLImageSource(urlc);
-            }
-            if (cls[i].isAssignableFrom(Image.class)) {
-                Toolkit tk = Toolkit.getDefaultToolkit();
-                return tk.createImage(new URLImageSource(urlc));
-            }
-        }
-        return null;
-    }
-}
--- a/jdk/src/java.desktop/share/classes/sun/net/www/content/image/x_xbitmap.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,52 +0,0 @@
-/*
- * Copyright (c) 1994, 2013, 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.net.www.content.image;
-
-import java.net.*;
-import sun.awt.image.*;
-import java.awt.Image;
-import java.awt.Toolkit;
-
-public class x_xbitmap extends ContentHandler {
-    public Object getContent(URLConnection urlc) throws java.io.IOException {
-        return new URLImageSource(urlc);
-    }
-
-    @SuppressWarnings("rawtypes")
-    public Object getContent(URLConnection urlc, Class[] classes) throws java.io.IOException {
-        Class<?>[] cls = classes;
-        for (int i = 0; i < cls.length; i++) {
-            if (cls[i].isAssignableFrom(URLImageSource.class)) {
-                return new URLImageSource(urlc);
-            }
-            if (cls[i].isAssignableFrom(Image.class)) {
-                Toolkit tk = Toolkit.getDefaultToolkit();
-                return tk.createImage(new URLImageSource(urlc));
-            }
-        }
-        return null;
-    }
-}
--- a/jdk/src/java.desktop/share/classes/sun/net/www/content/image/x_xpixmap.java	Thu Jul 16 19:31:01 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,52 +0,0 @@
-/*
- * Copyright (c) 1994, 2013, 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.net.www.content.image;
-
-import java.net.*;
-import sun.awt.image.*;
-import java.awt.Image;
-import java.awt.Toolkit;
-
-public class x_xpixmap extends ContentHandler {
-    public Object getContent(URLConnection urlc) throws java.io.IOException {
-        return new URLImageSource(urlc);
-    }
-
-    @SuppressWarnings("rawtypes")
-    public Object getContent(URLConnection urlc, Class[] classes) throws java.io.IOException {
-        Class<?>[] cls = classes;
-        for (int i = 0; i < cls.length; i++) {
-            if (cls[i].isAssignableFrom(URLImageSource.class)) {
-                return new URLImageSource(urlc);
-            }
-            if (cls[i].isAssignableFrom(Image.class)) {
-                Toolkit tk = Toolkit.getDefaultToolkit();
-                return tk.createImage(new URLImageSource(urlc));
-            }
-        }
-        return null;
-    }
-}
--- a/jdk/src/java.desktop/share/classes/sun/print/PrintJob2D.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/sun/print/PrintJob2D.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 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
@@ -987,12 +987,7 @@
     }
 
     private void startPrinterJobThread() {
-        String name = "printerJobThread";
-        if (System.getSecurityManager() == null) {
-            printerJobThread = new Thread(this, name);
-        } else {
-            printerJobThread = new ManagedLocalsThread(this, name);
-        }
+        printerJobThread = new ManagedLocalsThread(this, "printerJobThread");
         printerJobThread.start();
     }
 
--- a/jdk/src/java.desktop/share/classes/sun/print/ServiceNotifier.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/classes/sun/print/ServiceNotifier.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 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
@@ -50,7 +50,7 @@
     private PrintServiceAttributeSet lastSet;
 
     ServiceNotifier(PrintService service) {
-        super((Runnable) null, service.getName() + " notifier");
+        super(service.getName() + " notifier");
         this.service = service;
         listeners = new Vector<>();
         try {
--- a/jdk/src/java.desktop/share/native/common/java2d/opengl/OGLContext.h	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/common/java2d/opengl/OGLContext.h	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -122,8 +122,6 @@
     sun_java2d_opengl_OGLContext_OGLContextCaps_LAST_SHARED_CAP
 #define CAPS_EXT_FBOBJECT    \
     sun_java2d_opengl_OGLContext_OGLContextCaps_CAPS_EXT_FBOBJECT
-#define CAPS_STORED_ALPHA    \
-    sun_java2d_opengl_OGLContext_OGLContextCaps_CAPS_STORED_ALPHA
 #define CAPS_DOUBLEBUFFERED  \
     sun_java2d_opengl_OGLContext_OGLContextCaps_CAPS_DOUBLEBUFFERED
 #define CAPS_EXT_LCD_SHADER  \
--- a/jdk/src/java.desktop/share/native/common/java2d/opengl/OGLSurfaceData.h	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/common/java2d/opengl/OGLSurfaceData.h	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 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
@@ -118,7 +118,7 @@
  * x/yOffset would be (0,0) (the same applies to pbuffers).
  *
  *     jint width/height;
- * The cached surface bounds.  For offscreen surface types (OGLSD_PBUFFER,
+ * The cached surface bounds.  For offscreen surface types (OGLSD_FBOBJECT,
  * OGLSD_TEXTURE, etc.) these values must remain constant.  Onscreen window
  * surfaces (OGLSD_WINDOW, OGLSD_FLIP_BACKBUFFER, etc.) may have their
  * bounds changed in response to a programmatic or user-initiated event, so
@@ -218,7 +218,6 @@
  */
 #define OGLSD_UNDEFINED       sun_java2d_pipe_hw_AccelSurface_UNDEFINED
 #define OGLSD_WINDOW          sun_java2d_pipe_hw_AccelSurface_WINDOW
-#define OGLSD_PBUFFER         sun_java2d_pipe_hw_AccelSurface_RT_PLAIN
 #define OGLSD_TEXTURE         sun_java2d_pipe_hw_AccelSurface_TEXTURE
 #define OGLSD_FLIP_BACKBUFFER sun_java2d_pipe_hw_AccelSurface_FLIP_BACKBUFFER
 #define OGLSD_FBOBJECT        sun_java2d_pipe_hw_AccelSurface_RT_TEXTURE
--- a/jdk/src/java.desktop/share/native/libawt/awt/image/awt_parseImage.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libawt/awt/image/awt_parseImage.c	Wed Jul 05 20:42:36 2017 +0200
@@ -852,7 +852,7 @@
             hintP->needToExpand = TRUE;
             hintP->expandToNbits = cmodelP->maxNbits;
         }
-        else if (rasterP->sppsm.offsets != NULL) {
+        else {
             for (i=0; i < rasterP->numBands; i++) {
                 if (!(rasterP->sppsm.offsets[i] % 8)) {
                     hintP->needToExpand  = TRUE;
--- a/jdk/src/java.desktop/share/native/libawt/awt/image/imageInitIDs.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libawt/awt/image/imageInitIDs.c	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 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
@@ -45,8 +45,6 @@
     CHECK_NULL(g_RasterWidthID    = (*env)->GetFieldID(env, cls, "width", "I"));
     CHECK_NULL(g_RasterHeightID   = (*env)->GetFieldID(env, cls, "height", "I"));
     CHECK_NULL(g_RasterNumBandsID = (*env)->GetFieldID(env, cls, "numBands", "I"));
-    CHECK_NULL(g_RasterGetDataMID = (*env)->GetMethodID(env, cls, "getDataElements",
-                                        "(IIIILjava/lang/Object;)Ljava/lang/Object;"));
     CHECK_NULL(g_RasterMinXID  = (*env)->GetFieldID(env, cls, "minX", "I"));
     CHECK_NULL(g_RasterMinYID  = (*env)->GetFieldID(env, cls, "minY", "I"));
     CHECK_NULL(g_RasterBaseOriginXID  = (*env)->GetFieldID(env, cls,
@@ -67,7 +65,6 @@
     CHECK_NULL(g_BCRdataID = (*env)->GetFieldID(env, cls, "data", "[B"));
     CHECK_NULL(g_BCRscanstrID = (*env)->GetFieldID(env, cls, "scanlineStride", "I"));
     CHECK_NULL(g_BCRpixstrID = (*env)->GetFieldID(env, cls, "pixelStride", "I"));
-    CHECK_NULL(g_BCRbandoffsID = (*env)->GetFieldID(env, cls, "bandOffset", "I"));
     CHECK_NULL(g_BCRdataOffsetsID = (*env)->GetFieldID(env, cls, "dataOffsets", "[I"));
     CHECK_NULL(g_BCRtypeID = (*env)->GetFieldID(env, cls, "type", "I"));
 }
@@ -86,7 +83,6 @@
     CHECK_NULL(g_SCRdataID = (*env)->GetFieldID(env, cls, "data", "[S"));
     CHECK_NULL(g_SCRscanstrID = (*env)->GetFieldID(env, cls, "scanlineStride", "I"));
     CHECK_NULL(g_SCRpixstrID = (*env)->GetFieldID(env, cls, "pixelStride", "I"));
-    CHECK_NULL(g_SCRbandoffsID = (*env)->GetFieldID(env, cls, "bandOffset", "I"));
     CHECK_NULL(g_SCRdataOffsetsID = (*env)->GetFieldID(env, cls, "dataOffsets", "[I"));
     CHECK_NULL(g_SCRtypeID = (*env)->GetFieldID(env, cls, "type", "I"));
 }
@@ -96,9 +92,6 @@
     CHECK_NULL(g_ICRscanstrID = (*env)->GetFieldID(env, cls, "scanlineStride", "I"));
     CHECK_NULL(g_ICRpixstrID = (*env)->GetFieldID(env, cls, "pixelStride", "I"));
     CHECK_NULL(g_ICRdataOffsetsID = (*env)->GetFieldID(env, cls, "dataOffsets", "[I"));
-    CHECK_NULL(g_ICRbandoffsID = (*env)->GetFieldID(env, cls, "bandOffset", "I"));
-    CHECK_NULL(g_ICRputDataMID  = (*env)->GetMethodID(env, cls, "setDataElements",
-                                     "(IIIILjava/lang/Object;)V"));
     CHECK_NULL(g_ICRtypeID = (*env)->GetFieldID(env, cls, "type", "I"));
 }
 
@@ -121,8 +114,6 @@
     CHECK_NULL(g_CMisAlphaPreID = (*env)->GetFieldID(env, cls, "isAlphaPremultiplied",
                                           "Z"));
     CHECK_NULL(g_CMtransparencyID = (*env)->GetFieldID(env, cls, "transparency", "I"));
-    CHECK_NULL(g_CMgetRGBMID      = (*env)->GetMethodID(env, cls, "getRGB",
-                                             "(Ljava/lang/Object;)I"));
     CHECK_NULL(g_CMcsTypeID       = (*env)->GetFieldID(env, cls, "colorSpaceType", "I"));
     CHECK_NULL(g_CMis_sRGBID      = (*env)->GetFieldID(env, cls, "is_sRGB", "Z"));
     CHECK_NULL(g_CMgetRGBdefaultMID   = (*env)->GetStaticMethodID(env, cls,
@@ -148,20 +139,8 @@
 }
 
 JNIEXPORT void JNICALL
-Java_java_awt_image_ComponentSampleModel_initIDs(JNIEnv *env, jclass cls) {
-    CHECK_NULL(g_CSMPixStrideID = (*env)->GetFieldID(env, cls, "pixelStride", "I"));
-    CHECK_NULL(g_CSMScanStrideID = (*env)->GetFieldID(env, cls, "scanlineStride", "I"));
-    CHECK_NULL(g_CSMBandOffsetsID = (*env)->GetFieldID(env, cls, "bandOffsets", "[I"));
-}
-
-JNIEXPORT void JNICALL
 Java_java_awt_image_Kernel_initIDs(JNIEnv *env, jclass cls) {
     CHECK_NULL(g_KernelWidthID   = (*env)->GetFieldID(env, cls, "width", "I"));
     CHECK_NULL(g_KernelHeightID  = (*env)->GetFieldID(env, cls, "height", "I"));
     CHECK_NULL(g_KernelDataID    = (*env)->GetFieldID(env, cls, "data", "[F"));
 }
-
-JNIEXPORT void JNICALL
-Java_java_awt_image_DataBufferInt_initIDs(JNIEnv *env, jclass cls) {
-    CHECK_NULL(g_DataBufferIntPdataID = (*env)->GetFieldID(env, cls, "pData", "J"));
-}
--- a/jdk/src/java.desktop/share/native/libawt/awt/image/imageInitIDs.h	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libawt/awt/image/imageInitIDs.h	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 1998, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 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
@@ -42,7 +42,6 @@
 /* Raster ids */
 IMGEXTERN jfieldID g_RasterWidthID;
 IMGEXTERN jfieldID g_RasterHeightID;
-IMGEXTERN jfieldID g_RasterNumBandsID;
 IMGEXTERN jfieldID g_RasterBaseRasterID;
 IMGEXTERN jfieldID g_RasterMinXID;
 IMGEXTERN jfieldID g_RasterMinYID;
@@ -52,12 +51,10 @@
 IMGEXTERN jfieldID g_RasterDataBufferID;
 IMGEXTERN jfieldID g_RasterNumDataElementsID;
 IMGEXTERN jfieldID g_RasterNumBandsID;
-IMGEXTERN jmethodID g_RasterGetDataMID;
 
 IMGEXTERN jfieldID g_BCRdataID;
 IMGEXTERN jfieldID g_BCRscanstrID;
 IMGEXTERN jfieldID g_BCRpixstrID;
-IMGEXTERN jfieldID g_BCRbandoffsID;
 IMGEXTERN jfieldID g_BCRdataOffsetsID;
 IMGEXTERN jfieldID g_BCRtypeID;
 IMGEXTERN jfieldID g_BPRdataID;
@@ -68,16 +65,13 @@
 IMGEXTERN jfieldID g_SCRdataID;
 IMGEXTERN jfieldID g_SCRscanstrID;
 IMGEXTERN jfieldID g_SCRpixstrID;
-IMGEXTERN jfieldID g_SCRbandoffsID;
 IMGEXTERN jfieldID g_SCRdataOffsetsID;
 IMGEXTERN jfieldID g_SCRtypeID;
 IMGEXTERN jfieldID g_ICRdataID;
 IMGEXTERN jfieldID g_ICRscanstrID;
 IMGEXTERN jfieldID g_ICRpixstrID;
-IMGEXTERN jfieldID g_ICRbandoffsID;
 IMGEXTERN jfieldID g_ICRdataOffsetsID;
 IMGEXTERN jfieldID g_ICRtypeID;
-IMGEXTERN jmethodID g_ICRputDataMID;
 
 /* Color Model ids */
 IMGEXTERN jfieldID g_CMpDataID;
@@ -87,7 +81,6 @@
 IMGEXTERN jfieldID g_CMsuppAlphaID;
 IMGEXTERN jfieldID g_CMisAlphaPreID;
 IMGEXTERN jfieldID g_CMtransparencyID;
-IMGEXTERN jmethodID g_CMgetRGBMID;
 IMGEXTERN jfieldID g_CMcsTypeID;
 IMGEXTERN jfieldID g_CMis_sRGBID;
 IMGEXTERN jmethodID g_CMgetRGBdefaultMID;
@@ -108,19 +101,9 @@
 IMGEXTERN jfieldID g_SPPSMnBitsID;
 IMGEXTERN jfieldID g_SPPSMmaxBitID;
 
-/* Component Sample Model ids */
-IMGEXTERN jfieldID g_CSMPixStrideID;
-IMGEXTERN jfieldID g_CSMScanStrideID;
-IMGEXTERN jfieldID g_CSMBandOffsetsID;
-
 /* Kernel ids */
 IMGEXTERN jfieldID g_KernelWidthID;
 IMGEXTERN jfieldID g_KernelHeightID;
-IMGEXTERN jfieldID g_KernelXOriginID;
-IMGEXTERN jfieldID g_KernelYOriginD;
 IMGEXTERN jfieldID g_KernelDataID;
 
-/* DataBufferInt ids */
-IMGEXTERN jfieldID g_DataBufferIntPdataID;
-
 #endif /* IMAGEINITIDS_H */
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/AlternateSubstSubtables.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/AlternateSubstSubtables.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -53,6 +53,7 @@
             Offset alternateSetTableOffset = SWAPW(alternateSetTableOffsetArray[coverageIndex]);
             const LEReferenceTo<AlternateSetTable> alternateSetTable(base, success,
                                   (const AlternateSetTable *) ((char *) this + alternateSetTableOffset));
+            if (!LE_SUCCESS(success)) return 0;
             TTGlyphID alternate = SWAPW(alternateSetTable->alternateArray[0]);
 
             if (filter == NULL || filter->accept(LE_SET_GLYPH(glyph, alternate), success)) {
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/AnchorTables.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/AnchorTables.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -44,21 +44,27 @@
     case 1:
     {
         LEReferenceTo<Format1AnchorTable> f1(base, success);
-        f1->getAnchor(f1, fontInstance, anchor, success);
+        if (LE_SUCCESS(success)) {
+            f1->getAnchor(f1, fontInstance, anchor, success);
+        }
         break;
     }
 
     case 2:
     {
         LEReferenceTo<Format2AnchorTable> f2(base, success);
-        f2->getAnchor(f2, glyphID, fontInstance, anchor, success);
+        if (LE_SUCCESS(success)) {
+            f2->getAnchor(f2, glyphID, fontInstance, anchor, success);
+        }
         break;
     }
 
     case 3:
     {
         LEReferenceTo<Format3AnchorTable> f3(base, success);
-        f3->getAnchor(f3, fontInstance, anchor, success);
+        if (LE_SUCCESS(success)) {
+            f3->getAnchor(f3, fontInstance, anchor, success);
+        }
         break;
     }
 
@@ -66,7 +72,9 @@
     {
         // unknown format: just use x, y coordinate, like format 1...
         LEReferenceTo<Format1AnchorTable> f1(base, success);
-        f1->getAnchor(f1, fontInstance, anchor, success);
+        if (LE_SUCCESS(success)) {
+            f1->getAnchor(f1, fontInstance, anchor, success);
+        }
         break;
     }
   }
@@ -112,16 +120,18 @@
 
     if (dtxOffset != 0) {
         LEReferenceTo<DeviceTable> dt(base, success, dtxOffset);
-        le_int16 adjx = dt->getAdjustment(dt, (le_int16) fontInstance->getXPixelsPerEm(), success);
-
-        pixels.fX += adjx;
+        if (LE_SUCCESS(success)) {
+            le_int16 adjx = dt->getAdjustment(dt, (le_int16) fontInstance->getXPixelsPerEm(), success);
+            pixels.fX += adjx;
+        }
     }
 
     if (dtyOffset != 0) {
         LEReferenceTo<DeviceTable> dt(base, success, dtyOffset);
-        le_int16 adjy = dt->getAdjustment(dt, (le_int16) fontInstance->getYPixelsPerEm(), success);
-
-        pixels.fY += adjy;
+        if (LE_SUCCESS(success)) {
+            le_int16 adjy = dt->getAdjustment(dt, (le_int16) fontInstance->getYPixelsPerEm(), success);
+            pixels.fY += adjy;
+        }
     }
 
     fontInstance->pixelsToUnits(pixels, anchor);
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/ContextualGlyphInsertionProc2.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/ContextualGlyphInsertionProc2.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -107,6 +107,10 @@
 
     le_int16 markIndex = SWAPW(entry->markedInsertionListIndex);
     if (markIndex > 0) {
+        if (markGlyph < 0 || markGlyph >= glyphStorage.getGlyphCount()) {
+           success = LE_INDEX_OUT_OF_BOUNDS_ERROR;
+           return 0;
+        }
         le_int16 count = (flags & cgiMarkedInsertCountMask) >> 5;
         le_bool isKashidaLike = (flags & cgiMarkedIsKashidaLike);
         le_bool isBefore = (flags & cgiMarkInsertBefore);
@@ -115,6 +119,10 @@
 
     le_int16 currIndex = SWAPW(entry->currentInsertionListIndex);
     if (currIndex > 0) {
+        if (currGlyph < 0 || currGlyph >= glyphStorage.getGlyphCount()) {
+           success = LE_INDEX_OUT_OF_BOUNDS_ERROR;
+           return 0;
+        }
         le_int16 count = flags & cgiCurrentInsertCountMask;
         le_bool isKashidaLike = (flags & cgiCurrentIsKashidaLike);
         le_bool isBefore = (flags & cgiCurrentInsertBefore);
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/ContextualGlyphSubstProc.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/ContextualGlyphSubstProc.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -76,6 +76,10 @@
   WordOffset currOffset = SWAPW(entry->currOffset);
 
   if (markOffset != 0 && LE_SUCCESS(success)) {
+    if (markGlyph < 0 || markGlyph >= glyphStorage.getGlyphCount()) {
+       success = LE_INDEX_OUT_OF_BOUNDS_ERROR;
+       return 0;
+    }
     LEGlyphID mGlyph = glyphStorage[markGlyph];
     TTGlyphID newGlyph = SWAPW(int16Table.getObject(markOffset + LE_GET_GLYPH(mGlyph), success)); // whew.
 
@@ -83,6 +87,10 @@
   }
 
   if (currOffset != 0) {
+    if (currGlyph < 0 || currGlyph >= glyphStorage.getGlyphCount()) {
+       success = LE_INDEX_OUT_OF_BOUNDS_ERROR;
+       return 0;
+    }
     LEGlyphID thisGlyph = glyphStorage[currGlyph];
     TTGlyphID newGlyph = SWAPW(int16Table.getObject(currOffset + LE_GET_GLYPH(thisGlyph), success)); // whew.
 
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/ContextualGlyphSubstProc2.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/ContextualGlyphSubstProc2.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -70,17 +70,25 @@
     if(LE_FAILURE(success)) return 0;
     le_uint16 newState = SWAPW(entry->newStateIndex);
     le_uint16 flags = SWAPW(entry->flags);
-    le_int16 markIndex = SWAPW(entry->markIndex);
-    le_int16 currIndex = SWAPW(entry->currIndex);
+    le_uint16 markIndex = SWAPW(entry->markIndex);
+    le_uint16 currIndex = SWAPW(entry->currIndex);
 
-    if (markIndex != -1) {
+    if (markIndex != 0x0FFFF) {
+        if (markGlyph < 0 || markGlyph >= glyphStorage.getGlyphCount()) {
+           success = LE_INDEX_OUT_OF_BOUNDS_ERROR;
+           return 0;
+        }
         le_uint32 offset = SWAPL(perGlyphTable(markIndex, success));
         LEGlyphID mGlyph = glyphStorage[markGlyph];
         TTGlyphID newGlyph = lookup(offset, mGlyph, success);
         glyphStorage[markGlyph] = LE_SET_GLYPH(mGlyph, newGlyph);
     }
 
-    if (currIndex != -1) {
+    if (currIndex != 0x0FFFF) {
+        if (currGlyph < 0 || currGlyph >= glyphStorage.getGlyphCount()) {
+           success = LE_INDEX_OUT_OF_BOUNDS_ERROR;
+           return 0;
+        }
         le_uint32 offset = SWAPL(perGlyphTable(currIndex, success));
         LEGlyphID thisGlyph = glyphStorage[currGlyph];
         TTGlyphID newGlyph = lookup(offset, thisGlyph, success);
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/Features.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/Features.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -41,7 +41,7 @@
 LEReferenceTo<FeatureTable> FeatureListTable::getFeatureTable(const LETableReference &base, le_uint16 featureIndex, LETag *featureTag, LEErrorCode &success) const
 {
     LEReferenceToArrayOf<FeatureRecord>
-        featureRecordArrayRef(base, success, featureRecordArray, featureIndex);
+        featureRecordArrayRef(base, success, featureRecordArray, featureIndex+1);
 
   if (featureIndex >= SWAPW(featureCount) || LE_FAILURE(success)) {
     return LEReferenceTo<FeatureTable>();
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/GXLayoutEngine.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/GXLayoutEngine.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -73,7 +73,7 @@
 
     fMorphTable->process(fMorphTable, glyphStorage, success);
 
-    return count;
+    return glyphStorage.getGlyphCount();
 }
 
 // apply positional tables
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/GXLayoutEngine2.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/GXLayoutEngine2.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -69,7 +69,7 @@
     }
 
     fMorphTable->process(fMorphTable, glyphStorage, fTypoFlags, success);
-    return count;
+    return glyphStorage.getGlyphCount();
 }
 
 // apply positional tables
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/IndicRearrangementProcessor.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/IndicRearrangementProcessor.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -70,6 +70,11 @@
     ByteOffset newState = SWAPW(entry->newStateOffset);
     IndicRearrangementFlags flags = (IndicRearrangementFlags) SWAPW(entry->flags);
 
+    if (currGlyph < 0 || currGlyph >= glyphStorage.getGlyphCount()) {
+       success = LE_INDEX_OUT_OF_BOUNDS_ERROR;
+       return 0;
+    }
+
     if (flags & irfMarkFirst) {
         firstGlyph = currGlyph;
     }
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/IndicRearrangementProcessor2.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/IndicRearrangementProcessor2.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -68,6 +68,11 @@
     le_uint16 newState = SWAPW(entry->newStateIndex); // index to the new state
     IndicRearrangementFlags  flags =  (IndicRearrangementFlags) SWAPW(entry->flags);
 
+    if (currGlyph < 0 || currGlyph >= glyphStorage.getGlyphCount()) {
+       success = LE_INDEX_OUT_OF_BOUNDS_ERROR;
+       return 0;
+    }
+
     if (flags & irfMarkFirst) {
         firstGlyph = currGlyph;
     }
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/LETableReference.h	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/LETableReference.h	Wed Jul 05 20:42:36 2017 +0200
@@ -188,7 +188,7 @@
 
   void addOffset(size_t offset, LEErrorCode &success) {
     if(hasBounds()) {
-      if(offset > fLength) {
+      if(offset >= fLength) {
         LE_DEBUG_TR("addOffset off end");
         success = LE_INDEX_OUT_OF_BOUNDS_ERROR;
         return;
@@ -203,7 +203,7 @@
     if(atPtr==NULL) return 0;
     if(LE_FAILURE(success)) return LE_UINTPTR_MAX;
     if((atPtr < fStart) ||
-       (hasBounds() && (atPtr > fStart+fLength))) {
+       (hasBounds() && (atPtr >= fStart+fLength))) {
       LE_DEBUG_TR3("ptrToOffset args out of range: %p", atPtr, 0);
       success = LE_INDEX_OUT_OF_BOUNDS_ERROR;
       return LE_UINTPTR_MAX;
@@ -240,6 +240,18 @@
   }
 
   /**
+  * Throw an error if size*count overflows
+  */
+  size_t verifyLength(size_t offset, size_t size, le_uint32 count, LEErrorCode &success) {
+    if(count!=0 && size>LE_UINT32_MAX/count) {
+      LE_DEBUG_TR3("verifyLength failed size=%u, count=%u", size, count);
+      success = LE_INDEX_OUT_OF_BOUNDS_ERROR;
+      return 0;
+    }
+    return verifyLength(offset, size*count, success);
+  }
+
+  /**
    * Change parent link to another
    */
   LETableReference &reparent(const LETableReference &base) {
@@ -424,7 +436,7 @@
       if(fCount == LE_UNBOUNDED_ARRAY) { // not a known length
         fCount = getLength()/LETableVarSizer<T>::getSize(); // fit to max size
       }
-      LETableReference::verifyLength(0, LETableVarSizer<T>::getSize()*fCount, success);
+      LETableReference::verifyLength(0, LETableVarSizer<T>::getSize(), fCount, success);
     }
     if(LE_FAILURE(success)) {
       fCount=0;
@@ -439,7 +451,7 @@
       if(fCount == LE_UNBOUNDED_ARRAY) { // not a known length
         fCount = getLength()/LETableVarSizer<T>::getSize(); // fit to max size
       }
-      LETableReference::verifyLength(0, LETableVarSizer<T>::getSize()*fCount, success);
+      LETableReference::verifyLength(0, LETableVarSizer<T>::getSize(), fCount, success);
     }
     if(LE_FAILURE(success)) clear();
   }
@@ -450,7 +462,7 @@
       if(fCount == LE_UNBOUNDED_ARRAY) { // not a known length
         fCount = getLength()/LETableVarSizer<T>::getSize(); // fit to max size
       }
-      LETableReference::verifyLength(0, LETableVarSizer<T>::getSize()*fCount, success);
+      LETableReference::verifyLength(0, LETableVarSizer<T>::getSize(), fCount, success);
     }
     if(LE_FAILURE(success)) clear();
   }
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/LigatureSubstProc.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/LigatureSubstProc.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -73,7 +73,7 @@
   const LigatureSubstitutionStateEntry *entry = entryTable.getAlias(index, success);
 
     ByteOffset newState = SWAPW(entry->newStateOffset);
-    le_int16 flags = SWAPW(entry->flags);
+    le_uint16 flags = SWAPW(entry->flags);
 
     if (flags & lsfSetComponent) {
         if (++m >= nComponents) {
@@ -92,15 +92,18 @@
     if (actionOffset != 0) {
       LEReferenceTo<LigatureActionEntry> ap(stHeader, success, actionOffset);
         LigatureActionEntry action;
-        le_int32 offset, i = 0;
+        le_int32 offset, i = 0, j = 0;
         le_int32 stack[nComponents];
         le_int16 mm = -1;
 
         do {
             le_uint32 componentGlyph = componentStack[m--];
 
+            if (j++ > 0) {
+                ap.addObject(success);
+            }
+
             action = SWAPL(*ap.getAlias());
-            ap.addObject(success); // ap++
 
             if (m < 0) {
                 m = nComponents - 1;
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/LigatureSubstProc2.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/LigatureSubstProc2.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -98,7 +98,7 @@
         ap.addObject(ligActionIndex, success);
         LEReferenceToArrayOf<TTGlyphID> ligatureTable(stHeader, success, ligatureOffset, LE_UNBOUNDED_ARRAY);
         LigatureActionEntry action;
-        le_int32 offset, i = 0;
+        le_int32 offset, i = 0, j = 0;
         le_int32 stack[nComponents];
         le_int16 mm = -1;
 
@@ -111,6 +111,10 @@
         do {
             le_uint32 componentGlyph = componentStack[m--]; // pop off
 
+            if (j++ > 0) {
+                ap.addObject(success);
+            }
+
             action = SWAPL(*ap.getAlias());
 
             if (m < 0) {
@@ -144,7 +148,6 @@
               LE_DEBUG_BAD_FONT("m<0")
             }
 #endif
-            ap.addObject(success);
         } while (LE_SUCCESS(success) && !(action & lafLast) && (m>=0) ); // stop if last bit is set, or if run out of items
 
         while (mm >= 0) {
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/MarkToBasePosnSubtables.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/MarkToBasePosnSubtables.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -97,13 +97,9 @@
 
     if( LE_FAILURE(success) ) { return 0; }
     Offset anchorTableOffset = SWAPW(baseRecord->baseAnchorTableOffsetArray[markClass]);
-    if (anchorTableOffset <= 0) {
-        // this means the table is mal-formed...
-        glyphIterator->setCurrGlyphBaseOffset(baseIterator.getCurrStreamPosition());
-        return 0;
-    }
+    LEReferenceTo<AnchorTable> anchorTable(baseArray, success, anchorTableOffset);
+    if( LE_FAILURE(success) ) { return 0; }
 
-    LEReferenceTo<AnchorTable> anchorTable(baseArray, success, anchorTableOffset);
     LEPoint baseAnchor, markAdvance, pixels;
 
 
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/MorphTables.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/MorphTables.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -52,8 +52,15 @@
     le_uint32 chain;
 
     for (chain = 0; LE_SUCCESS(success) && (chain < chainCount); chain += 1) {
+        if (chain > 0) {
+            le_uint32 chainLength = SWAPL(chainHeader->chainLength);
+            if (chainLength & 0x03) { // incorrect alignment for 32 bit tables
+                success = LE_MEMORY_ALLOCATION_ERROR; // as good a choice as any
+                return;
+            }
+            chainHeader.addOffset(chainLength, success);
+        }
         FeatureFlags defaultFlags = SWAPL(chainHeader->defaultFlags);
-        le_uint32 chainLength = SWAPL(chainHeader->chainLength);
         le_int16 nFeatureEntries = SWAPW(chainHeader->nFeatureEntries);
         le_int16 nSubtables = SWAPW(chainHeader->nSubtables);
         LEReferenceTo<MorphSubtableHeader> subtableHeader =
@@ -61,7 +68,14 @@
         le_int16 subtable;
 
         for (subtable = 0; LE_SUCCESS(success) && (subtable < nSubtables); subtable += 1) {
-            le_int16 length = SWAPW(subtableHeader->length);
+            if (subtable > 0) {
+                le_int16 length = SWAPW(subtableHeader->length);
+                if (length & 0x03) { // incorrect alignment for 32 bit tables
+                    success = LE_MEMORY_ALLOCATION_ERROR; // as good a choice as any
+                    return;
+                }
+                subtableHeader.addOffset(length, success);
+            }
             SubtableCoverage coverage = SWAPW(subtableHeader->coverage);
             FeatureFlags subtableFeatures = SWAPL(subtableHeader->subtableFeatures);
 
@@ -69,10 +83,7 @@
             if ((coverage & scfVertical) == 0 && (subtableFeatures & defaultFlags) != 0  && LE_SUCCESS(success)) {
               subtableHeader->process(subtableHeader, glyphStorage, success);
             }
-
-            subtableHeader.addOffset(length, success);
         }
-        chainHeader.addOffset(chainLength, success);
     }
 }
 
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/MorphTables2.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/MorphTables2.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -59,6 +59,10 @@
   for (chain = 0; LE_SUCCESS(success) && (chain < chainCount); chain++) {
         if (chain>0) {
           le_uint32 chainLength = SWAPL(chainHeader->chainLength);
+          if (chainLength & 0x03) { // incorrect alignment for 32 bit tables
+              success = LE_MEMORY_ALLOCATION_ERROR; // as good a choice as any
+              return;
+          }
           chainHeader.addOffset(chainLength, success); // Don't increment the first time
         }
         FeatureFlags flag = SWAPL(chainHeader->defaultFlags);
@@ -188,6 +192,10 @@
         for (subtable = 0;  LE_SUCCESS(success) && subtable < nSubtables; subtable++) {
             if(subtable>0)  {
               le_uint32 length = SWAPL(subtableHeader->length);
+              if (length & 0x03) { // incorrect alignment for 32 bit tables
+                  success = LE_MEMORY_ALLOCATION_ERROR; // as good a choice as any
+                  return;
+              }
               subtableHeader.addOffset(length, success); // Don't addOffset for the last entry.
             }
             le_uint32 coverage = SWAPL(subtableHeader->coverage);
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/PairPositioningSubtables.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/PairPositioningSubtables.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -179,12 +179,13 @@
         LEReferenceTo<PairValueRecord> record(records);
 
         for(le_int32 r = 0; r < recordCount; r += 1) {
+          if (r > 0) {
+            record.addOffset(recordSize, success);
+          }
           if(LE_FAILURE(success)) return LEReferenceTo<PairValueRecord>();
           if (SWAPW(record->secondGlyph) == glyphID) {
             return record;
           }
-
-          record.addOffset(recordSize, success);
         }
 #else
   #error dead code - not updated.
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/SingleSubstitutionSubtables.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/SingleSubstitutionSubtables.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -94,7 +94,9 @@
         return 0;
     }
 
-    if (coverageIndex >= 0) {
+    LEReferenceToArrayOf<TTGlyphID> substituteArrayRef(base, success, substituteArray, SWAPW(glyphCount));
+
+    if (coverageIndex >= 0 && LE_SUCCESS(success) && coverageIndex < substituteArrayRef.getCount()) {
         TTGlyphID substitute = SWAPW(substituteArray[coverageIndex]);
 
         if (filter == NULL || filter->accept(LE_SET_GLYPH(glyph, substitute), success)) {
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/StateTableProcessor.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/StateTableProcessor.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -85,6 +85,7 @@
         if (currGlyph == glyphCount) {
             // XXX: How do we handle EOT vs. EOL?
             classCode = classCodeEOT;
+            break;
         } else {
             TTGlyphID glyphCode = (TTGlyphID) LE_GET_GLYPH(glyphStorage[currGlyph]);
 
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/StateTableProcessor2.cpp	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/StateTableProcessor2.cpp	Wed Jul 05 20:42:36 2017 +0200
@@ -103,6 +103,7 @@
                 if (currGlyph == glyphCount || currGlyph == -1) {
                     // XXX: How do we handle EOT vs. EOL?
                     classCode = classCodeEOT;
+                    break;
                 } else {
                     LEGlyphID gid = glyphStorage[currGlyph];
                     TTGlyphID glyphCode = (TTGlyphID) LE_GET_GLYPH(gid);
@@ -134,6 +135,7 @@
                 if (currGlyph == glyphCount || currGlyph == -1) {
                     // XXX: How do we handle EOT vs. EOL?
                     classCode = classCodeEOT;
+                    break;
                 } else {
                     LEGlyphID gid = glyphStorage[currGlyph];
                     TTGlyphID glyphCode = (TTGlyphID) LE_GET_GLYPH(gid);
@@ -171,6 +173,7 @@
                 if (currGlyph == glyphCount || currGlyph == -1) {
                     // XXX: How do we handle EOT vs. EOL?
                     classCode = classCodeEOT;
+                    break;
                 } else if(currGlyph > glyphCount) {
                   // note if > glyphCount, we've run off the end (bad font)
                   currGlyph = glyphCount;
@@ -211,6 +214,7 @@
                 if (currGlyph == glyphCount || currGlyph == -1) {
                     // XXX: How do we handle EOT vs. EOL?
                     classCode = classCodeEOT;
+                    break;
                 } else {
                     TTGlyphID glyphCode = (TTGlyphID) LE_GET_GLYPH(glyphStorage[currGlyph]);
                     if (glyphCode == 0xFFFF) {
--- a/jdk/src/java.desktop/share/native/libfontmanager/layout/StateTables.h	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libfontmanager/layout/StateTables.h	Wed Jul 05 20:42:36 2017 +0200
@@ -126,7 +126,7 @@
 struct StateEntry
 {
     ByteOffset  newStateOffset;
-    le_int16    flags;
+    le_uint16    flags;
 };
 
 typedef le_uint16 EntryTableIndex2;
--- a/jdk/src/java.desktop/share/native/libsplashscreen/splashscreen_png.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/share/native/libsplashscreen/splashscreen_png.c	Wed Jul 05 20:42:36 2017 +0200
@@ -48,8 +48,8 @@
     int stride;
     ImageFormat srcFormat;
     png_uint_32 i, rowbytes;
-    png_bytepp row_pointers = NULL;
-    png_bytep image_data = NULL;
+    volatile png_bytepp row_pointers = NULL;
+    volatile png_bytep image_data = NULL;
     int success = 0;
     double gamma;
 
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/GtkFileDialogPeer.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/GtkFileDialogPeer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2010, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2010, 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
@@ -116,12 +116,7 @@
                     showNativeDialog();
                     fd.setVisible(false);
                 };
-                if (System.getSecurityManager() == null) {
-                    new Thread(task).start();
-                } else {
-                    new ManagedLocalsThread(task).start();
-                }
-
+                new ManagedLocalsThread(task).start();
             } else {
                 quit();
                 fd.setVisible(false);
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/InfoWindow.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/InfoWindow.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2009, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2009, 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
@@ -29,7 +29,6 @@
 import java.awt.event.*;
 import java.awt.peer.TrayIconPeer;
 import sun.awt.*;
-import sun.misc.InnocuousThread;
 import sun.misc.ManagedLocalsThread;
 
 import java.awt.image.*;
@@ -455,11 +454,7 @@
             final Thread thread;
 
             Displayer() {
-                if (System.getSecurityManager() == null) {
-                    this.thread = new Thread(this);
-                } else {
-                    this.thread = new ManagedLocalsThread(this);
-                }
+                this.thread = new ManagedLocalsThread(this);
                 this.thread.setDaemon(true);
             }
 
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/XTextAreaPeer.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/XTextAreaPeer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 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
@@ -138,6 +138,7 @@
         setScrollBarVisibility();
         // After this line we should not change the component's text
         firstChangeSkipped = true;
+        compAccessor.setPeer(textPane, this);
     }
 
     @Override
@@ -146,7 +147,6 @@
         // visible caret has a timer thread which must be stopped
         jtext.getCaret().setVisible(false);
         jtext.removeNotify();
-        textPane.removeNotify();
         super.dispose();
     }
 
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/XTextFieldPeer.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/XTextFieldPeer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 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
@@ -95,6 +95,7 @@
 
         // After this line we should not change the component's text
         firstChangeSkipped = true;
+        AWTAccessor.getComponentAccessor().setPeer(xtext, this);
     }
 
     @Override
@@ -102,7 +103,6 @@
         XToolkit.specialPeerMap.remove(xtext);
         // visible caret has a timer thread which must be stopped
         xtext.getCaret().setVisible(false);
-        xtext.removeNotify();
         super.dispose();
     }
 
@@ -259,7 +259,9 @@
         }
         background = c;
         if (xtext != null) {
-            xtext.setBackground(c);
+            if (xtext.getBackground() != c) {
+                xtext.setBackground(c);
+            }
             xtext.setSelectedTextColor(c);
         }
         repaintText();
@@ -269,7 +271,9 @@
     public void setForeground(Color c) {
         foreground = c;
         if (xtext != null) {
-            xtext.setForeground(foreground);
+            if (xtext.getForeground() != c) {
+                xtext.setForeground(foreground);
+            }
             xtext.setSelectionColor(foreground);
             xtext.setCaretColor(foreground);
         }
@@ -280,7 +284,7 @@
     public void setFont(Font f) {
         synchronized (getStateLock()) {
             font = f;
-            if (xtext != null) {
+            if (xtext != null && xtext.getFont() != f) {
                 xtext.setFont(font);
             }
         }
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/XToolkit.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/XToolkit.java	Wed Jul 05 20:42:36 2017 +0200
@@ -281,12 +281,8 @@
                 }
             };
             String name = "XToolkt-Shutdown-Thread";
-            Thread shutdownThread;
-            if (System.getSecurityManager() == null) {
-                shutdownThread = new Thread(ThreadGroupUtils.getRootThreadGroup(), r, name);
-            } else {
-                shutdownThread = new InnocuousThread(r, name);
-            }
+            Thread shutdownThread = new ManagedLocalsThread(
+                    ThreadGroupUtils.getRootThreadGroup(), r, name);
             shutdownThread.setContextClassLoader(null);
             Runtime.getRuntime().addShutdownHook(shutdownThread);
             return null;
@@ -333,12 +329,8 @@
 
             toolkitThread = AccessController.doPrivileged((PrivilegedAction<Thread>) () -> {
                 String name = "AWT-XAWT";
-                Thread thread;
-                if (System.getSecurityManager() == null) {
-                    thread = new Thread(ThreadGroupUtils.getRootThreadGroup(), XToolkit.this, name);
-                } else {
-                    thread = new InnocuousThread(XToolkit.this, name);
-                }
+                Thread thread = new ManagedLocalsThread(
+                        ThreadGroupUtils.getRootThreadGroup(), this, name);
                 thread.setContextClassLoader(null);
                 thread.setPriority(Thread.NORM_PRIORITY + 1);
                 thread.setDaemon(true);
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11/XWindowPeer.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11/XWindowPeer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -682,28 +682,33 @@
         GraphicsConfiguration newGC = null;
         Rectangle screenBounds;
 
-        for (int i = 0; i < gds.length; i++) {
-            screenBounds = gds[i].getDefaultConfiguration().getBounds();
-            if (newBounds.intersects(screenBounds)) {
-                horizAmt = Math.min(newBounds.x + newBounds.width,
-                                    screenBounds.x + screenBounds.width) -
-                           Math.max(newBounds.x, screenBounds.x);
-                vertAmt = Math.min(newBounds.y + newBounds.height,
-                                   screenBounds.y + screenBounds.height)-
-                          Math.max(newBounds.y, screenBounds.y);
-                intAmt = horizAmt * vertAmt;
-                if (intAmt == area) {
-                    // Completely on this screen - done!
-                    newScreenNum = i;
-                    newGC = gds[i].getDefaultConfiguration();
-                    break;
-                }
-                if (intAmt > largestAmt) {
-                    largestAmt = intAmt;
-                    newScreenNum = i;
-                    newGC = gds[i].getDefaultConfiguration();
+        XToolkit.awtUnlock();
+        try {
+            for (int i = 0; i < gds.length; i++) {
+                screenBounds = gds[i].getDefaultConfiguration().getBounds();
+                if (newBounds.intersects(screenBounds)) {
+                    horizAmt = Math.min(newBounds.x + newBounds.width,
+                                        screenBounds.x + screenBounds.width) -
+                               Math.max(newBounds.x, screenBounds.x);
+                    vertAmt = Math.min(newBounds.y + newBounds.height,
+                                       screenBounds.y + screenBounds.height)-
+                              Math.max(newBounds.y, screenBounds.y);
+                    intAmt = horizAmt * vertAmt;
+                    if (intAmt == area) {
+                        // Completely on this screen - done!
+                        newScreenNum = i;
+                        newGC = gds[i].getDefaultConfiguration();
+                        break;
+                    }
+                    if (intAmt > largestAmt) {
+                        largestAmt = intAmt;
+                        newScreenNum = i;
+                        newGC = gds[i].getDefaultConfiguration();
+                    }
                 }
             }
+        } finally {
+            XToolkit.awtLock();
         }
         if (newScreenNum != curScreenNum) {
             if (log.isLoggable(PlatformLogger.Level.FINEST)) {
--- a/jdk/src/java.desktop/unix/classes/sun/awt/X11GraphicsDevice.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/unix/classes/sun/awt/X11GraphicsDevice.java	Wed Jul 05 20:42:36 2017 +0200
@@ -43,7 +43,7 @@
 import sun.java2d.loops.SurfaceType;
 
 import sun.awt.util.ThreadGroupUtils;
-import sun.misc.InnocuousThread;
+import sun.misc.ManagedLocalsThread;
 
 /**
  * This is an implementation of a GraphicsDevice object for a single
@@ -284,7 +284,6 @@
      * Returns true only if:
      *   - the Xrandr extension is present
      *   - the necessary Xrandr functions were loaded successfully
-     *   - XINERAMA is not enabled
      */
     private static synchronized boolean isXrandrExtensionSupported() {
         if (xrandrExtSupported == null) {
@@ -316,7 +315,9 @@
 
     @Override
     public boolean isDisplayChangeSupported() {
-        return (isFullScreenSupported() && (getFullScreenWindow() != null));
+        return (isFullScreenSupported()
+                && !((X11GraphicsEnvironment) GraphicsEnvironment
+                        .getLocalGraphicsEnvironment()).runningXinerama());
     }
 
     private static void enterFullScreenExclusive(Window w) {
@@ -346,7 +347,9 @@
         if (fsSupported && old != null) {
             // enter windowed mode (and restore original display mode)
             exitFullScreenExclusive(old);
-            setDisplayMode(origDisplayMode);
+            if (isDisplayChangeSupported()) {
+                setDisplayMode(origDisplayMode);
+            }
         }
 
         super.setFullScreenWindow(w);
@@ -428,16 +431,14 @@
                     Window old = getFullScreenWindow();
                     if (old != null) {
                         exitFullScreenExclusive(old);
-                        setDisplayMode(origDisplayMode);
+                        if (isDisplayChangeSupported()) {
+                            setDisplayMode(origDisplayMode);
+                        }
                     }
                 };
                 String name = "Display-Change-Shutdown-Thread-" + screen;
-                Thread t;
-                if (System.getSecurityManager() == null) {
-                    t = new Thread(ThreadGroupUtils.getRootThreadGroup(), r, name);
-                } else {
-                    t = new InnocuousThread(r, name);
-                }
+                Thread t = new ManagedLocalsThread(
+                        ThreadGroupUtils.getRootThreadGroup(), r, name);
                 t.setContextClassLoader(null);
                 Runtime.getRuntime().addShutdownHook(t);
                 return null;
--- a/jdk/src/java.desktop/unix/classes/sun/java2d/opengl/GLXGraphicsConfig.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/unix/classes/sun/java2d/opengl/GLXGraphicsConfig.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2008, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 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
@@ -399,23 +399,11 @@
         createCompatibleVolatileImage(int width, int height,
                                       int transparency, int type)
     {
-        if (type == FLIP_BACKBUFFER || type == WINDOW || type == UNDEFINED ||
-            transparency == Transparency.BITMASK)
-        {
+        if ((type != FBOBJECT && type != TEXTURE)
+                || transparency == Transparency.BITMASK
+                || type == FBOBJECT && !isCapPresent(CAPS_EXT_FBOBJECT)) {
             return null;
         }
-
-        if (type == FBOBJECT) {
-            if (!isCapPresent(CAPS_EXT_FBOBJECT)) {
-                return null;
-            }
-        } else if (type == PBUFFER) {
-            boolean isOpaque = transparency == Transparency.OPAQUE;
-            if (!isOpaque && !isCapPresent(CAPS_STORED_ALPHA)) {
-                return null;
-            }
-        }
-
         SunVolatileImage vi = new AccelTypedVolatileImage(this, width, height,
                                                           transparency, type);
         Surface sd = vi.getDestSurface();
--- a/jdk/src/java.desktop/unix/classes/sun/java2d/opengl/GLXSurfaceData.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/unix/classes/sun/java2d/opengl/GLXSurfaceData.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2008, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 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
@@ -30,11 +30,10 @@
 import java.awt.GraphicsEnvironment;
 import java.awt.Image;
 import java.awt.Rectangle;
-import java.awt.Transparency;
 import java.awt.image.ColorModel;
+
 import sun.awt.X11ComponentPeer;
 import sun.java2d.SurfaceData;
-import sun.java2d.loops.SurfaceType;
 
 public abstract class GLXSurfaceData extends OGLSurfaceData {
 
@@ -42,9 +41,6 @@
     private GLXGraphicsConfig graphicsConfig;
 
     private native void initOps(X11ComponentPeer peer, long aData);
-    protected native boolean initPbuffer(long pData, long pConfigInfo,
-                                         boolean isOpaque,
-                                         int width, int height);
 
     protected GLXSurfaceData(X11ComponentPeer peer, GLXGraphicsConfig gc,
                              ColorModel cm, int type)
@@ -91,7 +87,7 @@
 
     /**
      * Creates a SurfaceData object representing an off-screen buffer (either
-     * a Pbuffer or Texture).
+     * a FBO or Texture).
      */
     public static GLXOffScreenSurfaceData createData(GLXGraphicsConfig gc,
                                                      int width, int height,
--- a/jdk/src/java.desktop/unix/classes/sun/java2d/opengl/GLXVolatileSurfaceManager.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/unix/classes/sun/java2d/opengl/GLXVolatileSurfaceManager.java	Wed Jul 05 20:42:36 2017 +0200
@@ -46,7 +46,7 @@
 
 public class GLXVolatileSurfaceManager extends VolatileSurfaceManager {
 
-    private boolean accelerationEnabled;
+    private final boolean accelerationEnabled;
 
     public GLXVolatileSurfaceManager(SunVolatileImage vImg, Object context) {
         super(vImg, context);
@@ -54,18 +54,13 @@
         /*
          * We will attempt to accelerate this image only under the
          * following conditions:
-         *   - the image is opaque OR
-         *   - the image is translucent AND
-         *       - the GraphicsConfig supports the FBO extension OR
-         *       - the GraphicsConfig has a stored alpha channel
+         *   - the image is not bitmask AND the GraphicsConfig supports the FBO
+         *     extension
          */
         int transparency = vImg.getTransparency();
-        GLXGraphicsConfig gc = (GLXGraphicsConfig)vImg.getGraphicsConfig();
-        accelerationEnabled =
-            (transparency == Transparency.OPAQUE) ||
-            ((transparency == Transparency.TRANSLUCENT) &&
-             (gc.isCapPresent(CAPS_EXT_FBOBJECT) ||
-              gc.isCapPresent(CAPS_STORED_ALPHA)));
+        GLXGraphicsConfig gc = (GLXGraphicsConfig) vImg.getGraphicsConfig();
+        accelerationEnabled = gc.isCapPresent(CAPS_EXT_FBOBJECT)
+                && transparency != Transparency.BITMASK;
     }
 
     protected boolean isAccelerationEnabled() {
@@ -73,7 +68,7 @@
     }
 
     /**
-     * Create a pbuffer-based SurfaceData object (or init the backbuffer
+     * Create a FBO-based SurfaceData object (or init the backbuffer
      * of an existing window if this is a double buffered GraphicsConfig)
      */
     protected SurfaceData initAcceleratedSurface() {
@@ -113,10 +108,9 @@
                 ColorModel cm = gc.getColorModel(vImg.getTransparency());
                 int type = vImg.getForcedAccelSurfaceType();
                 // if acceleration type is forced (type != UNDEFINED) then
-                // use the forced type, otherwise choose one based on caps
+                // use the forced type, otherwise choose FBOBJECT
                 if (type == OGLSurfaceData.UNDEFINED) {
-                    type = gc.isCapPresent(CAPS_EXT_FBOBJECT) ?
-                        OGLSurfaceData.FBOBJECT : OGLSurfaceData.PBUFFER;
+                    type = OGLSurfaceData.FBOBJECT;
                 }
                 if (createVSynced) {
                     sData = GLXSurfaceData.createData(peer, vImg, type);
--- a/jdk/src/java.desktop/unix/classes/sun/print/PrintServiceLookupProvider.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/unix/classes/sun/print/PrintServiceLookupProvider.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 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
@@ -213,12 +213,7 @@
     public PrintServiceLookupProvider() {
         // start the printer listener thread
         if (pollServices) {
-            Thread thr;
-            if (System.getSecurityManager() == null) {
-                thr = new Thread(new PrinterChangeListener());
-            } else {
-                thr = new ManagedLocalsThread(new PrinterChangeListener());
-            }
+            Thread thr = new ManagedLocalsThread(new PrinterChangeListener());
             thr.setDaemon(true);
             thr.start();
             IPPPrintService.debug_println(debugPrefix+"polling turned on");
--- a/jdk/src/java.desktop/unix/native/common/java2d/opengl/GLXGraphicsConfig.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/unix/native/common/java2d/opengl/GLXGraphicsConfig.c	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2008, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 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
@@ -472,7 +472,7 @@
     GLXPbuffer scratch;
     GLXGraphicsConfigInfo *glxinfo;
     jint caps = CAPS_EMPTY;
-    int db, alpha;
+    int db;
     const unsigned char *versionstr;
 
     J2dRlsTraceLn(J2D_TRACE_INFO, "GLXGraphicsConfig_getGLXConfigInfo");
@@ -583,10 +583,6 @@
     if (db) {
         caps |= CAPS_DOUBLEBUFFERED;
     }
-    j2d_glXGetFBConfigAttrib(awt_display, fbconfig, GLX_ALPHA_SIZE, &alpha);
-    if (alpha > 0) {
-        caps |= CAPS_STORED_ALPHA;
-    }
 
     // initialize the OGLContext, which wraps the GLXFBConfig and GLXContext
     oglc = GLXGC_InitOGLContext(fbconfig, context, scratch, caps);
--- a/jdk/src/java.desktop/unix/native/common/java2d/opengl/GLXSurfaceData.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/unix/native/common/java2d/opengl/GLXSurfaceData.c	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 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
@@ -111,25 +111,13 @@
 
 /**
  * This function disposes of any native windowing system resources associated
- * with this surface.  For instance, if the given OGLSDOps is of type
- * OGLSD_PBUFFER, this method implementation will destroy the actual pbuffer
- * surface.
+ * with this surface.
  */
 void
 OGLSD_DestroyOGLSurface(JNIEnv *env, OGLSDOps *oglsdo)
 {
-    GLXSDOps *glxsdo = (GLXSDOps *)oglsdo->privOps;
-
     J2dTraceLn(J2D_TRACE_INFO, "OGLSD_DestroyOGLSurface");
-
-    if (oglsdo->drawableType == OGLSD_PBUFFER) {
-        if (glxsdo->drawable != 0) {
-            j2d_glXDestroyPbuffer(awt_display, glxsdo->drawable);
-            glxsdo->drawable = 0;
-        }
-    } else if (oglsdo->drawableType == OGLSD_WINDOW) {
-        // X Window is free'd later by AWT code...
-    }
+    // X Window is free'd later by AWT code...
 }
 
 /**
@@ -358,74 +346,6 @@
     return 0;
 }
 
-JNIEXPORT jboolean JNICALL
-Java_sun_java2d_opengl_GLXSurfaceData_initPbuffer
-    (JNIEnv *env, jobject glxsd,
-     jlong pData, jlong pConfigInfo,
-     jboolean isOpaque,
-     jint width, jint height)
-{
-    OGLSDOps *oglsdo = (OGLSDOps *)jlong_to_ptr(pData);
-    GLXGraphicsConfigInfo *glxinfo =
-        (GLXGraphicsConfigInfo *)jlong_to_ptr(pConfigInfo);
-    GLXSDOps *glxsdo;
-    GLXPbuffer pbuffer;
-    int attrlist[] = {GLX_PBUFFER_WIDTH, 0,
-                      GLX_PBUFFER_HEIGHT, 0,
-                      GLX_PRESERVED_CONTENTS, GL_FALSE, 0};
-
-    J2dTraceLn3(J2D_TRACE_INFO,
-                "GLXSurfaceData_initPbuffer: w=%d h=%d opq=%d",
-                width, height, isOpaque);
-
-    if (oglsdo == NULL) {
-        J2dRlsTraceLn(J2D_TRACE_ERROR,
-                      "GLXSurfaceData_initPbuffer: ops are null");
-        return JNI_FALSE;
-    }
-
-    glxsdo = (GLXSDOps *)oglsdo->privOps;
-    if (glxsdo == NULL) {
-        J2dRlsTraceLn(J2D_TRACE_ERROR,
-                      "GLXSurfaceData_initPbuffer: glx ops are null");
-        return JNI_FALSE;
-    }
-
-    if (glxinfo == NULL) {
-        J2dRlsTraceLn(J2D_TRACE_ERROR,
-                      "GLXSurfaceData_initPbuffer: glx config info is null");
-        return JNI_FALSE;
-    }
-
-    attrlist[1] = width;
-    attrlist[3] = height;
-
-    surfaceCreationFailed = JNI_FALSE;
-    EXEC_WITH_XERROR_HANDLER(
-        GLXSD_BadAllocXErrHandler,
-        pbuffer = j2d_glXCreatePbuffer(awt_display,
-                                       glxinfo->fbconfig, attrlist));
-    if ((pbuffer == 0) || surfaceCreationFailed) {
-        J2dRlsTraceLn(J2D_TRACE_ERROR,
-            "GLXSurfaceData_initPbuffer: could not create glx pbuffer");
-        return JNI_FALSE;
-    }
-
-    oglsdo->drawableType = OGLSD_PBUFFER;
-    oglsdo->isOpaque = isOpaque;
-    oglsdo->width = width;
-    oglsdo->height = height;
-    oglsdo->xOffset = 0;
-    oglsdo->yOffset = 0;
-
-    glxsdo->drawable = pbuffer;
-    glxsdo->xdrawable = 0;
-
-    OGLSD_SetNativeDimensions(env, oglsdo, width, height);
-
-    return JNI_TRUE;
-}
-
 void
 OGLSD_SwapBuffers(JNIEnv *env, jlong window)
 {
--- a/jdk/src/java.desktop/unix/native/libawt_xawt/xawt/XToolkit.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/unix/native/libawt_xawt/xawt/XToolkit.c	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2002, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2002, 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
@@ -554,8 +554,10 @@
             curPollTimeout = min(AWT_MAX_POLL_TIMEOUT, curPollTimeout);
         } else if (timeout_control == TIMEOUT_EVENTS) {
             /* subtract 1/4 (plus 1, in case the division truncates to 0) */
-            curPollTimeout -= ((curPollTimeout>>2) + 1);
-            curPollTimeout = max(AWT_MIN_POLL_TIMEOUT, curPollTimeout);
+            if (curPollTimeout > 0) {
+                curPollTimeout -= ((curPollTimeout>>2) + 1);
+                curPollTimeout = max(AWT_MIN_POLL_TIMEOUT, curPollTimeout);
+            }
         }
         break;
     case AWT_POLL_AGING_FAST:
--- a/jdk/src/java.desktop/windows/classes/sun/awt/shell/Win32ShellFolderManager2.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/windows/classes/sun/awt/shell/Win32ShellFolderManager2.java	Wed Jul 05 20:42:36 2017 +0200
@@ -41,8 +41,7 @@
 import static sun.awt.shell.Win32ShellFolder2.*;
 import sun.awt.OSInfo;
 import sun.awt.util.ThreadGroupUtils;
-import sun.misc.InnocuousThread;
-
+import sun.misc.ManagedLocalsThread;
 // NOTE: This class supersedes Win32ShellFolderManager, which was removed
 //       from distribution after version 1.4.2.
 
@@ -525,12 +524,8 @@
                 return null;
             });
             AccessController.doPrivileged((PrivilegedAction<Void>) () -> {
-                Thread t;
-                if (System.getSecurityManager() == null) {
-                    t = new Thread(ThreadGroupUtils.getRootThreadGroup(), shutdownHook);
-                } else {
-                    t = new InnocuousThread(shutdownHook);
-                }
+                Thread t = new ManagedLocalsThread(
+                        ThreadGroupUtils.getRootThreadGroup(), shutdownHook);
                 Runtime.getRuntime().addShutdownHook(t);
                 return null;
             });
@@ -549,17 +544,12 @@
             };
             comThread = AccessController.doPrivileged((PrivilegedAction<Thread>) () -> {
                 String name = "Swing-Shell";
-                Thread thread;
-                if (System.getSecurityManager() == null) {
-                     /* The thread must be a member of a thread group
-                      * which will not get GCed before VM exit.
-                      * Make its parent the top-level thread group.
-                      */
-                    thread = new Thread(ThreadGroupUtils.getRootThreadGroup(), comRun, name);
-                } else {
-                    /* InnocuousThread is a member of a correct TG by default */
-                    thread = new InnocuousThread(comRun, name);
-                }
+                 /* The thread must be a member of a thread group
+                  * which will not get GCed before VM exit.
+                  * Make its parent the top-level thread group.
+                  */
+                Thread thread = new ManagedLocalsThread(
+                        ThreadGroupUtils.getRootThreadGroup(), comRun, name);
                 thread.setDaemon(true);
                 return thread;
             });
--- a/jdk/src/java.desktop/windows/classes/sun/awt/windows/WFileDialogPeer.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/windows/classes/sun/awt/windows/WFileDialogPeer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1996, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1996, 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
@@ -98,11 +98,7 @@
 
     @Override
     public void show() {
-        if (System.getSecurityManager() == null) {
-            new Thread(this::_show).start();
-        } else {
-            new ManagedLocalsThread(this::_show).start();
-        }
+        new ManagedLocalsThread(this::_show).start();
     }
 
     @Override
--- a/jdk/src/java.desktop/windows/classes/sun/awt/windows/WPageDialogPeer.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/windows/classes/sun/awt/windows/WPageDialogPeer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 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
@@ -53,10 +53,6 @@
             }
             ((WPrintDialog)target).setVisible(false);
         };
-        if (System.getSecurityManager() == null) {
-            new Thread(runnable).start();
-        } else {
-            new ManagedLocalsThread(runnable).start();
-        }
+        new ManagedLocalsThread(runnable).start();
     }
 }
--- a/jdk/src/java.desktop/windows/classes/sun/awt/windows/WPrintDialogPeer.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/windows/classes/sun/awt/windows/WPrintDialogPeer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1999, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1999, 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
@@ -78,11 +78,7 @@
             }
             ((WPrintDialog)target).setVisible(false);
         };
-        if (System.getSecurityManager() == null) {
-            new Thread(runnable).start();
-        } else {
-            new ManagedLocalsThread(runnable).start();
-        }
+        new ManagedLocalsThread(runnable).start();
     }
 
     synchronized void setHWnd(long hwnd) {
--- a/jdk/src/java.desktop/windows/classes/sun/awt/windows/WToolkit.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/windows/classes/sun/awt/windows/WToolkit.java	Wed Jul 05 20:42:36 2017 +0200
@@ -51,7 +51,7 @@
 import sun.java2d.d3d.D3DRenderQueue;
 import sun.java2d.opengl.OGLRenderQueue;
 
-import sun.misc.InnocuousThread;
+import sun.misc.ManagedLocalsThread;
 import sun.print.PrintJob2D;
 
 import java.awt.dnd.DragSource;
@@ -255,12 +255,7 @@
                 (PrivilegedAction<ThreadGroup>) ThreadGroupUtils::getRootThreadGroup);
         if (!startToolkitThread(this, rootTG)) {
             String name = "AWT-Windows";
-            Thread toolkitThread;
-            if (System.getSecurityManager() == null) {
-                toolkitThread = new Thread(rootTG, this, name);
-            } else {
-                toolkitThread = new InnocuousThread(this, name);
-            }
+            Thread toolkitThread = new ManagedLocalsThread(rootTG, this, name);
             toolkitThread.setDaemon(true);
             toolkitThread.start();
         }
@@ -287,16 +282,12 @@
 
     private void registerShutdownHook() {
         AccessController.doPrivileged((PrivilegedAction<Void>) () -> {
-            Thread shutdown;
-            if (System.getSecurityManager() == null) {
-                shutdown = new Thread(ThreadGroupUtils.getRootThreadGroup(), this::shutdown);
-            } else {
-                shutdown = new InnocuousThread(this::shutdown);
-            }
+            Thread shutdown = new ManagedLocalsThread(
+                    ThreadGroupUtils.getRootThreadGroup(), this::shutdown);
             shutdown.setContextClassLoader(null);
             Runtime.getRuntime().addShutdownHook(shutdown);
             return null;
-         });
+        });
      }
 
     @Override
--- a/jdk/src/java.desktop/windows/classes/sun/java2d/d3d/D3DScreenUpdateManager.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/windows/classes/sun/java2d/d3d/D3DScreenUpdateManager.java	Wed Jul 05 20:42:36 2017 +0200
@@ -49,7 +49,7 @@
 import sun.java2d.windows.GDIWindowSurfaceData;
 import sun.java2d.d3d.D3DSurfaceData.D3DWindowSurfaceData;
 import sun.java2d.windows.WindowsFlags;
-import sun.misc.InnocuousThread;
+import sun.misc.ManagedLocalsThread;
 
 /**
  * This class handles rendering to the screen with the D3D pipeline.
@@ -99,12 +99,8 @@
                 done = true;
                 wakeUpUpdateThread();
             };
-            Thread shutdown;
-            if (System.getSecurityManager() == null) {
-                shutdown = new Thread(ThreadGroupUtils.getRootThreadGroup(), shutdownRunnable);
-            } else {
-                shutdown = new InnocuousThread(shutdownRunnable);
-            }
+            Thread shutdown = new ManagedLocalsThread(
+                    ThreadGroupUtils.getRootThreadGroup(), shutdownRunnable);
             shutdown.setContextClassLoader(null);
             try {
                 Runtime.getRuntime().addShutdownHook(shutdown);
@@ -351,15 +347,9 @@
     private synchronized void startUpdateThread() {
         if (screenUpdater == null) {
             screenUpdater = AccessController.doPrivileged((PrivilegedAction<Thread>) () -> {
-                Thread t;
                 String name = "D3D Screen Updater";
-                if (System.getSecurityManager() == null) {
-                    t = new Thread(ThreadGroupUtils.getRootThreadGroup(),
-                            D3DScreenUpdateManager.this,
-                            name);
-                } else {
-                    t = new InnocuousThread(D3DScreenUpdateManager.this, name);
-                }
+                Thread t = new ManagedLocalsThread(
+                        ThreadGroupUtils.getRootThreadGroup(), this, name);
                 // REMIND: should it be higher?
                 t.setPriority(Thread.NORM_PRIORITY + 2);
                 t.setDaemon(true);
--- a/jdk/src/java.desktop/windows/classes/sun/java2d/opengl/WGLGraphicsConfig.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/windows/classes/sun/java2d/opengl/WGLGraphicsConfig.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -27,7 +27,6 @@
 
 import java.awt.AWTException;
 import java.awt.BufferCapabilities;
-import java.awt.BufferCapabilities.FlipContents;
 import java.awt.Color;
 import java.awt.Component;
 import java.awt.Graphics;
@@ -425,23 +424,11 @@
         createCompatibleVolatileImage(int width, int height,
                                       int transparency, int type)
     {
-        if (type == FLIP_BACKBUFFER || type == WINDOW || type == UNDEFINED ||
-            transparency == Transparency.BITMASK)
-        {
+        if ((type != FBOBJECT && type != TEXTURE)
+                || transparency == Transparency.BITMASK
+                || type == FBOBJECT && !isCapPresent(CAPS_EXT_FBOBJECT)) {
             return null;
         }
-
-        if (type == FBOBJECT) {
-            if (!isCapPresent(CAPS_EXT_FBOBJECT)) {
-                return null;
-            }
-        } else if (type == PBUFFER) {
-            boolean isOpaque = transparency == Transparency.OPAQUE;
-            if (!isOpaque && !isCapPresent(CAPS_STORED_ALPHA)) {
-                return null;
-            }
-        }
-
         SunVolatileImage vi = new AccelTypedVolatileImage(this, width, height,
                                                           transparency, type);
         Surface sd = vi.getDestSurface();
--- a/jdk/src/java.desktop/windows/classes/sun/java2d/opengl/WGLSurfaceData.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/windows/classes/sun/java2d/opengl/WGLSurfaceData.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2009, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -43,9 +43,6 @@
 
     private native void initOps(long pConfigInfo, WComponentPeer peer,
                                 long hwnd);
-    protected native boolean initPbuffer(long pData, long pConfigInfo,
-                                         boolean isOpaque,
-                                         int width, int height);
 
     protected WGLSurfaceData(WComponentPeer peer, WGLGraphicsConfig gc,
                              ColorModel cm, int type)
--- a/jdk/src/java.desktop/windows/classes/sun/java2d/opengl/WGLVolatileSurfaceManager.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/windows/classes/sun/java2d/opengl/WGLVolatileSurfaceManager.java	Wed Jul 05 20:42:36 2017 +0200
@@ -43,10 +43,9 @@
 import sun.java2d.pipe.hw.ExtendedBufferCapabilities;
 import static sun.java2d.pipe.hw.ExtendedBufferCapabilities.VSyncType.*;
 
-public class WGLVolatileSurfaceManager
-    extends VolatileSurfaceManager
-{
-    private boolean accelerationEnabled;
+public class WGLVolatileSurfaceManager extends VolatileSurfaceManager {
+
+    private final boolean accelerationEnabled;
 
     public WGLVolatileSurfaceManager(SunVolatileImage vImg, Object context) {
         super(vImg, context);
@@ -54,18 +53,13 @@
         /*
          * We will attempt to accelerate this image only under the
          * following conditions:
-         *   - the image is opaque OR
-         *   - the image is translucent AND
-         *       - the GraphicsConfig supports the FBO extension OR
-         *       - the GraphicsConfig has a stored alpha channel
+         *   - the image is not bitmask AND the GraphicsConfig supports the FBO
+         *     extension
          */
         int transparency = vImg.getTransparency();
-        WGLGraphicsConfig gc = (WGLGraphicsConfig)vImg.getGraphicsConfig();
-        accelerationEnabled =
-            (transparency == Transparency.OPAQUE) ||
-            ((transparency == Transparency.TRANSLUCENT) &&
-             (gc.isCapPresent(CAPS_EXT_FBOBJECT) ||
-              gc.isCapPresent(CAPS_STORED_ALPHA)));
+        WGLGraphicsConfig gc = (WGLGraphicsConfig) vImg.getGraphicsConfig();
+        accelerationEnabled = gc.isCapPresent(CAPS_EXT_FBOBJECT)
+                && transparency != Transparency.BITMASK;
     }
 
     protected boolean isAccelerationEnabled() {
@@ -73,7 +67,7 @@
     }
 
     /**
-     * Create a pbuffer-based SurfaceData object (or init the backbuffer
+     * Create a FBO-based SurfaceData object (or init the backbuffer
      * of an existing window if this is a double buffered GraphicsConfig).
      */
     protected SurfaceData initAcceleratedSurface() {
@@ -111,10 +105,9 @@
                 ColorModel cm = gc.getColorModel(vImg.getTransparency());
                 int type = vImg.getForcedAccelSurfaceType();
                 // if acceleration type is forced (type != UNDEFINED) then
-                // use the forced type, otherwise choose one based on caps
+                // use the forced type, otherwise choose FBOBJECT
                 if (type == OGLSurfaceData.UNDEFINED) {
-                    type = gc.isCapPresent(CAPS_EXT_FBOBJECT) ?
-                        OGLSurfaceData.FBOBJECT : OGLSurfaceData.PBUFFER;
+                    type = OGLSurfaceData.FBOBJECT;
                 }
                 if (createVSynced) {
                     sData = WGLSurfaceData.createData(peer, vImg, type);
--- a/jdk/src/java.desktop/windows/classes/sun/print/PrintServiceLookupProvider.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/windows/classes/sun/print/PrintServiceLookupProvider.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 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
@@ -99,12 +99,7 @@
                 return;
             }
             // start the printer listener thread
-            Thread thr;
-            if (System.getSecurityManager() == null) {
-                thr = new Thread(new PrinterChangeListener());
-            } else {
-                thr = new ManagedLocalsThread(new PrinterChangeListener());
-            }
+            Thread thr = new ManagedLocalsThread(new PrinterChangeListener());
             thr.setDaemon(true);
             thr.start();
         } /* else condition ought to never happen! */
--- a/jdk/src/java.desktop/windows/native/libawt/java2d/opengl/WGLGraphicsConfig.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/windows/native/libawt/java2d/opengl/WGLGraphicsConfig.c	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2008, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -502,8 +502,8 @@
     const unsigned char *versionstr;
     const char *extstr;
     jint caps = CAPS_EMPTY;
-    int attrKeys[] = { WGL_DOUBLE_BUFFER_ARB, WGL_ALPHA_BITS_ARB };
-    int attrVals[2];
+    int attrKeys[] = { WGL_DOUBLE_BUFFER_ARB};
+    int attrVals[1];
 
     J2dRlsTraceLn(J2D_TRACE_INFO, "WGLGraphicsConfig_getWGLConfigInfo");
 
@@ -624,13 +624,10 @@
     }
 
     // get config-specific capabilities
-    j2d_wglGetPixelFormatAttribivARB(hdc, pixfmt, 0, 2, attrKeys, attrVals);
+    j2d_wglGetPixelFormatAttribivARB(hdc, pixfmt, 0, 1, attrKeys, attrVals);
     if (attrVals[0]) {
         caps |= CAPS_DOUBLEBUFFERED;
     }
-    if (attrVals[1] > 0) {
-        caps |= CAPS_STORED_ALPHA;
-    }
 
     // create the scratch pbuffer
     scratch = j2d_wglCreatePbufferARB(hdc, pixfmt, 1, 1, NULL);
--- a/jdk/src/java.desktop/windows/native/libawt/java2d/opengl/WGLSurfaceData.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.desktop/windows/native/libawt/java2d/opengl/WGLSurfaceData.c	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2004, 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
@@ -107,28 +107,13 @@
 
 /**
  * This function disposes of any native windowing system resources associated
- * with this surface.  For instance, if the given OGLSDOps is of type
- * OGLSD_PBUFFER, this method implementation will destroy the actual pbuffer
- * surface.
+ * with this surface.
  */
 void
 OGLSD_DestroyOGLSurface(JNIEnv *env, OGLSDOps *oglsdo)
 {
-    WGLSDOps *wglsdo = (WGLSDOps *)oglsdo->privOps;
-
     J2dTraceLn(J2D_TRACE_INFO, "OGLSD_DestroyOGLSurface");
-
-    if (oglsdo->drawableType == OGLSD_PBUFFER) {
-        if (wglsdo->pbuffer != 0) {
-            if (wglsdo->pbufferDC != 0) {
-                j2d_wglReleasePbufferDCARB(wglsdo->pbuffer,
-                                           wglsdo->pbufferDC);
-                wglsdo->pbufferDC = 0;
-            }
-            j2d_wglDestroyPbufferARB(wglsdo->pbuffer);
-            wglsdo->pbuffer = 0;
-        }
-    }
+    // Window is free'd later by AWT code...
 }
 
 /**
@@ -276,19 +261,11 @@
     ctxinfo = (WGLCtxInfo *)oglc->ctxInfo;
 
     // get the hdc for the destination surface
-    if (dstOps->drawableType == OGLSD_PBUFFER) {
-        dstHDC = dstWGLOps->pbufferDC;
-    } else {
-        dstHDC = GetDC(dstWGLOps->window);
-    }
+    dstHDC = GetDC(dstWGLOps->window);
 
     // get the hdc for the source surface
-    if (srcOps->drawableType == OGLSD_PBUFFER) {
-        srcHDC = srcWGLOps->pbufferDC;
-    } else {
-        // the source will always be equal to the destination in this case
-        srcHDC = dstHDC;
-    }
+    // the source will always be equal to the destination in this case
+    srcHDC = dstHDC;
 
     // REMIND: in theory we should be able to use wglMakeContextCurrentARB()
     // even when the src/dst surfaces are the same, but this causes problems
@@ -306,9 +283,7 @@
     if (!success) {
         J2dRlsTraceLn(J2D_TRACE_ERROR,
                       "OGLSD_MakeOGLContextCurrent: could not make current");
-        if (dstOps->drawableType != OGLSD_PBUFFER) {
-            ReleaseDC(dstWGLOps->window, dstHDC);
-        }
+        ReleaseDC(dstWGLOps->window, dstHDC);
         return NULL;
     }
 
@@ -319,9 +294,7 @@
         j2d_glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0);
     }
 
-    if (dstOps->drawableType != OGLSD_PBUFFER) {
-        ReleaseDC(dstWGLOps->window, dstHDC);
-    }
+    ReleaseDC(dstWGLOps->window, dstHDC);
 
     return oglc;
 }
@@ -400,141 +373,6 @@
     return JNI_TRUE;
 }
 
-JNIEXPORT jboolean JNICALL
-Java_sun_java2d_opengl_WGLSurfaceData_initPbuffer
-    (JNIEnv *env, jobject wglsd,
-     jlong pData, jlong pConfigInfo,
-     jboolean isOpaque,
-     jint width, jint height)
-{
-    int attrKeys[] = {
-        WGL_MAX_PBUFFER_WIDTH_ARB,
-        WGL_MAX_PBUFFER_HEIGHT_ARB,
-    };
-    int attrVals[2];
-    int pbAttrList[] = { 0 };
-    OGLSDOps *oglsdo = (OGLSDOps *)jlong_to_ptr(pData);
-    WGLGraphicsConfigInfo *wglInfo =
-        (WGLGraphicsConfigInfo *)jlong_to_ptr(pConfigInfo);
-    WGLSDOps *wglsdo;
-    HWND hwnd;
-    HDC hdc, pbufferDC;
-    HPBUFFERARB pbuffer;
-    int maxWidth, maxHeight;
-    int actualWidth, actualHeight;
-
-    J2dTraceLn3(J2D_TRACE_INFO,
-                "WGLSurfaceData_initPbuffer: w=%d h=%d opq=%d",
-                width, height, isOpaque);
-
-    if (oglsdo == NULL) {
-        J2dRlsTraceLn(J2D_TRACE_ERROR,
-            "WGLSurfaceData_initPbuffer: ops are null");
-        return JNI_FALSE;
-    }
-
-    wglsdo = (WGLSDOps *)oglsdo->privOps;
-    if (wglsdo == NULL) {
-        J2dRlsTraceLn(J2D_TRACE_ERROR,
-            "WGLSurfaceData_initPbuffer: wgl ops are null");
-        return JNI_FALSE;
-    }
-
-    if (wglInfo == NULL) {
-        J2dRlsTraceLn(J2D_TRACE_ERROR,
-            "WGLSurfaceData_initPbuffer: wgl config info is null");
-        return JNI_FALSE;
-    }
-
-    // create a scratch window
-    hwnd = WGLGC_CreateScratchWindow(wglInfo->screen);
-    if (hwnd == 0) {
-        J2dRlsTraceLn(J2D_TRACE_ERROR,
-            "WGLSurfaceData_initPbuffer: could not create scratch window");
-        return JNI_FALSE;
-    }
-
-    // get the HDC for the scratch window
-    hdc = GetDC(hwnd);
-    if (hdc == 0) {
-        J2dRlsTraceLn(J2D_TRACE_ERROR,
-            "WGLSurfaceData_initPbuffer: could not get dc for scratch window");
-        DestroyWindow(hwnd);
-        return JNI_FALSE;
-    }
-
-    // get the maximum allowable pbuffer dimensions
-    j2d_wglGetPixelFormatAttribivARB(hdc, wglInfo->pixfmt, 0, 2,
-                                     attrKeys, attrVals);
-    maxWidth  = attrVals[0];
-    maxHeight = attrVals[1];
-
-    J2dTraceLn4(J2D_TRACE_VERBOSE,
-                "  desired pbuffer dimensions: w=%d h=%d maxw=%d maxh=%d",
-                width, height, maxWidth, maxHeight);
-
-    // if either dimension is 0 or larger than the maximum, we cannot
-    // allocate a pbuffer with the requested dimensions
-    if (width  == 0 || width  > maxWidth ||
-        height == 0 || height > maxHeight)
-    {
-        J2dRlsTraceLn(J2D_TRACE_ERROR,
-            "WGLSurfaceData_initPbuffer: invalid dimensions");
-        ReleaseDC(hwnd, hdc);
-        DestroyWindow(hwnd);
-        return JNI_FALSE;
-    }
-
-    pbuffer = j2d_wglCreatePbufferARB(hdc, wglInfo->pixfmt,
-                                      width, height, pbAttrList);
-
-    ReleaseDC(hwnd, hdc);
-    DestroyWindow(hwnd);
-
-    if (pbuffer == 0) {
-        J2dRlsTraceLn(J2D_TRACE_ERROR,
-            "WGLSurfaceData_initPbuffer: could not create wgl pbuffer");
-        return JNI_FALSE;
-    }
-
-    // note that we get the DC for the pbuffer at creation time, and then
-    // release the DC when the pbuffer is disposed; the WGL_ARB_pbuffer
-    // spec is vague about such things, but from past experience we know
-    // this approach to be more robust than, for example, doing a
-    // Get/ReleasePbufferDC() everytime we make a context current
-    pbufferDC = j2d_wglGetPbufferDCARB(pbuffer);
-    if (pbufferDC == 0) {
-        J2dRlsTraceLn(J2D_TRACE_ERROR,
-            "WGLSurfaceData_initPbuffer: could not get dc for pbuffer");
-        j2d_wglDestroyPbufferARB(pbuffer);
-        return JNI_FALSE;
-    }
-
-    // make sure the actual dimensions match those that we requested
-    j2d_wglQueryPbufferARB(pbuffer, WGL_PBUFFER_WIDTH_ARB, &actualWidth);
-    j2d_wglQueryPbufferARB(pbuffer, WGL_PBUFFER_HEIGHT_ARB, &actualHeight);
-
-    if (width != actualWidth || height != actualHeight) {
-        J2dRlsTraceLn2(J2D_TRACE_ERROR,
-            "WGLSurfaceData_initPbuffer: actual (w=%d h=%d) != requested",
-                       actualWidth, actualHeight);
-        j2d_wglReleasePbufferDCARB(pbuffer, pbufferDC);
-        j2d_wglDestroyPbufferARB(pbuffer);
-        return JNI_FALSE;
-    }
-
-    oglsdo->drawableType = OGLSD_PBUFFER;
-    oglsdo->isOpaque = isOpaque;
-    oglsdo->width = width;
-    oglsdo->height = height;
-    wglsdo->pbuffer = pbuffer;
-    wglsdo->pbufferDC = pbufferDC;
-
-    OGLSD_SetNativeDimensions(env, oglsdo, width, height);
-
-    return JNI_TRUE;
-}
-
 void
 OGLSD_SwapBuffers(JNIEnv *env, jlong pPeerData)
 {
--- a/jdk/src/java.management/share/classes/javax/management/MBeanServerInvocationHandler.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.management/share/classes/javax/management/MBeanServerInvocationHandler.java	Wed Jul 05 20:42:36 2017 +0200
@@ -141,6 +141,12 @@
         if (connection == null) {
             throw new IllegalArgumentException("Null connection");
         }
+        if (Proxy.isProxyClass(connection.getClass())) {
+            if (MBeanServerInvocationHandler.class.isAssignableFrom(
+                    Proxy.getInvocationHandler(connection).getClass())) {
+                throw new IllegalArgumentException("Wrapping MBeanServerInvocationHandler");
+            }
+        }
         if (objectName == null) {
             throw new IllegalArgumentException("Null object name");
         }
@@ -418,6 +424,10 @@
                              new Class<?>[] {Object.class})
             && isLocal(proxy, method))
             return true;
+        if (methodName.equals("finalize")
+            && method.getParameterTypes().length == 0) {
+            return true;
+        }
         return false;
     }
 
@@ -453,6 +463,9 @@
                 connection + "[" + objectName + "])";
         } else if (methodName.equals("hashCode")) {
             return objectName.hashCode()+connection.hashCode();
+        } else if (methodName.equals("finalize")) {
+            // ignore the finalizer invocation via proxy
+            return null;
         }
 
         throw new RuntimeException("Unexpected method name: " + methodName);
--- a/jdk/src/java.management/share/classes/javax/management/remote/rmi/RMIConnectionImpl.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.management/share/classes/javax/management/remote/rmi/RMIConnectionImpl.java	Wed Jul 05 20:42:36 2017 +0200
@@ -32,7 +32,6 @@
 import java.security.AccessControlContext;
 import java.security.AccessController;
 import java.security.Permission;
-import java.security.PermissionCollection;
 import java.security.Permissions;
 import java.security.PrivilegedAction;
 import java.security.PrivilegedActionException;
@@ -46,7 +45,6 @@
 import javax.management.*;
 import javax.management.remote.JMXServerErrorException;
 import javax.management.remote.NotificationResult;
-import javax.management.remote.TargetedNotification;
 import javax.security.auth.Subject;
 import sun.reflect.misc.ReflectUtil;
 
@@ -59,6 +57,7 @@
 import com.sun.jmx.remote.util.ClassLogger;
 import com.sun.jmx.remote.util.EnvHelp;
 import com.sun.jmx.remote.util.OrderClassLoaders;
+import javax.management.loading.ClassLoaderRepository;
 
 /**
  * <p>Implementation of the {@link RMIConnection} interface.  User
@@ -131,20 +130,24 @@
 
         final ClassLoader dcl = defaultClassLoader;
 
-        this.classLoaderWithRepository =
-            AccessController.doPrivileged(
-                new PrivilegedAction<ClassLoaderWithRepository>() {
-                    public ClassLoaderWithRepository run() {
-                        return new ClassLoaderWithRepository(
-                                      mbeanServer.getClassLoaderRepository(),
-                                      dcl);
-                    }
-                },
-
-                withPermissions( new MBeanPermission("*", "getClassLoaderRepository"),
-                                 new RuntimePermission("createClassLoader"))
-            );
-
+        ClassLoaderRepository repository = AccessController.doPrivileged(
+            new PrivilegedAction<ClassLoaderRepository>() {
+                public ClassLoaderRepository run() {
+                    return mbeanServer.getClassLoaderRepository();
+                }
+            },
+            withPermissions(new MBeanPermission("*", "getClassLoaderRepository"))
+        );
+        this.classLoaderWithRepository = AccessController.doPrivileged(
+            new PrivilegedAction<ClassLoaderWithRepository>() {
+                public ClassLoaderWithRepository run() {
+                    return new ClassLoaderWithRepository(
+                        repository,
+                        dcl);
+                }
+            },
+            withPermissions(new RuntimePermission("createClassLoader"))
+        );
 
         this.defaultContextClassLoader =
             AccessController.doPrivileged(
--- a/jdk/src/java.rmi/share/classes/java/rmi/server/RemoteObjectInvocationHandler.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/java.rmi/share/classes/java/rmi/server/RemoteObjectInvocationHandler.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2005, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 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
@@ -102,6 +102,9 @@
      * representation of the proxy.
      * </ul>
      *
+     * <p>If <code>method</code> overrides {@link Object#finalize Object.finalize},
+     * it is ignored.
+     *
      * <p>Otherwise, a remote call is made as follows:
      *
      * <ul>
@@ -144,6 +147,8 @@
     {
         if (method.getDeclaringClass() == Object.class) {
             return invokeObjectMethod(proxy, method, args);
+        } else if ("finalize".equals(method.getName()) && method.getParameterCount() == 0) {
+            return null; // ignore
         } else {
             return invokeRemoteMethod(proxy, method, args);
         }
--- a/jdk/src/jdk.crypto.ec/share/native/libsunec/impl/ec.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/jdk.crypto.ec/share/native/libsunec/impl/ec.c	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2007, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2007, 2015, Oracle and/or its affiliates. All rights reserved.
  * Use is subject to license terms.
  *
  * This library is free software; you can redistribute it and/or
@@ -34,6 +34,7 @@
  *   Dr Vipul Gupta <vipul.gupta@sun.com> and
  *   Douglas Stebila <douglas@stebila.ca>, Sun Microsystems Laboratories
  *
+ * Last Modified Date from the Original Code: April 2015
  *********************************************************************** */
 
 #include "mplogic.h"
@@ -585,6 +586,10 @@
         return SECFailure;
     }
 
+    if (EC_ValidatePublicKey(ecParams, publicValue, kmflag) != SECSuccess) {
+        return SECFailure;
+    }
+
     memset(derivedSecret, 0, sizeof *derivedSecret);
     len = (ecParams->fieldID.size + 7) >> 3;
     pointQ.len = 2*len + 1;
--- a/jdk/src/jdk.crypto.ec/share/native/libsunec/impl/ecc_impl.h	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/jdk.crypto.ec/share/native/libsunec/impl/ecc_impl.h	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2007, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2007, 2013, Oracle and/or its affiliates. All rights reserved.
  * Use is subject to license terms.
  *
  * This library is free software; you can redistribute it and/or
@@ -34,6 +34,7 @@
  *   Dr Vipul Gupta <vipul.gupta@sun.com> and
  *   Douglas Stebila <douglas@stebila.ca>, Sun Microsystems Laboratories
  *
+ * Last Modified Date from the Original Code: November 2013
  *********************************************************************** */
 
 #ifndef _ECC_IMPL_H
--- a/jdk/src/jdk.crypto.ec/share/native/libsunec/impl/ecdecode.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/jdk.crypto.ec/share/native/libsunec/impl/ecdecode.c	Wed Jul 05 20:42:36 2017 +0200
@@ -34,6 +34,7 @@
  *   Dr Vipul Gupta <vipul.gupta@sun.com> and
  *   Douglas Stebila <douglas@stebila.ca>, Sun Microsystems Laboratories
  *
+ * Last Modified Date from the Original Code: March 2012
  *********************************************************************** */
 
 #include <sys/types.h>
--- a/jdk/src/jdk.crypto.ec/share/native/libsunec/impl/mpi.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/jdk.crypto.ec/share/native/libsunec/impl/mpi.c	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2007, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2007, 2014, Oracle and/or its affiliates. All rights reserved.
  * Use is subject to license terms.
  *
  * This library is free software; you can redistribute it and/or
@@ -34,6 +34,7 @@
  *   Netscape Communications Corporation
  *   Douglas Stebila <douglas@stebila.ca> of Sun Laboratories.
  *
+ * Last Modified Date from the Original Code: June 2014
  *********************************************************************** */
 
 /*  Arbitrary precision integer arithmetic library */
--- a/jdk/src/jdk.crypto.ec/share/native/libsunec/impl/oid.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/jdk.crypto.ec/share/native/libsunec/impl/oid.c	Wed Jul 05 20:42:36 2017 +0200
@@ -33,6 +33,7 @@
  * Contributor(s):
  *   Dr Vipul Gupta <vipul.gupta@sun.com>, Sun Microsystems Laboratories
  *
+ * Last Modified Date from the Original Code: March 2012
  *********************************************************************** */
 
 #include <sys/types.h>
--- a/jdk/src/jdk.crypto.ec/share/native/libsunec/impl/secitem.c	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/jdk.crypto.ec/share/native/libsunec/impl/secitem.c	Wed Jul 05 20:42:36 2017 +0200
@@ -32,6 +32,7 @@
  *
  * Contributor(s):
  *
+ * Last Modified Date from the Original Code: March 2012
  *********************************************************************** */
 
 /*
--- a/jdk/src/jdk.crypto.pkcs11/share/classes/sun/security/pkcs11/P11Key.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/jdk.crypto.pkcs11/share/classes/sun/security/pkcs11/P11Key.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 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
@@ -165,7 +165,7 @@
         } else {
             otherEnc = other.getEncoded();
         }
-        return Arrays.equals(thisEnc, otherEnc);
+        return MessageDigest.isEqual(thisEnc, otherEnc);
     }
 
     public int hashCode() {
--- a/jdk/src/jdk.crypto.pkcs11/share/classes/sun/security/pkcs11/wrapper/Functions.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/jdk.crypto.pkcs11/share/classes/sun/security/pkcs11/wrapper/Functions.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 2015, Oracle and/or its affiliates. All rights reserved.
  */
 
 /* Copyright  (c) 2002 Graz University of Technology. All rights reserved.
@@ -447,22 +447,6 @@
     /**
      * Check the given arrays for equalitiy. This method considers both arrays as
      * equal, if both are <code>null</code> or both have the same length and
-     * contain exactly the same byte values.
-     *
-     * @param array1 The first array.
-     * @param array2 The second array.
-     * @return True, if both arrays are <code>null</code> or both have the same
-     *         length and contain exactly the same byte values. False, otherwise.
-     * @preconditions
-     * @postconditions
-     */
-    public static boolean equals(byte[] array1, byte[] array2) {
-        return Arrays.equals(array1, array2);
-    }
-
-    /**
-     * Check the given arrays for equalitiy. This method considers both arrays as
-     * equal, if both are <code>null</code> or both have the same length and
      * contain exactly the same char values.
      *
      * @param array1 The first array.
@@ -472,7 +456,7 @@
      * @preconditions
      * @postconditions
      */
-    public static boolean equals(char[] array1, char[] array2) {
+    private static boolean equals(char[] array1, char[] array2) {
         return Arrays.equals(array1, array2);
     }
 
--- a/jdk/src/jdk.crypto.ucrypto/solaris/classes/com/oracle/security/ucrypto/NativeGCMCipher.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/jdk.crypto.ucrypto/solaris/classes/com/oracle/security/ucrypto/NativeGCMCipher.java	Wed Jul 05 20:42:36 2017 +0200
@@ -206,7 +206,7 @@
         }
         if (doEncrypt) {
             requireReinit = Arrays.equals(ivBytes, lastEncIv) &&
-                Arrays.equals(keyBytes, lastEncKey);
+                MessageDigest.isEqual(keyBytes, lastEncKey);
             if (requireReinit) {
                 throw new InvalidAlgorithmParameterException
                     ("Cannot reuse iv for GCM encryption");
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/jdk.dev/share/classes/jdk/tools/jimage/ExtractedImage.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,210 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.tools.jimage;
+
+import java.io.File;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.PrintWriter;
+import java.nio.file.Files;
+import java.nio.file.Path;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.HashSet;
+import java.util.LinkedHashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Map.Entry;
+import java.util.Set;
+import java.util.function.Consumer;
+import java.util.stream.Stream;
+import jdk.internal.jimage.Archive;
+import jdk.internal.jimage.ImageFileCreator;
+import jdk.internal.jimage.ImageModuleData;
+import jdk.internal.jimage.ImageModuleDataWriter;
+
+/**
+ *
+ * Support for extracted image.
+ */
+public final class ExtractedImage {
+
+    /**
+     * An Archive backed by a directory.
+     */
+    public class DirArchive implements Archive {
+
+        /**
+         * A File located in a Directory.
+         */
+        private class FileEntry extends Archive.Entry {
+
+            private final long size;
+            private final Path path;
+
+            FileEntry(Path path, String name) {
+                super(DirArchive.this, getPathName(path), name,
+                        Archive.Entry.EntryType.CLASS_OR_RESOURCE);
+                this.path = path;
+                try {
+                    size = Files.size(path);
+                } catch (IOException ex) {
+                    throw new RuntimeException(ex);
+                }
+            }
+
+            /**
+             * Returns the number of bytes of this file.
+             */
+            @Override
+            public long size() {
+                return size;
+            }
+
+            @Override
+            public InputStream stream() throws IOException {
+                InputStream stream = Files.newInputStream(path);
+                open.add(stream);
+                return stream;
+            }
+        }
+
+        private final Path dirPath;
+        private final String moduleName;
+        private final List<InputStream> open = new ArrayList<>();
+        private final int chop;
+
+        protected DirArchive(Path dirPath) throws IOException {
+            if (!Files.isDirectory(dirPath)) {
+                throw new IOException("Not a directory");
+            }
+            chop = dirPath.toString().length() + 1;
+            this.moduleName = dirPath.getFileName().toString();
+            System.out.println("Module name " + this.moduleName);
+            this.dirPath = dirPath;
+        }
+
+        @Override
+        public String moduleName() {
+            return moduleName;
+        }
+
+        @Override
+        public Stream<Entry> entries() {
+            try {
+                return Files.walk(dirPath).map(this::toEntry).filter(n -> n != null);
+            } catch(IOException ex) {
+                throw new RuntimeException(ex);
+            }
+        }
+
+        private Archive.Entry toEntry(Path p) {
+            if (Files.isDirectory(p)) {
+                return null;
+            }
+            String name = getPathName(p).substring(chop);
+            if (name.startsWith("_")) {
+                return null;
+            }
+            if (verbose) {
+                String verboseName = moduleName + "/" + name;
+                log.println(verboseName);
+            }
+
+            return new FileEntry(p, name);
+        }
+
+        @Override
+        public void close() throws IOException {
+            IOException e = null;
+            for (InputStream stream : open) {
+                try {
+                    stream.close();
+                } catch (IOException ex) {
+                    if (e == null) {
+                        e = ex;
+                    } else {
+                        e.addSuppressed(ex);
+                    }
+                }
+            }
+            if (e != null) {
+                throw e;
+            }
+        }
+
+        @Override
+        public void open() throws IOException {
+            // NOOP
+        }
+    }
+    private Map<String, Set<String>> modulePackages = new LinkedHashMap<>();
+    private Set<Archive> archives = new HashSet<>();
+    private final PrintWriter log;
+    private final boolean verbose;
+
+    ExtractedImage(Path dirPath, PrintWriter log,
+            boolean verbose) throws IOException {
+        if (!Files.isDirectory(dirPath)) {
+            throw new IOException("Not a directory");
+        }
+        Files.walk(dirPath, 1).forEach((p) -> {
+            try {
+                if (!dirPath.equals(p)) {
+                    String name = getPathName(p);
+                    if (name.endsWith(ImageModuleData.META_DATA_EXTENSION)) {
+                        List<String> lines = Files.readAllLines(p);
+                        for (Entry<String, List<String>> entry
+                                : ImageModuleDataWriter.toModulePackages(lines).entrySet()) {
+                            Set<String> pkgs = new HashSet<>();
+                            pkgs.addAll(entry.getValue());
+                            modulePackages.put(entry.getKey(), pkgs);
+                        }
+                        modulePackages = Collections.unmodifiableMap(modulePackages);
+                    } else {
+                        if (Files.isDirectory(p)) {
+                            Archive a = new DirArchive(p);
+                            archives.add(a);
+                        }
+                    }
+                }
+            } catch (IOException ex) {
+                throw new RuntimeException(ex);
+            }
+        });
+        archives = Collections.unmodifiableSet(archives);
+        this.log = log;
+        this.verbose = verbose;
+    }
+
+    void recreateJImage(Path path) throws IOException {
+
+        ImageFileCreator.recreateJimage(path, archives, modulePackages);
+    }
+
+    private static String getPathName(Path path) {
+        return path.toString().replace(File.separatorChar, '/');
+    }
+}
--- a/jdk/src/jdk.dev/share/classes/jdk/tools/jimage/JImageTask.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/jdk.dev/share/classes/jdk/tools/jimage/JImageTask.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -25,141 +25,98 @@
 
 package jdk.tools.jimage;
 
-import java.io.BufferedOutputStream;
-import java.io.DataOutputStream;
 import java.io.File;
 import java.io.IOException;
-import java.io.OutputStream;
 import java.io.PrintWriter;
+import java.nio.ByteBuffer;
+import java.nio.ByteOrder;
+import java.nio.channels.FileChannel;
 import java.nio.file.Files;
 import java.nio.file.Path;
-import java.text.MessageFormat;
-import java.util.ArrayList;
+import static java.nio.file.StandardOpenOption.READ;
+import static java.nio.file.StandardOpenOption.WRITE;
 import java.util.LinkedList;
 import java.util.List;
-import java.util.Locale;
-import java.util.MissingResourceException;
-import java.util.ResourceBundle;
-import java.util.stream.Collectors;
-import java.util.stream.Stream;
 import jdk.internal.jimage.BasicImageReader;
-import jdk.internal.jimage.BasicImageWriter;
 import jdk.internal.jimage.ImageHeader;
+import static jdk.internal.jimage.ImageHeader.MAGIC;
+import static jdk.internal.jimage.ImageHeader.MAJOR_VERSION;
+import static jdk.internal.jimage.ImageHeader.MINOR_VERSION;
 import jdk.internal.jimage.ImageLocation;
-import jdk.internal.jimage.PackageModuleMap;
+import jdk.internal.jimage.ImageModuleData;
+import jdk.internal.jimage.ImageResourcesTree;
+import jdk.tools.jimage.TaskHelper.BadArgs;
+import jdk.tools.jimage.TaskHelper.HiddenOption;
+import jdk.tools.jimage.TaskHelper.Option;
+import jdk.tools.jimage.TaskHelper.OptionsHelper;
 
 class JImageTask {
-    static class BadArgs extends Exception {
-        static final long serialVersionUID = 8765093759964640723L;  // ## re-generate
-        final String key;
-        final Object[] args;
-        boolean showUsage;
 
-        BadArgs(String key, Object... args) {
-            super(JImageTask.getMessage(key, args));
-            this.key = key;
-            this.args = args;
-        }
-
-        BadArgs showUsage(boolean b) {
-            showUsage = b;
-            return this;
-        }
-    }
-
-    static abstract class Option {
-        final boolean hasArg;
-        final String[] aliases;
-
-        Option(boolean hasArg, String... aliases) {
-            this.hasArg = hasArg;
-            this.aliases = aliases;
-        }
-
-        boolean isHidden() {
-            return false;
-        }
-
-        boolean matches(String opt) {
-            for (String a : aliases) {
-                if (a.equals(opt)) {
-                    return true;
-                } else if (opt.startsWith("--") && hasArg && opt.startsWith(a + "=")) {
-                    return true;
-                }
-            }
-            return false;
-        }
-
-        boolean ignoreRest() {
-            return false;
-        }
-
-        abstract void process(JImageTask task, String opt, String arg) throws BadArgs;
-    }
-
-    static abstract class HiddenOption extends Option {
-        HiddenOption(boolean hasArg, String... aliases) {
-            super(hasArg, aliases);
-        }
-
-        @Override
-        boolean isHidden() {
-            return true;
-        }
-    }
-
-    static Option[] recognizedOptions = {
-        new Option(true, "--dir") {
+    static final Option<?>[] recognizedOptions = {
+        new Option<JImageTask>(true, "--dir") {
             @Override
-            void process(JImageTask task, String opt, String arg) throws BadArgs {
+            protected void process(JImageTask task, String opt, String arg) throws BadArgs {
                  task.options.directory = arg;
             }
         },
-        new HiddenOption(false, "--fullversion") {
+        new HiddenOption<JImageTask>(false, "--fullversion") {
             @Override
-            void process(JImageTask task, String opt, String arg) {
+            protected void process(JImageTask task, String opt, String arg) {
                 task.options.fullVersion = true;
             }
         },
-        new Option(false, "--help") {
+        new Option<JImageTask>(false, "--help") {
             @Override
-            void process(JImageTask task, String opt, String arg) {
+            protected void process(JImageTask task, String opt, String arg) {
                 task.options.help = true;
             }
         },
-        new Option(false, "--verbose") {
+
+        new Option<JImageTask>(true, "--flags") {
             @Override
-            void process(JImageTask task, String opt, String arg) throws BadArgs {
+            protected void process(JImageTask task, String opt, String arg) {
+                task.options.flags = arg;
+            }
+        },
+
+        new Option<JImageTask>(false, "--verbose") {
+            @Override
+            protected void process(JImageTask task, String opt, String arg) throws BadArgs {
                  task.options.verbose = true;
             }
         },
-        new Option(false, "--version") {
+        new Option<JImageTask>(false, "--version") {
             @Override
-            void process(JImageTask task, String opt, String arg) {
+            protected void process(JImageTask task, String opt, String arg) {
                 task.options.version = true;
             }
         },
     };
+    private static final TaskHelper taskHelper
+            = new TaskHelper("jdk.tools.jimage.resources.jimage");
+    private static final OptionsHelper<JImageTask> optionsHelper
+            = taskHelper.newOptionsHelper(JImageTask.class, recognizedOptions);
 
-    static class Options {
+    static class OptionsValues {
         Task task = Task.LIST;
         String directory = ".";
         boolean fullVersion;
         boolean help;
+        String flags;
         boolean verbose;
         boolean version;
         List<File> jimages = new LinkedList<>();
     }
 
     private static final String PROGNAME = "jimage";
-    private final Options options = new Options();
+    private final OptionsValues options = new OptionsValues();
 
     enum Task {
-        RECREATE,
         EXTRACT,
         INFO,
         LIST,
+        RECREATE,
+        SET,
         VERIFY
     };
 
@@ -210,23 +167,29 @@
 
     int run(String[] args) {
         if (log == null) {
-            log = new PrintWriter(System.out);
+            setLog(new PrintWriter(System.out));
         }
 
         try {
-            handleOptions(args);
+            List<String> unhandled = optionsHelper.handleOptions(this, args);
+            if(!unhandled.isEmpty()) {
+                options.task = Enum.valueOf(Task.class, unhandled.get(0).toUpperCase());
+                for(int i = 1; i < unhandled.size(); i++) {
+                    options.jimages.add(new File(unhandled.get(i)));
+                }
+            }
             if (options.help) {
-                showHelp();
+                optionsHelper.showHelp(PROGNAME, "recreate only options:");
             }
             if (options.version || options.fullVersion) {
-                showVersion(options.fullVersion);
+                taskHelper.showVersion(options.fullVersion);
             }
             boolean ok = run();
             return ok ? EXIT_OK : EXIT_ERROR;
         } catch (BadArgs e) {
-            reportError(e.key, e.args);
+            taskHelper.reportError(e.key, e.args);
             if (e.showUsage) {
-                log.println(getMessage("main.usage.summary", PROGNAME));
+                log.println(taskHelper.getMessage("main.usage.summary", PROGNAME));
             }
             return EXIT_CMDERR;
         } catch (Exception x) {
@@ -237,98 +200,26 @@
         }
     }
 
-    static final String MODULES_ENTRY = PackageModuleMap.MODULES_ENTRY;
-    static final String PACKAGES_ENTRY = "/" + PackageModuleMap.PACKAGES_ENTRY;
-
     private void recreate() throws IOException, BadArgs {
         File directory = new File(options.directory);
-        Path dirPath = directory.toPath();
-        int chop = dirPath.toString().length() + 1;
-
         if (!directory.isDirectory()) {
-            throw new BadArgs("err.not.a.dir", directory.getAbsolutePath());
+            throw taskHelper.newBadArgs("err.not.a.dir", directory.getAbsolutePath());
         }
-
+        Path dirPath = directory.toPath();
         if (options.jimages.isEmpty()) {
-            throw new BadArgs("err.jimage.not.specified");
+            throw taskHelper.newBadArgs("err.jimage.not.specified");
         } else if (options.jimages.size() != 1) {
-            throw new BadArgs("err.only.one.jimage");
+            throw taskHelper.newBadArgs("err.only.one.jimage");
         }
 
-        File jimage = options.jimages.get(0);
-        final List<File> files = new ArrayList<>();
-        final BasicImageWriter writer = new BasicImageWriter();
-        final Long longZero = 0L;
-
-        // Note: code sensitive to Netbeans parser crashing.
-        long total = Files.walk(dirPath).reduce(longZero, (Long offset, Path path) -> {
-                    long size = 0;
-                    String pathString = path.toString();
-
-                    if (pathString.length() < chop || pathString.startsWith(".")) {
-                        return 0L;
-                    }
-
-                    File file = path.toFile();
-
-                    if (file.isFile()) {
-                        String name = pathString.substring(chop).replace(File.separatorChar, '/');
-
-                        if (options.verbose) {
-                            log.println(name);
-                        }
-
-                        if (name.endsWith(MODULES_ENTRY) || name.endsWith(PACKAGES_ENTRY)) {
-                            try {
-                                try (Stream<String> lines = Files.lines(path)) {
-                                    size = lines.peek(s -> writer.addString(s)).count() * 4;
-                                }
-                            } catch (IOException ex) {
-                                // Caught again when writing file.
-                                size = 0;
-                            }
-                        } else {
-                            size = file.length();
-                        }
+        Path jimage = options.jimages.get(0).toPath();
 
-                        writer.addLocation(name, offset, 0L, size);
-                        files.add(file);
-                    }
-
-                    return offset + size;
-                },
-                (Long offsetL, Long offsetR) -> { return longZero; } );
-
-        if (jimage.createNewFile()) {
-            try (OutputStream os = Files.newOutputStream(jimage.toPath());
-                    BufferedOutputStream bos = new BufferedOutputStream(os);
-                    DataOutputStream out = new DataOutputStream(bos)) {
-
-                byte[] index = writer.getBytes();
-                out.write(index, 0, index.length);
-
-                for (File file : files) {
-                    try {
-                        Path path = file.toPath();
-                        String name = path.toString().replace(File.separatorChar, '/');
-
-                        if (name.endsWith(MODULES_ENTRY) || name.endsWith(PACKAGES_ENTRY)) {
-                            for (String line: Files.readAllLines(path)) {
-                                int off = writer.addString(line);
-                                out.writeInt(off);
-                            }
-                        } else {
-                            Files.copy(path, out);
-                        }
-                    } catch (IOException ex) {
-                        throw new BadArgs("err.cannot.read.file", file.getName());
-                    }
-                }
-            }
+        if (jimage.toFile().createNewFile()) {
+            ExtractedImage img = new ExtractedImage(dirPath, log, options.verbose);
+            img.recreateJImage(jimage);
         } else {
-            throw new BadArgs("err.jimage.already.exists", jimage.getName());
+            throw taskHelper.newBadArgs("err.jimage.already.exists", jimage.getFileName());
         }
-
     }
 
     private void title(File file, BasicImageReader reader) {
@@ -351,10 +242,12 @@
     }
 
     private interface ResourceAction {
-        public void apply(BasicImageReader reader, String name, ImageLocation location) throws IOException, BadArgs;
+        public void apply(BasicImageReader reader, String name,
+                ImageLocation location) throws IOException, BadArgs;
     }
 
-    private void extract(BasicImageReader reader, String name, ImageLocation location) throws IOException, BadArgs {
+    private void extract(BasicImageReader reader, String name,
+            ImageLocation location) throws IOException, BadArgs {
         File directory = new File(options.directory);
         byte[] bytes = reader.getResource(location);
         File resource =  new File(directory, name);
@@ -362,21 +255,23 @@
 
         if (parent.exists()) {
             if (!parent.isDirectory()) {
-                throw new BadArgs("err.cannot.create.dir", parent.getAbsolutePath());
+                throw taskHelper.newBadArgs("err.cannot.create.dir", parent.getAbsolutePath());
             }
         } else if (!parent.mkdirs()) {
-            throw new BadArgs("err.cannot.create.dir", parent.getAbsolutePath());
+            throw taskHelper.newBadArgs("err.cannot.create.dir", parent.getAbsolutePath());
         }
 
-        if (name.endsWith(MODULES_ENTRY) || name.endsWith(PACKAGES_ENTRY)) {
-            List<String> names = reader.getNames(bytes);
-            Files.write(resource.toPath(), names);
+        if (name.endsWith(ImageModuleData.META_DATA_EXTENSION)) {
+            ImageModuleData imageModuleData = new ImageModuleData(reader, bytes);
+            List<String> lines = imageModuleData.fromModulePackages();
+            Files.write(resource.toPath(), lines);
         } else {
-            Files.write(resource.toPath(), bytes);
+            if (!ImageResourcesTree.isTreeInfoResource(name)) {
+                Files.write(resource.toPath(), bytes);
+            }
         }
     }
 
-    private static final int NAME_WIDTH = 40;
     private static final int NUMBER_WIDTH = 12;
     private static final int OFFSET_WIDTH = NUMBER_WIDTH;
     private static final int SIZE_WIDTH = NUMBER_WIDTH;
@@ -397,12 +292,14 @@
         }
     }
 
-    private void info(File file, BasicImageReader reader) {
+    private void info(File file, BasicImageReader reader) throws IOException {
         ImageHeader header = reader.getHeader();
 
         log.println(" Major Version:  " + header.getMajorVersion());
         log.println(" Minor Version:  " + header.getMinorVersion());
-        log.println(" Location Count: " + header.getLocationCount());
+        log.println(" Flags:          " + Integer.toHexString(header.getMinorVersion()));
+        log.println(" Resource Count: " + header.getResourceCount());
+        log.println(" Table Length:   " + header.getTableLength());
         log.println(" Offsets Size:   " + header.getOffsetsSize());
         log.println(" Redirects Size: " + header.getRedirectSize());
         log.println(" Locations Size: " + header.getLocationsSize());
@@ -414,16 +311,39 @@
         print(reader, name);
     }
 
-    void verify(BasicImageReader reader, String name, ImageLocation location) {
-        if (name.endsWith(".class")) {
-            byte[] bytes;
+    void set(File file, BasicImageReader reader) throws BadArgs {
+        try {
+            ImageHeader oldHeader = reader.getHeader();
+
+            int value = 0;
             try {
-                bytes = reader.getResource(location);
-            } catch (IOException ex) {
-                log.println(ex);
-                bytes = null;
+                value = Integer.valueOf(options.flags);
+            } catch (NumberFormatException ex) {
+                throw taskHelper.newBadArgs("err.flags.not.int", options.flags);
             }
 
+            ImageHeader newHeader = new ImageHeader(MAGIC, MAJOR_VERSION, MINOR_VERSION,
+                    value,
+                    oldHeader.getResourceCount(), oldHeader.getTableLength(),
+                    oldHeader.getLocationsSize(), oldHeader.getStringsSize());
+
+            ByteBuffer buffer = ByteBuffer.allocate(ImageHeader.getHeaderSize());
+            buffer.order(ByteOrder.nativeOrder());
+            newHeader.writeTo(buffer);
+            buffer.rewind();
+
+            try (FileChannel channel = FileChannel.open(file.toPath(), READ, WRITE)) {
+                channel.write(buffer, 0);
+            }
+        } catch (IOException ex) {
+            throw taskHelper.newBadArgs("err.cannot.update.file", file.getName());
+        }
+    }
+
+     void verify(BasicImageReader reader, String name, ImageLocation location) {
+        if (name.endsWith(".class")) {
+            byte[] bytes = reader.getResource(location);
+
             if (bytes == null || bytes.length <= 4 ||
                 (bytes[0] & 0xFF) != 0xCA ||
                 (bytes[1] & 0xFF) != 0xFE ||
@@ -435,10 +355,11 @@
         }
     }
 
-    private void iterate(JImageAction jimageAction, ResourceAction resourceAction) throws IOException, BadArgs {
+    private void iterate(JImageAction jimageAction,
+            ResourceAction resourceAction) throws IOException, BadArgs {
         for (File file : options.jimages) {
             if (!file.exists() || !file.isFile()) {
-                throw new BadArgs("err.not.a.jimage", file.getName());
+                throw taskHelper.newBadArgs("err.not.a.jimage", file.getName());
             }
 
             String path = file.getCanonicalPath();
@@ -449,11 +370,13 @@
             }
 
             if (resourceAction != null) {
-                String[] entryNames = reader.getEntryNames(true);
+                String[] entryNames = reader.getEntryNames();
 
                 for (String name : entryNames) {
-                    ImageLocation location = reader.findLocation(name);
-                    resourceAction.apply(reader, name, location);
+                    if (!ImageResourcesTree.isTreeInfoResource(name)) {
+                        ImageLocation location = reader.findLocation(name);
+                        resourceAction.apply(reader, name, location);
+                    }
                 }
             }
        }
@@ -461,9 +384,6 @@
 
     private boolean run() throws IOException, BadArgs {
         switch (options.task) {
-            case RECREATE:
-                recreate();
-                break;
             case EXTRACT:
                 iterate(null, this::extract);
                 break;
@@ -473,11 +393,17 @@
             case LIST:
                 iterate(this::listTitle, this::list);
                 break;
+            case RECREATE:
+                recreate();
+                break;
+            case SET:
+                iterate(this::set, null);
+                break;
             case VERIFY:
                 iterate(this::title, this::verify);
                 break;
             default:
-                throw new BadArgs("err.invalid.task", options.task.name()).showUsage(true);
+                throw taskHelper.newBadArgs("err.invalid.task", options.task.name()).showUsage(true);
         }
         return true;
     }
@@ -485,112 +411,6 @@
     private PrintWriter log;
     void setLog(PrintWriter out) {
         log = out;
-    }
-    public void handleOptions(String[] args) throws BadArgs {
-        // process options
-        int first = 0;
-
-        if (args.length == 0) {
-            return;
-        }
-
-        String arg = args[first];
-
-        if (!arg.startsWith("-")) {
-            try {
-                options.task = Enum.valueOf(Task.class, arg.toUpperCase());
-                first++;
-            } catch (IllegalArgumentException e) {
-                throw new BadArgs("err.invalid.task", arg).showUsage(true);
-            }
-        }
-
-        for (int i = first; i < args.length; i++) {
-            arg = args[i];
-
-            if (arg.charAt(0) == '-') {
-                Option option = getOption(arg);
-                String param = null;
-
-                if (option.hasArg) {
-                    if (arg.startsWith("--") && arg.indexOf('=') > 0) {
-                        param = arg.substring(arg.indexOf('=') + 1, arg.length());
-                    } else if (i + 1 < args.length) {
-                        param = args[++i];
-                    }
-
-                    if (param == null || param.isEmpty() || param.charAt(0) == '-') {
-                        throw new BadArgs("err.missing.arg", arg).showUsage(true);
-                    }
-                }
-
-                option.process(this, arg, param);
-
-                if (option.ignoreRest()) {
-                    i = args.length;
-                }
-            } else {
-                File file = new File(arg);
-                options.jimages.add(file);
-            }
-        }
-    }
-
-    private Option getOption(String name) throws BadArgs {
-        for (Option o : recognizedOptions) {
-            if (o.matches(name)) {
-                return o;
-            }
-        }
-        throw new BadArgs("err.unknown.option", name).showUsage(true);
-    }
-
-    private void reportError(String key, Object... args) {
-        log.println(getMessage("error.prefix") + " " + getMessage(key, args));
-    }
-
-    private void warning(String key, Object... args) {
-        log.println(getMessage("warn.prefix") + " " + getMessage(key, args));
-    }
-
-    private void showHelp() {
-        log.println(getMessage("main.usage", PROGNAME));
-        for (Option o : recognizedOptions) {
-            String name = o.aliases[0].substring(1); // there must always be at least one name
-            name = name.charAt(0) == '-' ? name.substring(1) : name;
-            if (o.isHidden() || name.equals("h")) {
-                continue;
-            }
-            log.println(getMessage("main.opt." + name));
-        }
-    }
-
-    private void showVersion(boolean full) {
-        log.println(version(full ? "full" : "release"));
-    }
-
-    private String version(String key) {
-        return System.getProperty("java.version");
-    }
-
-    static String getMessage(String key, Object... args) {
-        try {
-            return MessageFormat.format(ResourceBundleHelper.bundle.getString(key), args);
-        } catch (MissingResourceException e) {
-            throw new InternalError("Missing message: " + key);
-        }
-    }
-
-    private static class ResourceBundleHelper {
-        static final ResourceBundle bundle;
-
-        static {
-            Locale locale = Locale.getDefault();
-            try {
-                bundle = ResourceBundle.getBundle("jdk.tools.jimage.resources.jimage", locale);
-            } catch (MissingResourceException e) {
-                throw new InternalError("Cannot find jimage resource bundle for locale " + locale);
-            }
-        }
+        taskHelper.setLog(log);
     }
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/jdk.dev/share/classes/jdk/tools/jimage/TaskHelper.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,231 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.tools.jimage;
+
+import java.io.PrintWriter;
+import java.text.MessageFormat;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Locale;
+import java.util.MissingResourceException;
+import java.util.ResourceBundle;
+
+/**
+ *
+ * JImage tools shared helper.
+ */
+public final class TaskHelper {
+
+    public class BadArgs extends Exception {
+
+        static final long serialVersionUID = 8765093759964640721L;
+
+        private BadArgs(String key, Object... args) {
+            super(bundleHelper.getMessage(key, args));
+            this.key = key;
+            this.args = args;
+        }
+
+        public BadArgs showUsage(boolean b) {
+            showUsage = b;
+            return this;
+        }
+        public final String key;
+        public final Object[] args;
+        public boolean showUsage;
+    }
+
+    public static abstract class Option<T> {
+
+        final boolean hasArg;
+        final String[] aliases;
+
+        public Option(boolean hasArg, String... aliases) {
+            this.hasArg = hasArg;
+            this.aliases = aliases;
+        }
+
+        public boolean isHidden() {
+            return false;
+        }
+
+        public boolean matches(String opt) {
+            for (String a : aliases) {
+                if (a.equals(opt)) {
+                    return true;
+                } else if (opt.startsWith("--") && hasArg && opt.startsWith(a + "=")) {
+                    return true;
+                }
+            }
+            return false;
+        }
+
+        public boolean ignoreRest() {
+            return false;
+        }
+
+        protected abstract void process(T task, String opt, String arg) throws BadArgs;
+    }
+
+    public static abstract class HiddenOption<T> extends Option<T> {
+
+        public HiddenOption(boolean hasArg, String... aliases) {
+            super(hasArg, aliases);
+        }
+
+        @Override
+        public boolean isHidden() {
+            return true;
+        }
+    }
+
+    private class ResourceBundleHelper {
+
+        private final ResourceBundle bundle;
+
+        ResourceBundleHelper(String path) {
+            Locale locale = Locale.getDefault();
+            try {
+                bundle = ResourceBundle.getBundle(path, locale);
+            } catch (MissingResourceException e) {
+                throw new InternalError("Cannot find resource bundle for locale " + locale);
+            }
+        }
+
+        String getMessage(String key, Object... args) {
+            String val = bundle.getString(key);
+            return MessageFormat.format(val, args);
+        }
+
+    }
+
+    public class OptionsHelper<T> {
+
+        private final List<Option<T>> options;
+
+        OptionsHelper(List<Option<T>> options) {
+            this.options = options;
+        }
+
+        public List<String> handleOptions(T task, String[] args) throws BadArgs {
+            List<String> rest = new ArrayList<>();
+            // process options
+            for (int i = 0; i < args.length; i++) {
+                if (args[i].charAt(0) == '-') {
+                    String name = args[i];
+                    Option<T> option = getOption(name);
+                    if (option == null) {
+                        throw new BadArgs("err.unknown.option", name).showUsage(true);
+                    }
+                    String param = null;
+                    if (option.hasArg) {
+                        if (name.startsWith("--") && name.indexOf('=') > 0) {
+                            param = name.substring(name.indexOf('=') + 1, name.length());
+                        } else if (i + 1 < args.length) {
+                            param = args[++i];
+                        }
+                        if (param == null || param.isEmpty() || param.charAt(0) == '-') {
+                            throw new BadArgs("err.missing.arg", name).showUsage(true);
+                        }
+                    }
+                    option.process(task, name, param);
+                    if (option.ignoreRest()) {
+                        i = args.length;
+                    }
+                } else {
+                    rest.add(args[i]);
+                }
+            }
+            return rest;
+        }
+
+        private Option<T> getOption(String name) throws BadArgs {
+            for (Option<T> o : options) {
+                if (o.matches(name)) {
+                    return o;
+                }
+            }
+            return null;
+        }
+
+        public void showHelp(String progName, String pluginsHeader) {
+            log.println(bundleHelper.getMessage("main.usage", progName));
+            for (Option<?> o : options) {
+                String name = o.aliases[0].substring(1); // there must always be at least one name
+                name = name.charAt(0) == '-' ? name.substring(1) : name;
+                if (o.isHidden() || name.equals("h")) {
+                    continue;
+                }
+                log.println(bundleHelper.getMessage("main.opt." + name));
+            }
+        }
+    }
+
+    private PrintWriter log;
+    private final ResourceBundleHelper bundleHelper;
+
+    public TaskHelper(String path) {
+        this.bundleHelper = new ResourceBundleHelper(path);
+    }
+
+    public <T> OptionsHelper<T> newOptionsHelper(Class<T> clazz, Option<?>[] options) {
+        List<Option<T>> optionsList = new ArrayList<>();
+        for (Option<?> o : options) {
+            @SuppressWarnings("unchecked")
+            Option<T> opt = (Option<T>) o;
+            optionsList.add(opt);
+        }
+        return new OptionsHelper<>(optionsList);
+    }
+
+    public BadArgs newBadArgs(String key, Object... args) {
+        return new BadArgs(key, args);
+    }
+
+    public String getMessage(String key, Object... args) {
+        return bundleHelper.getMessage(key, args);
+    }
+
+    public void setLog(PrintWriter log) {
+        this.log = log;
+    }
+
+    public void reportError(String key, Object... args) {
+        log.println(bundleHelper.getMessage("error.prefix") + " " + bundleHelper.getMessage(key, args));
+    }
+
+    public void warning(String key, Object... args) {
+        log.println(bundleHelper.getMessage("warn.prefix") + " " + bundleHelper.getMessage(key, args));
+    }
+
+    public void showVersion(boolean full) {
+        log.println(version(full ? "full" : "release"));
+    }
+
+    public String version(String key) {
+        return System.getProperty("java.version");
+    }
+
+}
--- a/jdk/src/jdk.dev/share/classes/jdk/tools/jimage/resources/jimage.properties	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/jdk.dev/share/classes/jdk/tools/jimage/resources/jimage.properties	Wed Jul 05 20:42:36 2017 +0200
@@ -1,16 +1,17 @@
 main.usage.summary=\
-Usage: {0} <extract|recreate|info|list|verify> <options> jimage...\n\
+Usage: {0} <extract|info|list|recreate|set|verify> <options> jimage...\n\
 use --help for a list of possible options
 
 main.usage=\
-Usage: {0} <extract|recreate|info|list|verify> <options> jimage...\n\
+Usage: {0} <extract|info|list|recreate|set|verify> <options> jimage...\n\
 \n\
 \  extract  - Extract all jimage entries into separate files into the directory\n\
 \             specified by --dir=<directory> (default='.')\n\
-\  recreate - Reconstructs a jimage from an extracted directory (--dir)\n\
 \  info     - Prints information specified in the jimage header.\n\
 \  list     - Prints the names of all the entries in the jimage.  When used with\n\
 \             --verbose will also print entry attributes ex. size and offset.\n\
+\  recreate - Reconstructs a jimage from an extracted directory (--dir)\n\
+\  set      - sets the value of specific jimage header entries\n\
 \  verify   - Reports errors on any .class entries that don't verify as classes.\n\
 \n\
 Possible options include:
@@ -19,27 +20,32 @@
 warn.prefix=Warning:
 
 main.opt.dir=\
-\  --dir                                Target directory for create/expand
+\  --dir                                Target directory for extract/recreate
+
+main.opt.flags=\
+\  --flags=value                        Set the jimage flags to value
+
+main.opt.help=\
+\  --help                               Print this usage message
 
 main.opt.verbose=\
 \  --verbose                            Verbose listing
 
-main.opt.help=\
-\  --help                               Print this usage message
-
 main.opt.version=\
 \  --version                            Version information
 
-err.invalid.task=task must be list|expand|info|verify: {0}
-err.not.a.dir=not a directory: {0}
-err.jimage.not.specified=no jimage specified
-err.only.one.jimage=only one jimage should be specified
-err.jimage.already.exists=jimage already exists: {0}
+err.cannot.create.dir=cannot create directory: {0}
 err.cannot.read.file=cannot read file: {0}
-err.cannot.create.dir=cannot create directory: {0}
-err.not.a.jimage=not a jimage file: {0}
-err.unknown.option=unknown option: {0}
-err.missing.arg=no value given for {0}
+err.cannot.update.file=cannot update file: {0}
+err.flags.not.int=--flags value not integer: {0}
 err.internal.error=internal error: {0} {1} {2}
 err.invalid.arg.for.option=invalid argument for option: {0}
+err.invalid.task=task must be extract|recreate|info|list|verify: {0}
+err.jimage.already.exists=jimage already exists: {0}
+err.jimage.not.specified=no jimage specified
+err.missing.arg=no value given for {0}
+err.not.a.dir=not a directory: {0}
+err.not.a.jimage=not a jimage file: {0}
+err.only.one.jimage=only one jimage should be specified
 err.option.unsupported={0} not supported: {1}
+err.unknown.option=unknown option: {0}
--- a/jdk/src/jdk.naming.dns/share/classes/com/sun/jndi/dns/DnsClient.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/jdk.naming.dns/share/classes/com/sun/jndi/dns/DnsClient.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 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
@@ -184,119 +184,124 @@
         Exception caughtException = null;
         boolean[] doNotRetry = new boolean[servers.length];
 
-        //
-        // The UDP retry strategy is to try the 1st server, and then
-        // each server in order. If no answer, double the timeout
-        // and try each server again.
-        //
-        for (int retry = 0; retry < retries; retry++) {
+        try {
+            //
+            // The UDP retry strategy is to try the 1st server, and then
+            // each server in order. If no answer, double the timeout
+            // and try each server again.
+            //
+            for (int retry = 0; retry < retries; retry++) {
 
-            // Try each name server.
-            for (int i = 0; i < servers.length; i++) {
-                if (doNotRetry[i]) {
-                    continue;
-                }
-
-                // send the request packet and wait for a response.
-                try {
-                    if (debug) {
-                        dprint("SEND ID (" + (retry + 1) + "): " + xid);
+                // Try each name server.
+                for (int i = 0; i < servers.length; i++) {
+                    if (doNotRetry[i]) {
+                        continue;
                     }
 
-                    byte[] msg = null;
-                    msg = doUdpQuery(pkt, servers[i], serverPorts[i],
-                                        retry, xid);
-                    //
-                    // If the matching response is not got within the
-                    // given timeout, check if the response was enqueued
-                    // by some other thread, if not proceed with the next
-                    // server or retry.
-                    //
-                    if (msg == null) {
-                        if (resps.size() > 0) {
-                            msg = lookupResponse(xid);
-                        }
-                        if (msg == null) { // try next server or retry
-                            continue;
+                    // send the request packet and wait for a response.
+                    try {
+                        if (debug) {
+                            dprint("SEND ID (" + (retry + 1) + "): " + xid);
                         }
-                    }
-                    Header hdr = new Header(msg, msg.length);
 
-                    if (auth && !hdr.authoritative) {
-                        caughtException = new NameNotFoundException(
-                                "DNS response not authoritative");
-                        doNotRetry[i] = true;
-                        continue;
-                    }
-                    if (hdr.truncated) {    // message is truncated -- try TCP
-
-                        // Try each server, starting with the one that just
-                        // provided the truncated message.
-                        for (int j = 0; j < servers.length; j++) {
-                            int ij = (i + j) % servers.length;
-                            if (doNotRetry[ij]) {
+                        byte[] msg = null;
+                        msg = doUdpQuery(pkt, servers[i], serverPorts[i],
+                                            retry, xid);
+                        //
+                        // If the matching response is not got within the
+                        // given timeout, check if the response was enqueued
+                        // by some other thread, if not proceed with the next
+                        // server or retry.
+                        //
+                        if (msg == null) {
+                            if (resps.size() > 0) {
+                                msg = lookupResponse(xid);
+                            }
+                            if (msg == null) { // try next server or retry
                                 continue;
                             }
-                            try {
-                                Tcp tcp =
-                                    new Tcp(servers[ij], serverPorts[ij]);
-                                byte[] msg2;
+                        }
+                        Header hdr = new Header(msg, msg.length);
+
+                        if (auth && !hdr.authoritative) {
+                            caughtException = new NameNotFoundException(
+                                    "DNS response not authoritative");
+                            doNotRetry[i] = true;
+                            continue;
+                        }
+                        if (hdr.truncated) {  // message is truncated -- try TCP
+
+                            // Try each server, starting with the one that just
+                            // provided the truncated message.
+                            for (int j = 0; j < servers.length; j++) {
+                                int ij = (i + j) % servers.length;
+                                if (doNotRetry[ij]) {
+                                    continue;
+                                }
                                 try {
-                                    msg2 = doTcpQuery(tcp, pkt);
-                                } finally {
-                                    tcp.close();
-                                }
-                                Header hdr2 = new Header(msg2, msg2.length);
-                                if (hdr2.query) {
-                                    throw new CommunicationException(
-                                        "DNS error: expecting response");
-                                }
-                                checkResponseCode(hdr2);
+                                    Tcp tcp =
+                                        new Tcp(servers[ij], serverPorts[ij]);
+                                    byte[] msg2;
+                                    try {
+                                        msg2 = doTcpQuery(tcp, pkt);
+                                    } finally {
+                                        tcp.close();
+                                    }
+                                    Header hdr2 = new Header(msg2, msg2.length);
+                                    if (hdr2.query) {
+                                        throw new CommunicationException(
+                                            "DNS error: expecting response");
+                                    }
+                                    checkResponseCode(hdr2);
 
-                                if (!auth || hdr2.authoritative) {
-                                    // Got a valid response
-                                    hdr = hdr2;
-                                    msg = msg2;
-                                    break;
-                                } else {
-                                    doNotRetry[ij] = true;
+                                    if (!auth || hdr2.authoritative) {
+                                        // Got a valid response
+                                        hdr = hdr2;
+                                        msg = msg2;
+                                        break;
+                                    } else {
+                                        doNotRetry[ij] = true;
+                                    }
+                                } catch (Exception e) {
+                                    // Try next server, or use UDP response
                                 }
-                            } catch (Exception e) {
-                                // Try next server, or use UDP response
-                            }
-                        } // servers
-                    }
-                    return new ResourceRecords(msg, msg.length, hdr, false);
+                            } // servers
+                        }
+                        return new ResourceRecords(msg, msg.length, hdr, false);
 
-                } catch (IOException e) {
-                    if (debug) {
-                        dprint("Caught IOException:" + e);
-                    }
-                    if (caughtException == null) {
-                        caughtException = e;
-                    }
-                    // Use reflection to allow pre-1.4 compilation.
-                    // This won't be needed much longer.
-                    if (e.getClass().getName().equals(
-                            "java.net.PortUnreachableException")) {
+                    } catch (IOException e) {
+                        if (debug) {
+                            dprint("Caught IOException:" + e);
+                        }
+                        if (caughtException == null) {
+                            caughtException = e;
+                        }
+                        // Use reflection to allow pre-1.4 compilation.
+                        // This won't be needed much longer.
+                        if (e.getClass().getName().equals(
+                                "java.net.PortUnreachableException")) {
+                            doNotRetry[i] = true;
+                        }
+                    } catch (NameNotFoundException e) {
+                        // This is authoritative, so return immediately
+                        throw e;
+                    } catch (CommunicationException e) {
+                        if (caughtException == null) {
+                            caughtException = e;
+                        }
+                    } catch (NamingException e) {
+                        if (caughtException == null) {
+                            caughtException = e;
+                        }
                         doNotRetry[i] = true;
                     }
-                } catch (NameNotFoundException e) {
-                    throw e;
-                } catch (CommunicationException e) {
-                    if (caughtException == null) {
-                        caughtException = e;
-                    }
-                } catch (NamingException e) {
-                    if (caughtException == null) {
-                        caughtException = e;
-                    }
-                    doNotRetry[i] = true;
-                }
-            } // servers
-        } // retries
+                } // servers
+            } // retries
 
-        reqs.remove(xid);
+        } finally {
+            reqs.remove(xid); // cleanup
+        }
+
         if (caughtException instanceof NamingException) {
             throw (NamingException) caughtException;
         }
--- a/jdk/src/jdk.rmic/share/classes/sun/tools/java/ClassPath.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/jdk.rmic/share/classes/sun/tools/java/ClassPath.java	Wed Jul 05 20:42:36 2017 +0200
@@ -394,7 +394,7 @@
         this.pkgDirs = new HashMap<>();
 
         // fill in module directories at the root dir
-        Path root = fs.getPath("/");
+        Path root = fs.getPath("/modules");
         try {
             try (DirectoryStream<Path> stream = Files.newDirectoryStream(root)) {
                 for (Path entry: stream) {
--- a/jdk/src/jdk.security.auth/share/classes/com/sun/security/auth/module/Krb5LoginModule.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/src/jdk.security.auth/share/classes/com/sun/security/auth/module/Krb5LoginModule.java	Wed Jul 05 20:42:36 2017 +0200
@@ -122,8 +122,9 @@
  * must also be set to true; Otherwise a configuration error will
  * be returned.</dd>
  * <dt>{@code renewTGT}:</dt>
- * <dd>Set this to true, if you want to renew
- * the TGT. If this is set, {@code useTicketCache} must also be
+ * <dd>Set this to true, if you want to renew the TGT when it's more than
+ * half-way expired (the time until expiration is less than the time
+ * since start time). If this is set, {@code useTicketCache} must also be
  * set to true; otherwise a configuration error will be returned.</dd>
  * <dt>{@code doNotPrompt}:</dt>
  * <dd>Set this to true if you do not want to be
@@ -649,17 +650,19 @@
                     (principal, ticketCacheName);
 
                 if (cred != null) {
-                    // check to renew credentials
+                    if (renewTGT && isOld(cred)) {
+                        // renew if ticket is old.
+                        Credentials newCred = renewCredentials(cred);
+                        if (newCred != null) {
+                            cred = newCred;
+                        }
+                    }
                     if (!isCurrent(cred)) {
-                        if (renewTGT) {
-                            cred = renewCredentials(cred);
-                        } else {
-                            // credentials have expired
-                            cred = null;
-                            if (debug)
-                                System.out.println("Credentials are" +
-                                                " no longer valid");
-                        }
+                        // credentials have expired
+                        cred = null;
+                        if (debug)
+                            System.out.println("Credentials are" +
+                                    " no longer valid");
                     }
                 }
 
@@ -968,7 +971,7 @@
         }
     }
 
-    private boolean isCurrent(Credentials creds)
+    private static boolean isCurrent(Credentials creds)
     {
         Date endTime = creds.getEndTime();
         if (endTime != null) {
@@ -977,6 +980,23 @@
         return true;
     }
 
+    private static boolean isOld(Credentials creds)
+    {
+        Date endTime = creds.getEndTime();
+        if (endTime != null) {
+            Date authTime = creds.getAuthTime();
+            long now = System.currentTimeMillis();
+            if (authTime != null) {
+                // pass the mid between auth and end
+                return now - authTime.getTime() > endTime.getTime() - now;
+            } else {
+                // will expire in less than 2 hours
+                return now <= endTime.getTime() - 1000*3600*2L;
+            }
+        }
+        return false;
+    }
+
     private Credentials renewCredentials(Credentials creds)
     {
         Credentials lcreds;
--- a/jdk/test/ProblemList.txt	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/ProblemList.txt	Wed Jul 05 20:42:36 2017 +0200
@@ -298,6 +298,9 @@
 # 8051770
 sun/security/provider/SecureRandom/StrongSecureRandom.java      macosx-10.10
 
+# 8074580
+sun/security/pkcs11/rsa/TestKeyPairGenerator.java               generic-all
+
 ############################################################################
 
 # jdk_sound
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/com/sun/crypto/provider/Cipher/PBE/PBESameBuffer/AESPBEWrapper.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,114 @@
+/*
+ * Copyright (c) 2012, 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.
+ */
+
+import java.io.PrintStream;
+import java.security.AlgorithmParameters;
+import java.security.InvalidKeyException;
+import java.security.Provider;
+import javax.crypto.Cipher;
+import javax.crypto.SecretKeyFactory;
+import javax.crypto.spec.PBEKeySpec;
+
+/**
+ * Wrapper class to test a given AES-based PBE algorithm.
+ *
+ * @author Alexander Fomin
+ */
+public class AESPBEWrapper extends PBEWrapper {
+
+    private AlgorithmParameters pbeParams;
+
+    /**
+     * Constructor. Instantiate Cipher using the given AES-based PBE algorithms.
+     *
+     * @param p security Provider
+     * @param algo PKDF2 algorithm
+     * @param passwd password phrase
+     * @param out print stream
+     * @throws Exception all exceptions are thrown
+     */
+    public AESPBEWrapper(Provider p, String algo, String passwd,
+            PrintStream out) throws Exception {
+        super(algo,
+                SecretKeyFactory.getInstance(algo, p).generateSecret(
+                        new PBEKeySpec(passwd.toCharArray())),
+                Cipher.getInstance(algo, p), out);
+    }
+
+    /**
+     * Perform encryption/decryption operation (depending on the specified
+     * edMode) on the same byte buffer. Compare result with the result at an
+     * allocated buffer. If both results are equal - return true, otherwise
+     * return false.
+     *
+     * @param edMode specified mode
+     * @param inputText text to decrypt
+     * @param offset offset in the text
+     * @param len input length
+     * @return ture - test passed; false - test failed
+     */
+    @Override
+    public boolean execute(int edMode, byte[] inputText, int offset, int len) {
+        try {
+            // init Cipher
+            if (Cipher.ENCRYPT_MODE == edMode) {
+                ci.init(Cipher.ENCRYPT_MODE, this.key);
+                pbeParams = ci.getParameters();
+            } else {
+                ci.init(Cipher.DECRYPT_MODE, this.key, pbeParams);
+            }
+
+            // First, generate the cipherText at an allocated buffer
+            byte[] outputText = ci.doFinal(inputText, offset, len);
+
+            // Second, generate cipherText again at the same buffer of plainText
+            int myoff = offset / 2;
+            int off = ci.update(inputText, offset, len, inputText, myoff);
+            ci.doFinal(inputText, myoff + off);
+
+            if (this.algo.endsWith("AES_256")) {
+                out.print("Expected exception uncaught, "
+                        + "keyStrength > 128 within " + this.algo);
+
+                return false;
+            }
+
+            // Compare to see whether the two results are the same or not
+            return equalsBlock(inputText, myoff, outputText, 0,
+                    outputText.length);
+        } catch (Exception ex) {
+            if ((ex instanceof InvalidKeyException)
+                    && this.algo.endsWith("AES_256")) {
+                out.println("Expected InvalidKeyException exception: "
+                        + ex.getMessage());
+
+                return true;
+            }
+
+            out.println("Catch unexpected exception within " + algo);
+            ex.printStackTrace(out);
+
+            return false;
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/com/sun/crypto/provider/Cipher/PBE/PBESameBuffer/PBECipherWrapper.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,110 @@
+/*
+ * Copyright (c) 2012, 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.
+ */
+
+/*
+ * @author Valerie PENG
+ * @author Yun Ke
+ * @author Alexander Fomin
+ * @author rhalade
+ */
+import java.security.spec.AlgorithmParameterSpec;
+
+import java.util.StringTokenizer;
+
+import java.security.InvalidKeyException;
+import java.security.Provider;
+
+import java.io.PrintStream;
+
+import javax.crypto.Cipher;
+import javax.crypto.SecretKeyFactory;
+import javax.crypto.spec.PBEKeySpec;
+import javax.crypto.spec.PBEParameterSpec;
+
+public class PBECipherWrapper extends PBEWrapper {
+
+    private final AlgorithmParameterSpec aps;
+
+    public PBECipherWrapper(
+            Provider p, String algo, String passwd, PrintStream out)
+            throws Exception {
+        super(algo,
+                SecretKeyFactory.getInstance(
+                        new StringTokenizer(algo, "/").nextToken(), p).generateSecret(
+                        new PBEKeySpec(passwd.toCharArray())),
+                Cipher.getInstance(algo, p), out);
+
+        int SALT_SIZE = 8;
+        aps = new PBEParameterSpec(generateSalt(SALT_SIZE), ITERATION_COUNT);
+    }
+
+    @Override
+    public boolean execute(int edMode, byte[] inputText, int offset,
+            int len) {
+        StringTokenizer st = new StringTokenizer(algo, "/");
+        String baseAlgo = st.nextToken().toUpperCase();
+
+        // Perform encryption or decryption depends on the specified edMode
+        try {
+            ci.init(edMode, key, aps);
+
+            // First, generate the cipherText at an allocated buffer
+            byte[] outputText = ci.doFinal(inputText, offset, len);
+
+            // Second, generate cipherText again at the same buffer of
+            // plainText
+            int myoff = offset / 2;
+            int off = ci.update(inputText, offset, len, inputText, myoff);
+
+            ci.doFinal(inputText, myoff + off);
+
+            if (baseAlgo.endsWith("TRIPLEDES")
+                    || baseAlgo.endsWith("AES_256")) {
+                out.print("Expected exception uncaught,"
+                        + "keyStrength > 128 within " + this.algo);
+
+                return false;
+            }
+
+            // Compare to see whether the two results are the same or not
+            boolean result = equalsBlock(inputText, myoff, outputText, 0,
+                    outputText.length);
+
+            return result;
+        } catch (Exception ex) {
+            if ((ex instanceof InvalidKeyException)
+                    && (baseAlgo.endsWith("TRIPLEDES")
+                    || baseAlgo.endsWith("AES_256"))) {
+                out.println("Expected InvalidKeyException exception: "
+                        + ex.getMessage());
+
+                return true;
+            }
+
+            out.println("Catch unexpected exception within " + algo);
+            ex.printStackTrace(out);
+
+            return false;
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/com/sun/crypto/provider/Cipher/PBE/PBESameBuffer/PBESameBuffer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,152 @@
+/*
+ * Copyright (c) 2012, 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 8041787
+ * @library .
+ * @build PBEWrapper PBEWrapperCreator PBKDF2Wrapper AESPBEWrapper PBECipherWrapper
+ * @summary Verify that same encrypt/decrypt buffer can be used for PBE ciphers
+ * @author Alexander Fomin
+ * @author rhalade
+ * @run main PBESameBuffer
+ */
+import java.io.PrintStream;
+import java.security.*;
+import java.util.Random;
+import javax.crypto.Cipher;
+
+public class PBESameBuffer {
+
+    private static final String[] pbeAlgorithms = {
+        "pbeWithMD5ANDdes", "PBEWithMD5AndDES/CBC/PKCS5Padding",
+        "pbeWithMD5ANDtripledes", "PBEWithMD5AndTRIPLEDES/CBC/PKCS5Padding",
+        "PBEwithSHA1AndDESede", "PBEwithSHA1AndDESede/CBC/PKCS5Padding",
+        "PBEwithSHA1AndRC2_40", "PBEwithSHA1AndRC2_40/CBC/PKCS5Padding",
+        "PBEWithSHA1AndRC2_128", "PBEWithSHA1AndRC2_128/CBC/PKCS5Padding",
+        "PBEWithSHA1AndRC4_40", "PBEWithSHA1AndRC4_40/ECB/NoPadding",
+        "PBEWithSHA1AndRC4_128", "PBEWithSHA1AndRC4_128/ECB/NoPadding",
+        "PBEWithHmacSHA1AndAES_128",
+        "PBEWithHmacSHA224AndAES_128",
+        "PBEWithHmacSHA256AndAES_128",
+        "PBEWithHmacSHA384AndAES_128",
+        "PBEWithHmacSHA512AndAES_128",
+        "PBEWithHmacSHA1AndAES_256",
+        "PBEWithHmacSHA224AndAES_256",
+        "PBEWithHmacSHA256AndAES_256",
+        "PBEWithHmacSHA384AndAES_256",
+        "PBEWithHmacSHA512AndAES_256",
+        "PBKDF2WithHmacSHA1",
+        "PBKDF2WithHmacSHA224",
+        "PBKDF2WithHmacSHA256",
+        "PBKDF2WithHmacSHA384",
+        "PBKDF2WithHmacSHA512"
+    };
+
+    private static final String PBEPASS = "Hush, it's supposed to be a secret!";
+
+    private static final int INPUT_LENGTH = 800;
+    private static final int[] OFFSETS = {0, 1, 2, 3};
+    private static final int NUM_PAD_BYTES = 8;
+    private static final int PBKDF2_ADD_PAD_BYTES = 8;
+
+    private static int OUTPUT_OFFSET;
+
+    public static void main(String[] args) {
+        if (!(new PBESameBuffer().test(args, System.out))) {
+            throw new RuntimeException("Some PBE algorithm tests failed");
+        }
+    }
+
+    public boolean test(String[] args, PrintStream out) {
+        boolean result = true;
+
+        Provider p = Security.getProvider("SunJCE");
+
+        for (int loop : OFFSETS) {
+            OUTPUT_OFFSET = loop;
+
+            // generate input data
+            byte[] inputText = new byte[INPUT_LENGTH + NUM_PAD_BYTES
+                    + OUTPUT_OFFSET * 2 + PBKDF2_ADD_PAD_BYTES];
+            new Random().nextBytes(inputText);
+
+            for (String algorithm : pbeAlgorithms) {
+                out.println("=> Testing algorithm " + algorithm + " and offset "
+                        + OUTPUT_OFFSET + ":");
+
+                try {
+                    // Initialize Cipher and key for this algorithm
+                    PBEWrapper pbeCi = PBEWrapperCreator.createWrapper(p,
+                            algorithm,
+                            PBEPASS,
+                            out);
+
+                    // Encrypt
+                    if ((pbeCi != null) && (!pbeCi.execute(Cipher.ENCRYPT_MODE,
+                            inputText,
+                            OUTPUT_OFFSET * 2,
+                            INPUT_LENGTH))) {
+                        result = false;
+                    }
+
+                    // PBKDF2 required 16 byte padding
+                    int padLength = getPadLength(algorithm);
+
+                    // Decrypt
+                    // Note: inputText is implicitly padded by the above encrypt
+                    // operation so decrypt operation can safely proceed
+                    if ((pbeCi != null) && (!pbeCi.execute(Cipher.DECRYPT_MODE,
+                            inputText,
+                            OUTPUT_OFFSET,
+                            INPUT_LENGTH + padLength))) {
+                        result = false;
+                    }
+                } catch (Exception ex) {
+                    ex.printStackTrace(out);
+                    result = false;
+                }
+            }
+        }
+
+        return result;
+    }
+
+    /**
+     * Get the padding length for the given algorithm
+     *
+     * @param theAlgName algorithm name
+     * @return padding length for the given algorithm
+     */
+    private int getPadLength(String theAlgName) {
+        if (theAlgName.toUpperCase().contains("PBKDF2")) {
+            return NUM_PAD_BYTES + PBKDF2_ADD_PAD_BYTES;
+        }
+
+        if (theAlgName.toUpperCase().contains("AES")) {
+            return NUM_PAD_BYTES + PBKDF2_ADD_PAD_BYTES;
+        }
+
+        return NUM_PAD_BYTES;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/com/sun/crypto/provider/Cipher/PBE/PBESameBuffer/PBEWrapper.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,98 @@
+/*
+ * Copyright (c) 2012, 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.
+ */
+
+import java.io.PrintStream;
+import java.util.Random;
+import javax.crypto.Cipher;
+import javax.crypto.SecretKey;
+
+/**
+ * PBEWrapper is the abstract class for all concrete PBE Cipher wrappers. A
+ * PBEWrapper object encapsulates the information and behavior needed to test if
+ * the multiple-part encryption/decryption is performing by expected way on the
+ * same byte buffer.
+ *
+ * @author Alexandr Fomin
+ * @author rhalade
+ */
+public abstract class PBEWrapper {
+
+    protected final static int ITERATION_COUNT = 1000;
+
+    protected final SecretKey key;
+    protected final Cipher ci;
+    protected final String algo;
+    protected final PrintStream out;
+
+    public PBEWrapper(String pAlgo, SecretKey pKey, Cipher pCi,
+            PrintStream pOut ){
+        this.algo = pAlgo;
+        this.key = pKey;
+        this.ci = pCi;
+        this.out = pOut;
+    }
+
+    /**
+     * Abstract method need to be implemented in the subclasses.
+     *
+     * @param edMode Cipher mode - encrypt/decrypt
+     * @param inputText byte buffer to process
+     * @param offset offset in byte the inputText
+     * @param len length of byte to process in inputText
+     * @return true if cipher operation is successful, false otherwise
+     */
+    public abstract boolean execute(int edMode, byte[] inputText, int offset,
+            int len);
+
+    /**
+     * An utility method to prepare "salt" for following Secret Key generation.
+     *
+     * @param numberOfBytes number of bytes in salt
+     * @return randomly generated byte array
+     */
+    protected static byte[] generateSalt(int numberOfBytes) {
+        byte[] salt = new byte[numberOfBytes];
+        new Random().nextBytes(salt);
+        return salt;
+    }
+
+    /**
+     * An utility method to check if two byte arrays are equal
+     *
+     * @param b1 first byte array
+     * @param off1 offset to compare from in b1
+     * @param b2 second byte array
+     * @param off2 offset to compare from in b2
+     * @param len length to compare
+     * @return true of arrays are equal, false otherwise
+     */
+    protected boolean equalsBlock(byte[] b1, int off1,
+            byte[] b2, int off2, int len) {
+        for (int i = off1, j = off2, k = 0; k < len; i++, j++, k++) {
+            if (b1[i] != b2[j]) {
+                return false;
+            }
+        }
+        return true;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/com/sun/crypto/provider/Cipher/PBE/PBESameBuffer/PBEWrapperCreator.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,59 @@
+/*
+ * Copyright (c) 2012, 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.
+ */
+
+import java.security.Provider;
+import java.io.PrintStream;
+
+/**
+ * An utility class to create PBEWrapper object for the TestCipherSameBuffer
+ * test.
+ *
+ * @author Alexander Fomin
+ */
+public class PBEWrapperCreator {
+
+    private static final String PBKDF2 = "PBKDF2";
+    private static final String AES = "AES";
+
+    /**
+     * Create PBEWrapper for the TestCipherSameBuffer test using given
+     * parameters.
+     *
+     * @param p security provider
+     * @param algo algorithms to test
+     * @param passwd a password phrase
+     * @param out print stream object
+     * @return PBEWrapper in accordance to requested algorithm
+     * @throws Exception all exception are thrown.
+     */
+    public static PBEWrapper createWrapper(Provider p, String algo,
+            String passwd, PrintStream out) throws Exception {
+        if (algo.toUpperCase().contains(PBKDF2)) {
+            return new PBKDF2Wrapper(p, algo, passwd, out);
+        } else if (algo.toUpperCase().contains(AES)) {
+            return new AESPBEWrapper(p, algo, passwd, out);
+        } else {
+            return new PBECipherWrapper(p, algo, passwd, out);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/com/sun/crypto/provider/Cipher/PBE/PBESameBuffer/PBKDF2Wrapper.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,114 @@
+/*
+ * Copyright (c) 2012, 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.
+ */
+
+import java.io.PrintStream;
+import java.security.Provider;
+import javax.crypto.Cipher;
+import javax.crypto.SecretKeyFactory;
+import javax.crypto.spec.IvParameterSpec;
+import javax.crypto.spec.PBEKeySpec;
+import javax.crypto.spec.SecretKeySpec;
+
+/**
+ * Wrapper class to test a given SecretKeyFactory.PBKDF2 algorithm.
+ *
+ * @author Alexander Fomin
+ */
+public class PBKDF2Wrapper extends PBEWrapper {
+    private static final String CIPHER_TANSFORMATION = "AES/CBC/PKCS5Padding";
+    private static final int SALT_SIZE = 64;
+    private static final int PKDF2_DEFAULT_KEY_LEN = 128;
+
+    private static volatile byte[] iv;
+
+    /**
+     * PBKDF2Wrapper constructor. Instantiate Cipher using
+     * "AES/CBC/PKCS5Padding" transformation. Generate a secret key using given
+     * PKDF2 algorithms.
+     *
+     * @param p security Provider
+     * @param algo PKDF2 algorithm
+     * @param passwd password phrase
+     * @param out print stream
+     * @throws Exception all exceptions are thrown
+     */
+    public PBKDF2Wrapper(Provider p, String algo, String passwd,
+            PrintStream out) throws Exception {
+        super(algo,
+                SecretKeyFactory.getInstance(algo, p).generateSecret(
+                        new PBEKeySpec(passwd.toCharArray(),
+                generateSalt(SALT_SIZE), ITERATION_COUNT, PKDF2_DEFAULT_KEY_LEN)),
+                Cipher.getInstance(CIPHER_TANSFORMATION, p), out);
+    }
+
+    /**
+     * Perform encryption/decryption operation (depending on the specified
+     * edMode) on the same byte buffer. Compare result with the result at an
+     * allocated buffer. If both results are equal - return true, otherwise
+     * return false.
+     *
+     * @param edMode specified mode
+     * @param inputText text to decrypt
+     * @param offset offset in the text
+     * @param len input length
+     * @return ture - test passed; false - test failed
+     */
+    @Override
+    public boolean execute(int edMode, byte[] inputText, int offset, int len) {
+        int needBytesForResult = -1;
+        String KEY_ALGORITHM = "AES";
+
+        try {
+            // init Cipher
+            if (Cipher.ENCRYPT_MODE == edMode) {
+                ci.init(Cipher.ENCRYPT_MODE, new SecretKeySpec(key.getEncoded(),
+                        KEY_ALGORITHM));
+                iv = ci.getParameters().getParameterSpec(IvParameterSpec.class).
+                        getIV();
+            } else {
+                ci.init(Cipher.DECRYPT_MODE,
+                        new SecretKeySpec(key.getEncoded(), KEY_ALGORITHM),
+                        new IvParameterSpec(iv));
+            }
+
+            // First, generate the cipherText at an allocated buffer
+            byte[] outputText = ci.doFinal(inputText, offset, len);
+
+            // Second, generate cipherText again at the same buffer of plainText
+            int myoff = offset / 2;
+            int off = ci.update(inputText, offset, len, inputText, myoff);
+            ci.doFinal(inputText, myoff + off);
+
+            // Compare to see whether the two results are the same or not
+            return equalsBlock(inputText, myoff, outputText, 0,
+                    outputText.length);
+        } catch (Exception ex) {
+            out.println("Catch unexpected exception within " + algo
+                    + " " + edMode + ": " + ex.getMessage()
+                    + ". getOutputSize()" + "returned " + needBytesForResult);
+            ex.printStackTrace(out);
+
+            return false;
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/com/sun/crypto/provider/Cipher/PBE/PBMacBuffer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,248 @@
+/*
+ * Copyright (c) 2012, 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.
+ */
+
+import java.nio.ByteBuffer;
+import java.security.InvalidKeyException;
+import java.security.NoSuchAlgorithmException;
+import java.security.SecureRandom;
+import java.security.spec.InvalidKeySpecException;
+import java.util.Random;
+import javax.crypto.Mac;
+import javax.crypto.SecretKey;
+import javax.crypto.SecretKeyFactory;
+import javax.crypto.spec.PBEKeySpec;
+
+/**
+ * @test
+ * @bug 8041787
+ * @summary verify that Mac.update works with different size ByteBuffer
+ * @author Alexander Fomin
+ * @run main PBMacBuffer
+ */
+public class PBMacBuffer {
+
+    private final int LARGE_SIZE = 500000;
+
+    public static void main(String[] args) {
+        String[] PBMAC1Algorithms = {
+            "HmacPBESHA1",
+            "PBEWithHmacSHA1",
+            "PBEWithHmacSHA224",
+            "PBEWithHmacSHA256",
+            "PBEWithHmacSHA384",
+            "PBEWithHmacSHA512"
+        };
+
+        String[] PBKDF2Algorithms = {
+            "PBKDF2WithHmacSHA1",
+            "PBKDF2WithHmacSHA224",
+            "PBKDF2WithHmacSHA256",
+            "PBKDF2WithHmacSHA384",
+            "PBKDF2WithHmacSHA512"
+        };
+
+        PBMacBuffer testRunner = new PBMacBuffer();
+        boolean failed = false;
+
+        for (String thePBMacAlgo : PBMAC1Algorithms) {
+
+            for (String thePBKDF2Algo : PBKDF2Algorithms) {
+
+                System.out.println("Running test with " + thePBMacAlgo
+                        + " and " + thePBKDF2Algo + ":");
+                try {
+                    if (!testRunner.doTest(thePBMacAlgo, thePBKDF2Algo)) {
+                        failed = true;
+                    }
+                } catch (NoSuchAlgorithmException | InvalidKeyException |
+                        InvalidKeySpecException e) {
+                    failed = true;
+                    e.printStackTrace(System.out);
+                    System.out.println("Test FAILED.");
+                }
+            }
+        }
+
+        if (failed) {
+            throw new RuntimeException("One or more tests failed....");
+        }
+    }
+
+    /**
+     * Tests Mac.update(ByteBuffer input) method. Three test cases are
+     * performed: - large ByteBuffer test case to test if the update() method
+     * process a large ByteBuffer correctly; - empty ByteBuffer test case to
+     * test if the update() method process an empty ByteBuffer correctly; - NULL
+     * ByteBuffer test case to test if the update() method throws expected
+     * IllegalArgumentException exception.
+     *
+     * @param theMacAlgo PBMAC algorithm to test
+     * @param thePBKDF2Algo PBKDF2 algorithm to test
+     * @return true - test passed; false - otherwise.
+     * @throws NoSuchAlgorithmException
+     * @throws InvalidKeyException
+     * @throws InvalidKeySpecException
+     * @see javax.crypto.Mac
+     */
+    protected boolean doTest(String theMacAlgo, String thePBKDF2Algo)
+            throws NoSuchAlgorithmException, InvalidKeyException,
+            InvalidKeySpecException {
+        // obtain a SecretKey using PBKDF2
+        SecretKey key = getSecretKey(thePBKDF2Algo);
+
+        // Instantiate Mac object and init it with a SecretKey
+        Mac theMac = Mac.getInstance(theMacAlgo);
+        theMac.init(key);
+
+        // Do large ByteBuffer test case
+        if (!largeByteBufferTest(theMac)) {
+            System.out.println("Large ByteBuffer test case failed.");
+            return false;
+        }
+
+        // Do empty ByteBuffer test case
+        if (!emptyByteBufferTest(theMac)) {
+            System.out.println("Empty ByteBuffer test case failed.");
+            return false;
+        }
+
+        // Do null ByteBuffer test case
+        if (!nullByteBufferTest(theMac)) {
+            System.out.println("NULL ByteBuffer test case failed.");
+            return false;
+        }
+
+        return true;
+    }
+
+    /**
+     * Large ByteBuffer test case. Generate random ByteBuffer of LARGE_SIZE
+     * size. Performs MAC operation with the given Mac object (theMac
+     * parameter).Verifies the assertion "Upon return, the buffer's position
+     * will be equal to its limit; its limit will not have changed".
+     *
+     * @param theMac MAC object to test.
+     * @return true - test case passed; false - otherwise;
+     */
+    protected boolean largeByteBufferTest(Mac theMac) {
+        ByteBuffer buf = generateRandomByteBuffer(LARGE_SIZE);
+        int limitBefore = buf.limit();
+
+        theMac.update(buf);
+        theMac.doFinal();
+
+        int limitAfter = buf.limit();
+        int positonAfter = buf.position();
+
+        if (limitAfter != limitBefore) {
+            System.out.println("FAIL: Buffer's limit has been chenged.");
+            return false;
+        }
+
+        if (positonAfter != limitAfter) {
+            System.out.println("FAIL: "
+                    + "Buffer's position isn't equal to its limit");
+            return false;
+        }
+
+        return true;
+    }
+
+    /**
+     * Empty ByteBuffer test case. Generates an empty ByteBuffer. Perform MAC
+     * operation. No exceptions are expected.
+     *
+     * @param theMac
+     * @return true - test case pass; exception otherwise
+     */
+    protected boolean emptyByteBufferTest(Mac theMac) {
+        ByteBuffer buf = generateRandomByteBuffer(0);
+        theMac.update(buf);
+        theMac.doFinal();
+        return true;
+    }
+
+    /**
+     * NULL ByteBuffer test case. Pass NULL ByteBuffer to Mac.update(ByteBuffer
+     * buffer) method. An IllegalArgumentException expected.
+     *
+     * @param theMac Mac object to test.
+     * @return true - test case pass; false - otherwise.
+     */
+    protected boolean nullByteBufferTest(Mac theMac) {
+        try {
+            ByteBuffer buf = null;
+            theMac.update(buf);
+            theMac.doFinal();
+        } catch (IllegalArgumentException e) {
+            // expected exception has been thrown
+            return true;
+        }
+
+        System.out.println("FAIL: "
+                + "IllegalArgumentException hasn't been thrown as expected");
+
+        return false;
+    }
+
+    /**
+     * Get SecretKey for the given PBKDF2 algorithm.
+     *
+     * @param thePBKDF2Algorithm - PBKDF2 algorithm
+     * @return SecretKey according to thePBKDF2Algorithm
+     * @throws NoSuchAlgorithmException
+     * @throws InvalidKeySpecException
+     */
+    protected SecretKey getSecretKey(String thePBKDF2Algorithm)
+            throws NoSuchAlgorithmException, InvalidKeySpecException {
+        // Prepare salt
+        byte[] salt = new byte[64]; // PKCS #5 v2.1 recommendation
+        new SecureRandom().nextBytes(salt);
+
+        // Generate secret key
+        PBEKeySpec pbeKeySpec = new PBEKeySpec(
+                "A #pwd# implied to be hidden!".toCharArray(),
+                salt, 1000, 128);
+        SecretKeyFactory keyFactory
+                = SecretKeyFactory.getInstance(thePBKDF2Algorithm);
+        return keyFactory.generateSecret(pbeKeySpec);
+    }
+
+    /**
+     * An utility method to generate a random ByteBuffer of the requested size.
+     *
+     * @param size size of the ByteBuffer.
+     * @return ByteBuffer populated random data;
+     */
+    private ByteBuffer generateRandomByteBuffer(int size) {
+        // generate randome byte array
+        byte[] data = new byte[size];
+        new Random().nextBytes(data);
+
+        // create ByteBuffer
+        ByteBuffer bb = ByteBuffer.wrap(data);
+
+        return bb;
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/com/sun/crypto/provider/Cipher/PBE/PBMacDoFinalVsUpdate.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,212 @@
+/*
+ * Copyright (c) 2012, 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.
+ */
+
+import java.security.InvalidKeyException;
+import java.security.NoSuchAlgorithmException;
+import java.security.SecureRandom;
+import java.security.spec.InvalidKeySpecException;
+import javax.crypto.Mac;
+import javax.crypto.SecretKey;
+import javax.crypto.SecretKeyFactory;
+import javax.crypto.spec.PBEKeySpec;
+
+/**
+ * @test
+ * @bug 8041787
+ * @summary Check if doFinal and update operation result in same PBMac
+ * @author Alexander Fomin
+ * @run main PBMacDoFinalVsUpdate
+ */
+public class PBMacDoFinalVsUpdate {
+
+    public static void main(String[] args) {
+        String[] PBMAC1Algorithms = {
+            "HmacPBESHA1",
+            "PBEWithHmacSHA1",
+            "PBEWithHmacSHA224",
+            "PBEWithHmacSHA256",
+            "PBEWithHmacSHA384",
+            "PBEWithHmacSHA512"
+        };
+
+        String[] PBKDF2Algorithms = {
+            "PBKDF2WithHmacSHA1",
+            "PBKDF2WithHmacSHA224",
+            "PBKDF2WithHmacSHA256",
+            "PBKDF2WithHmacSHA384",
+            "PBKDF2WithHmacSHA512"
+        };
+
+        PBMacDoFinalVsUpdate testRunner = new PBMacDoFinalVsUpdate();
+        boolean failed = false;
+
+        for (String thePBMacAlgo : PBMAC1Algorithms) {
+
+            for (String thePBKDF2Algo : PBKDF2Algorithms) {
+
+                System.out.println("Running test with " + thePBMacAlgo
+                        + " and " + thePBKDF2Algo + ":");
+                try {
+                    if (!testRunner.doTest(thePBMacAlgo, thePBKDF2Algo)) {
+                        failed = true;
+                    }
+                } catch (NoSuchAlgorithmException | InvalidKeyException |
+                        InvalidKeySpecException e) {
+                    failed = true;
+                    e.printStackTrace(System.out);
+                    System.out.println("Test FAILED.");
+                }
+            }
+        }
+
+        if (failed) {
+            throw new RuntimeException("One or more tests failed....");
+        }
+    }
+
+    /**
+     * Uses a random generator to initialize a message, instantiate a Mac object
+     * according to the given PBMAC1 algorithm, initialize the object with a
+     * SecretKey derived using PBKDF2 algorithm (see PKCS #5 v21, chapter 7.1),
+     * feed the message into the Mac object all at once and get the output MAC
+     * as result1. Reset the Mac object, chop the message into three pieces,
+     * feed into the Mac object sequentially, and get the output MAC as result2.
+     * Finally, compare result1 and result2 and see if they are the same.
+     *
+     * @param theMacAlgo PBMAC algorithm to test
+     * @param thePBKDF2Algo PBKDF2 algorithm to test
+     * @return true - the test is passed; false - otherwise.
+     * @throws NoSuchAlgorithmException
+     * @throws InvalidKeyException
+     * @throws InvalidKeySpecException
+     */
+    protected boolean doTest(String theMacAlgo, String thePBKDF2Algo)
+            throws NoSuchAlgorithmException, InvalidKeyException,
+            InvalidKeySpecException {
+        int OFFSET = 5;
+
+        // Some message for which a MAC result will be calculated
+        byte[] plain = new byte[25];
+        new SecureRandom().nextBytes(plain);
+
+        // Form tail - is one of the three pieces
+        byte[] tail = new byte[plain.length - OFFSET];
+        System.arraycopy(plain, OFFSET, tail, 0, tail.length);
+
+        // Obtain a SecretKey using PBKDF2
+        SecretKey key = getSecretKey(thePBKDF2Algo);
+
+        // Instantiate Mac object and init it with a SecretKey and calc result1
+        Mac theMac = Mac.getInstance(theMacAlgo);
+        theMac.init(key);
+        byte[] result1 = theMac.doFinal(plain);
+
+        if (!isMacLengthExpected(theMacAlgo, result1.length)) {
+            return false;
+        }
+
+        // Reset Mac and calculate result2
+        theMac.reset();
+        theMac.update(plain[0]);
+        theMac.update(plain, 1, OFFSET - 1);
+        byte[] result2 = theMac.doFinal(tail);
+
+        // Return result
+        if (!java.util.Arrays.equals(result1, result2)) {
+            System.out.println("result1 and result2 are not the same:");
+            System.out.println("result1: " + dumpByteArray(result1));
+            System.out.println("result2: " + dumpByteArray(result2));
+            return false;
+        } else {
+            System.out.println("Resulted MAC with update and doFinal is same");
+        }
+
+        return true;
+    }
+
+    /**
+     * Get SecretKey for the given PBKDF2 algorithm.
+     *
+     * @param thePBKDF2Algorithm - PBKDF2 algorithm
+     * @return SecretKey according to thePBKDF2Algorithm
+     * @throws NoSuchAlgorithmException
+     * @throws InvalidKeySpecException
+     */
+    protected SecretKey getSecretKey(String thePBKDF2Algorithm)
+            throws NoSuchAlgorithmException, InvalidKeySpecException {
+        // Prepare salt
+        byte[] salt = new byte[64]; // PKCS #5 v2.1 recommendation
+        new SecureRandom().nextBytes(salt);
+
+        // Generate secret key
+        PBEKeySpec pbeKeySpec = new PBEKeySpec(
+                "A #pwd# implied to be hidden!".toCharArray(),
+                salt, 1000, 128);
+        SecretKeyFactory keyFactory
+                = SecretKeyFactory.getInstance(thePBKDF2Algorithm);
+        return keyFactory.generateSecret(pbeKeySpec);
+    }
+
+    /**
+     * Check if the lengthToCheck is expected length for the given MACAlgo.
+     *
+     * @param MACAlgo PBMAC algorithm
+     * @param lengthToCheck the length of MAC need to check
+     * @return true - lengthToCheck is expected length for the MACAlgo; false -
+     * otherwise.
+     */
+    protected boolean isMacLengthExpected(String MACAlgo, int lengthToCheck) {
+        java.util.regex.Pattern p = java.util.regex.Pattern.compile("(\\d+)",
+                java.util.regex.Pattern.CASE_INSENSITIVE);
+        java.util.regex.Matcher m = p.matcher(MACAlgo);
+        int val = 0;
+
+        if (m.find()) {
+            val = Integer.parseInt(m.group(1));
+        }
+
+        // HmacPBESHA1 should return MAC 20 byte length
+        if ((val == 1) && (lengthToCheck == 20)) {
+            return true;
+        }
+
+        return (val / 8) == lengthToCheck;
+    }
+
+    /**
+     * An utility method to dump a byte array for debug output.
+     *
+     * @param theByteArray the byte array to dump
+     * @return string representation of the theByteArray in Hex.
+     */
+    protected String dumpByteArray(byte[] theByteArray) {
+        StringBuilder buf = new StringBuilder();
+
+        for (byte b : theByteArray) {
+            buf.append(Integer.toHexString(b));
+        }
+
+        return buf.toString();
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/com/sun/crypto/provider/Cipher/PBE/TestCipherPBECons.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,117 @@
+/*
+ * Copyright (c) 2012, 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.
+ */
+
+import java.io.PrintStream;
+import java.security.NoSuchAlgorithmException;
+import java.security.Provider;
+import java.security.Security;
+import javax.crypto.Cipher;
+import javax.crypto.NoSuchPaddingException;
+
+/**
+ * @test
+ * @bug 8041787
+ * @summary Verify that for PBEWithMD5AndDES cipher, only CBC mode and
+ * PKCS#5Padding is allowed
+ * @author Yun Ke
+ * @author Bill Situ
+ * @author Yu-Ching (Valerie) PENG
+ * @run main TestCipherKeyWrapperPBEKey
+ */
+public class TestCipherPBECons {
+
+    private static final String[] PBEAlgorithms = {"pbeWithMD5ANDdes",
+        "PBEWithMD5AndTripleDES"};
+    private static final String[] cipherModes = {"ECb", "cbC", "cFB", "Cfb32",
+        "OfB", "oFb64", "pCbC"};
+    private static final String[] cipherPaddings = {"Pkcs5Padding", "NoPaDDing"};
+
+    public static void main(String[] args) {
+        TestCipherPBECons test = new TestCipherPBECons();
+        Provider sunjce = Security.getProvider("SunJCE");
+
+        if (!test.runAll(sunjce, System.out)) {
+            throw new RuntimeException("One or more tests have failed....");
+        }
+    }
+
+    public boolean runAll(Provider p, PrintStream out) {
+        boolean finalResult = true;
+
+        for (String algorithm : PBEAlgorithms) {
+            for (String mode : cipherModes) {
+                for (String padding : cipherPaddings) {
+                    out.println("Running test with " + algorithm
+                            + "/" + mode + "/" + padding);
+                    try {
+                        if (!runTest(p, algorithm, mode, padding, out)) {
+                            finalResult = false;
+                            out.println("STATUS: Failed");
+                        } else {
+                            out.println("STATUS: Passed");
+                        }
+                    } catch (Exception ex) {
+                        finalResult = false;
+                        ex.printStackTrace(out);
+                        out.println("STATUS:Failed");
+                    }
+                }
+            }
+        }
+
+        return finalResult;
+    }
+
+    public boolean runTest(Provider p, String algo, String mo, String pad,
+            PrintStream out) throws Exception {
+        try {
+            // Initialization
+            Cipher ci = Cipher.getInstance(algo + "/" + mo + "/" + pad, p);
+
+            // No exception thrown, must be of the right mode and right
+            // padding scheme
+            return (mo.equalsIgnoreCase("CBC"))
+                    && (pad.equalsIgnoreCase("PKCS5Padding"));
+        } catch (NoSuchAlgorithmException ex) {
+            if (p.getName().compareTo("SunJCE") == 0) {
+                if (!(mo.equalsIgnoreCase("CBC")
+                        && pad.equalsIgnoreCase("PKCS5Padding"))) {
+                    out.println("NoSuchAlgorithmException is as expected");
+                    return true;
+                }
+            }
+
+            out.println("Caught exception: " + ex.getMessage());
+            throw ex;
+        } catch (NoSuchPaddingException ex) {
+            if (mo.equalsIgnoreCase("CBC")
+                    && pad.equalsIgnoreCase("NoPadding")) {
+                out.println("NoSuchPaddingException is as expected");
+                return true;
+            } else {
+                out.println("Caught unexpected exception: " + ex.getMessage());
+                return false;
+            }
+        }
+    }
+}
--- a/jdk/test/com/sun/jdi/cds/CDSBreakpointTest.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/com/sun/jdi/cds/CDSBreakpointTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -31,6 +31,9 @@
  *          jdk.jartool/sun.tools.jar
  * @library /lib/testlibrary
  * @library ..
+ * @build jdk.testlibrary.*
+ * @build TestScaffold VMConnection TargetListener TargetAdapter
+ * @build CDSJDITest
  * @run compile -g ../BreakpointTest.java
  * @run main CDSBreakpointTest
  */
--- a/jdk/test/com/sun/jdi/cds/CDSDeleteAllBkptsTest.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/com/sun/jdi/cds/CDSDeleteAllBkptsTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -31,6 +31,9 @@
  *          jdk.jartool/sun.tools.jar
  * @library /lib/testlibrary
  * @library ..
+ * @build jdk.testlibrary.*
+ * @build TestScaffold VMConnection TargetListener TargetAdapter
+ * @build CDSJDITest
  * @run compile -g ../DeleteAllBkptsTest.java
  * @run main CDSDeleteAllBkptsTest
  */
--- a/jdk/test/com/sun/jdi/cds/CDSFieldWatchpoints.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/com/sun/jdi/cds/CDSFieldWatchpoints.java	Wed Jul 05 20:42:36 2017 +0200
@@ -31,6 +31,9 @@
  *          jdk.jartool/sun.tools.jar
  * @library /lib/testlibrary
  * @library ..
+ * @build jdk.testlibrary.*
+ * @build TestScaffold VMConnection TargetListener TargetAdapter
+ * @build CDSJDITest
  * @run compile -g ../FieldWatchpoints.java
  * @run main CDSFieldWatchpoints
  */
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/awt/EventDispatchThread/PropertyPermissionOnEDT/PropertyPermissionOnEDT.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,105 @@
+/*
+ * 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.
+ */
+
+import java.awt.Point;
+import java.awt.Robot;
+import java.awt.event.FocusEvent;
+import java.awt.event.FocusListener;
+import java.awt.event.InputEvent;
+import java.awt.event.MouseEvent;
+import java.awt.event.MouseListener;
+
+import javax.swing.JFrame;
+import javax.swing.SwingUtilities;
+
+/**
+ * @test
+ * @bug 8080405
+ * @run main/othervm/policy=java.policy -Djava.security.manager PropertyPermissionOnEDT
+ */
+public final class PropertyPermissionOnEDT {
+
+    public static void main(final String[] args) throws Exception {
+        SwingUtilities.invokeAndWait(PropertyPermissionOnEDT::test);
+
+        JFrame frame = new JFrame();
+        frame.addMouseListener(new MouseListener() {
+            @Override
+            public void mouseClicked(final MouseEvent e) {
+                test();
+            }
+
+            @Override
+            public void mousePressed(MouseEvent e) {
+                test();
+            }
+
+            @Override
+            public void mouseReleased(MouseEvent e) {
+                test();
+            }
+
+            @Override
+            public void mouseEntered(MouseEvent e) {
+                test();
+            }
+
+            @Override
+            public void mouseExited(MouseEvent e) {
+                test();
+            }
+        });
+        frame.addFocusListener(new FocusListener() {
+            @Override
+            public void focusGained(FocusEvent e) {
+                test();
+            }
+
+            @Override
+            public void focusLost(FocusEvent e) {
+                test();
+            }
+        });
+        frame.addMouseWheelListener(e -> test());
+        frame.addWindowStateListener(e -> test());
+
+        frame.setSize(100, 100);
+        frame.setLocationRelativeTo(null);
+        frame.setVisible(true);
+        Robot robot = new Robot();
+        robot.setAutoWaitForIdle(true);
+        robot.setAutoDelay(100);
+        Point loc = frame.getLocationOnScreen();
+        robot.mouseMove(loc.x + frame.getWidth() / 2,
+                        loc.y + frame.getHeight() / 2);
+        robot.mousePress(InputEvent.BUTTON1_MASK);
+        robot.mouseRelease(InputEvent.BUTTON1_MASK);
+        robot.mouseWheel(100);
+        frame.dispose();
+    }
+
+    private static void test() {
+        String property = System.getProperty("os.name");
+        System.out.println("property = " + property);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/awt/EventDispatchThread/PropertyPermissionOnEDT/java.policy	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,4 @@
+grant {
+  permission java.util.PropertyPermission "os.name", "read";
+  permission java.awt.AWTPermission "createRobot";
+};
--- a/jdk/test/java/awt/EventQueue/6980209/bug6980209.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/EventQueue/6980209/bug6980209.java	Wed Jul 05 20:42:36 2017 +0200
@@ -27,18 +27,17 @@
    @author Semyon Sadetsky
   */
 
-import sun.util.logging.PlatformLogger;
-
 import javax.swing.*;
 import java.awt.*;
 import java.awt.event.ActionEvent;
 import java.awt.event.ActionListener;
 import java.awt.event.KeyEvent;
 import java.awt.event.KeyListener;
+import java.util.logging.Logger;
 
 public class bug6980209 implements ActionListener {
-    private final static PlatformLogger log =
-            PlatformLogger.getLogger("java.awt.event.WaitDispatchSupport");
+    private final static Logger log =
+            Logger.getLogger("java.awt.event.WaitDispatchSupport");
     public static final int ATTEMPTS = 100;
     public static final int EVENTS = 5;
 
@@ -52,8 +51,8 @@
     public static void main(String[] args) throws Exception {
         System.out.println(
                 "PLEASE DO NOT TOUCH KEYBOARD AND MOUSE DURING THE TEST RUN!");
-        // log.setLevel(PlatformLogger.Level.FINE);
-        // log.setLevel(PlatformLogger.Level.FINEST);
+        // log.setLevel(java.util.logging.Level.FINE);
+        // log.setLevel(java.util.logging.Level.FINEST);
         try {
             SwingUtilities.invokeAndWait(new Runnable() {
                 public void run() {
--- a/jdk/test/java/awt/FileDialog/8017487/bug8017487.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/FileDialog/8017487/bug8017487.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,6 +25,7 @@
    @bug 8017487
    @summary filechooser in Windows-Libraries folder: columns are mixed up
    @author Semyon Sadetsky
+   @modules java.desktop/sun.awt.shell
    @library /lib/testlibrary
    @build jdk.testlibrary.OSInfo
    @run main bug8017487
--- a/jdk/test/java/awt/Focus/8073453/AWTFocusTransitionTest.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Focus/8073453/AWTFocusTransitionTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -28,13 +28,11 @@
  * @compile AWTFocusTransitionTest.java
  * @run main/othervm AWTFocusTransitionTest
  */
-import sun.awt.SunToolkit;
 
 import java.awt.*;
 import java.awt.event.KeyEvent;
 
 public class AWTFocusTransitionTest {
-    private static SunToolkit toolkit;
     private static Robot robot;
 
     private static Frame frame;
@@ -42,20 +40,19 @@
     private static Button button;
 
     public static void main(String[] args) throws Exception {
-        toolkit = (SunToolkit)Toolkit.getDefaultToolkit();
         robot = new Robot();
         robot.setAutoDelay(50);
 
         try {
             createAndShowGUI();
 
-            toolkit.realSync();
+            robot.waitForIdle();
 
             checkFocusOwner(textField);
 
             robot.keyPress(KeyEvent.VK_TAB);
             robot.keyRelease(KeyEvent.VK_TAB);
-            toolkit.realSync();
+            robot.waitForIdle();
 
             checkFocusOwner(button);
 
@@ -63,7 +60,7 @@
             robot.keyPress(KeyEvent.VK_TAB);
             robot.keyRelease(KeyEvent.VK_TAB);
             robot.keyRelease(KeyEvent.VK_SHIFT);
-            toolkit.realSync();
+            robot.waitForIdle();
 
             checkFocusOwner(textField);
 
@@ -71,7 +68,7 @@
             robot.keyPress(KeyEvent.VK_TAB);
             robot.keyRelease(KeyEvent.VK_TAB);
             robot.keyRelease(KeyEvent.VK_SHIFT);
-            toolkit.realSync();
+            robot.waitForIdle();
 
             checkFocusOwner(button);
         } finally {
--- a/jdk/test/java/awt/Focus/8073453/SwingFocusTransitionTest.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Focus/8073453/SwingFocusTransitionTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -28,14 +28,12 @@
  * @compile SwingFocusTransitionTest.java
  * @run main/othervm SwingFocusTransitionTest
  */
-import sun.awt.SunToolkit;
 
 import javax.swing.*;
 import java.awt.*;
 import java.awt.event.KeyEvent;
 
 public class SwingFocusTransitionTest {
-    private static SunToolkit toolkit;
     private static Robot robot;
 
     private static JFrame frame;
@@ -43,7 +41,6 @@
     private static JButton button;
 
     public static void main(String[] args) throws Exception {
-        toolkit = (SunToolkit)Toolkit.getDefaultToolkit();
         robot = new Robot();
         robot.setAutoDelay(50);
 
@@ -55,13 +52,13 @@
                 }
             });
 
-            toolkit.realSync();
+            robot.waitForIdle();
 
             checkFocusOwner(textField);
 
             robot.keyPress(KeyEvent.VK_TAB);
             robot.keyRelease(KeyEvent.VK_TAB);
-            toolkit.realSync();
+            robot.waitForIdle();
 
             checkFocusOwner(button);
 
@@ -69,7 +66,7 @@
             robot.keyPress(KeyEvent.VK_TAB);
             robot.keyRelease(KeyEvent.VK_TAB);
             robot.keyRelease(KeyEvent.VK_SHIFT);
-            toolkit.realSync();
+            robot.waitForIdle();
 
             checkFocusOwner(textField);
 
@@ -77,7 +74,7 @@
             robot.keyPress(KeyEvent.VK_TAB);
             robot.keyRelease(KeyEvent.VK_TAB);
             robot.keyRelease(KeyEvent.VK_SHIFT);
-            toolkit.realSync();
+            robot.waitForIdle();
 
             checkFocusOwner(button);
         } finally {
--- a/jdk/test/java/awt/Focus/FocusEmbeddedFrameTest/FocusEmbeddedFrameTest.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Focus/FocusEmbeddedFrameTest/FocusEmbeddedFrameTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -26,6 +26,8 @@
   @bug       6516675
   @summary   Tests that EmbeddedFrame can be focused.
   @author    anton.tarasov: area=awt-focus
+  @modules   java.desktop/java.awt.peer
+             java.desktop/sun.awt
   @library   ../../regtesthelpers
   @build     Util UtilInternal
   @run       main FocusEmbeddedFrameTest
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/awt/Frame/NonEDT_GUI_DeadlockTest/NonEDT_GUI_Deadlock.html	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,44 @@
+<html>
+<!--
+ Copyright (c) 2003, 2015, Oracle and/or its affiliates. All rights reserved.
+ DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+
+ This code is free software; you can redistribute it and/or modify it
+ under the terms of the GNU General Public License version 2 only, as
+ published by the Free Software Foundation.
+
+ This code is distributed in the hope that it will be useful, but WITHOUT
+ ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ version 2 for more details (a copy is included in the LICENSE file that
+ accompanied this code).
+
+ You should have received a copy of the GNU General Public License version
+ 2 along with this work; if not, write to the Free Software Foundation,
+ Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+
+ Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ or visit www.oracle.com if you need additional information or have any
+ questions.
+-->
+
+<!--  
+  @test
+  @bug 4828019
+  @summary Frame/Window deadlock
+  @author yan@sparc.spb.su: area=
+  @run applet/timeout=9999 NonEDT_GUI_Deadlock.html
+  -->
+<head>
+<title>  </title>
+</head>
+<body>
+
+<h1>NonEDT_GUI_Deadlock<br>Bug ID: 4828019</h1>
+
+<p> This is an AUTOMATIC test, simply wait for completion </p>
+
+<APPLET CODE="NonEDT_GUI_Deadlock.class" WIDTH=200 HEIGHT=200></APPLET>
+</body>
+</html>
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/awt/Frame/NonEDT_GUI_DeadlockTest/NonEDT_GUI_Deadlock.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,323 @@
+/*
+ * Copyright (c) 2003, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+
+/*
+  test
+  @bug 4828019
+  @summary Frame/Window deadlock
+  @author yan@sparc.spb.su: area=
+  @run applet NonEDT_GUI_Deadlock.html
+*/
+
+// Note there is no @ in front of test above.  This is so that the
+//  harness will not mistake this file as a test file.  It should
+//  only see the html file as a test file. (the harness runs all
+//  valid test files, so it would run this test twice if this file
+//  were valid as well as the html file.)
+// Also, note the area= after Your Name in the author tag.  Here, you
+//  should put which functional area the test falls in.  See the
+//  AWT-core home page -> test areas and/or -> AWT team  for a list of
+//  areas.
+// Note also the 'AutomaticAppletTest.html' in the run tag.  This should
+//  be changed to the name of the test.
+
+
+/**
+ * NonEDT_GUI_Deadlock.java
+ *
+ * summary:
+ */
+
+import java.applet.Applet;
+import java.awt.*;
+import java.awt.event.*;
+import java.net.*;
+import java.io.*;
+
+
+//Automated tests should run as applet tests if possible because they
+// get their environments cleaned up, including AWT threads, any
+// test created threads, and any system resources used by the test
+// such as file descriptors.  (This is normally not a problem as
+// main tests usually run in a separate VM, however on some platforms
+// such as the Mac, separate VMs are not possible and non-applet
+// tests will cause problems).  Also, you don't have to worry about
+// synchronisation stuff in Applet tests they way you do in main
+// tests...
+
+
+public class NonEDT_GUI_Deadlock extends Applet
+{
+    //Declare things used in the test, like buttons and labels here
+    boolean bOK = false;
+    Thread badThread = null;
+
+    public void init()
+    {
+        //Create instructions for the user here, as well as set up
+        // the environment -- set the layout manager, add buttons,
+        // etc.
+
+
+        String[] instructions =
+        {
+            "This is an AUTOMATIC test",
+            "simply wait until it is done"
+        };
+        Sysout.createDialog( );
+        Sysout.printInstructions( instructions );
+
+    }//End  init()
+
+    public void start ()
+    {
+        //Get things going.  Request focus, set size, et cetera
+
+        setSize (200,300);
+        setVisible(true);
+        validate();
+
+        final Frame theFrame = new Frame("Window test");
+        theFrame.setSize(240, 200);
+
+        Thread thKiller = new Thread() {
+           public void run() {
+              try {
+                 Thread.sleep( 9000 );
+              }catch( Exception ex ) {
+              }
+              if( !bOK ) {
+                 // oops,
+                 //Sysout.println("Deadlock!");
+                 Runtime.getRuntime().halt(0);
+              }else{
+                 //Sysout.println("Passed ok.");
+              }
+           }
+        };
+        thKiller.setName("Killer thread");
+        thKiller.start();
+        Window w = new TestWindow(theFrame);
+        theFrame.toBack();
+        theFrame.setVisible(true);
+
+        theFrame.setLayout(new FlowLayout(FlowLayout.CENTER));
+        EventQueue.invokeLater(new Runnable() {
+           public void run() {
+               bOK = true;
+           }
+        });
+
+
+
+    }// start()
+    class TestWindow extends Window implements Runnable {
+
+        TestWindow(Frame f) {
+            super(f);
+
+            //setSize(240, 75);
+            setLocation(0, 75);
+
+            show();
+            toFront();
+
+            badThread = new Thread(this);
+            badThread.setName("Bad Thread");
+            badThread.start();
+
+        }
+
+        public void paint(Graphics g) {
+            g.drawString("Deadlock or no deadlock?",20,80);
+        }
+
+        public void run() {
+
+            long ts = System.currentTimeMillis();
+
+            while (true) {
+                if ((System.currentTimeMillis()-ts)>3000) {
+                    this.setVisible( false );
+                    dispose();
+                    break;
+                }
+
+                toFront();
+                try {
+                    Thread.sleep(80);
+                } catch (Exception e) {
+                }
+            }
+        }
+    }
+
+
+
+    public static void main(String args[]) {
+       NonEDT_GUI_Deadlock imt = new NonEDT_GUI_Deadlock();
+       imt.init();
+       imt.start();
+    }
+
+
+}// class NonEDT_GUI_Deadlock
+
+
+/****************************************************
+ Standard Test Machinery
+ DO NOT modify anything below -- it's a standard
+  chunk of code whose purpose is to make user
+  interaction uniform, and thereby make it simpler
+  to read and understand someone else's test.
+ ****************************************************/
+
+/**
+ This is part of the standard test machinery.
+ It creates a dialog (with the instructions), and is the interface
+  for sending text messages to the user.
+ To print the instructions, send an array of strings to Sysout.createDialog
+  WithInstructions method.  Put one line of instructions per array entry.
+ To display a message for the tester to see, simply call Sysout.println
+  with the string to be displayed.
+ This mimics System.out.println but works within the test harness as well
+  as standalone.
+ */
+
+class Sysout
+{
+    private static TestDialog dialog;
+
+    public static void createDialogWithInstructions( String[] instructions )
+    {
+        dialog = new TestDialog( new Frame(), "Instructions" );
+        dialog.printInstructions( instructions );
+        dialog.setVisible(true);
+        println( "Any messages for the tester will display here." );
+    }
+
+    public static void createDialog( )
+    {
+        dialog = new TestDialog( new Frame(), "Instructions" );
+        String[] defInstr = { "Instructions will appear here. ", "" } ;
+        dialog.printInstructions( defInstr );
+        dialog.setVisible(true);
+        println( "Any messages for the tester will display here." );
+    }
+
+
+    public static void printInstructions( String[] instructions )
+    {
+        dialog.printInstructions( instructions );
+    }
+
+
+    public static void println( String messageIn )
+    {
+        dialog.displayMessage( messageIn );
+    }
+
+}// Sysout  class
+
+/**
+  This is part of the standard test machinery.  It provides a place for the
+   test instructions to be displayed, and a place for interactive messages
+   to the user to be displayed.
+  To have the test instructions displayed, see Sysout.
+  To have a message to the user be displayed, see Sysout.
+  Do not call anything in this dialog directly.
+  */
+class TestDialog extends Dialog
+{
+
+    TextArea instructionsText;
+    TextArea messageText;
+    int maxStringLength = 80;
+
+    //DO NOT call this directly, go through Sysout
+    public TestDialog( Frame frame, String name )
+    {
+        super( frame, name );
+        int scrollBoth = TextArea.SCROLLBARS_BOTH;
+        instructionsText = new TextArea( "", 15, maxStringLength, scrollBoth );
+        add( "North", instructionsText );
+
+        messageText = new TextArea( "", 5, maxStringLength, scrollBoth );
+        add("Center", messageText);
+
+        pack();
+
+        show();
+    }// TestDialog()
+
+    //DO NOT call this directly, go through Sysout
+    public void printInstructions( String[] instructions )
+    {
+        //Clear out any current instructions
+        instructionsText.setText( "" );
+
+        //Go down array of instruction strings
+
+        String printStr, remainingStr;
+        for( int i=0; i < instructions.length; i++ )
+        {
+            //chop up each into pieces maxSringLength long
+            remainingStr = instructions[ i ];
+            while( remainingStr.length() > 0 )
+            {
+                //if longer than max then chop off first max chars to print
+                if( remainingStr.length() >= maxStringLength )
+                {
+                    //Try to chop on a word boundary
+                    int posOfSpace = remainingStr.
+                        lastIndexOf( ' ', maxStringLength - 1 );
+
+                    if( posOfSpace <= 0 ) posOfSpace = maxStringLength - 1;
+
+                    printStr = remainingStr.substring( 0, posOfSpace + 1 );
+                    remainingStr = remainingStr.substring( posOfSpace + 1 );
+                }
+                //else just print
+                else
+                {
+                    printStr = remainingStr;
+                    remainingStr = "";
+                }
+
+                instructionsText.append( printStr + "\n" );
+
+            }// while
+
+        }// for
+
+    }//printInstructions()
+
+    //DO NOT call this directly, go through Sysout
+    public void displayMessage( String messageIn )
+    {
+        messageText.append( messageIn + "\n" );
+        System.out.println(messageIn);
+    }
+
+}// TestDialog  class
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/awt/FullScreen/MultimonFullscreenTest/MultimonDeadlockTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,66 @@
+/*
+ * 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.
+ */
+
+/*
+  @test
+  @bug 8129116
+  @summary Deadlock with multimonitor fullscreen windows.
+  @run main/timeout=20 MultimonDeadlockTest
+ */
+import java.awt.*;
+import java.awt.event.WindowAdapter;
+import java.awt.event.WindowEvent;
+import java.lang.reflect.InvocationTargetException;
+
+public class MultimonDeadlockTest {
+
+    public static void main(String argv[]) {
+        final GraphicsDevice[] devices = GraphicsEnvironment
+                .getLocalGraphicsEnvironment()
+                .getScreenDevices();
+        if (devices.length < 2) {
+            System.out.println("It's a multiscreen test... skipping!");
+            return;
+        }
+
+        Frame frames[] = new Frame[devices.length];
+        try {
+            EventQueue.invokeAndWait(() -> {
+                for (int i = 0; i < devices.length; i++) {
+                    frames[i] = new Frame();
+                    frames[i].setSize(100, 100);
+                    frames[i].setBackground(Color.BLUE);
+                    devices[i].setFullScreenWindow(frames[i]);
+                }
+            });
+            Thread.sleep(5000);
+        } catch (InterruptedException | InvocationTargetException ex) {
+        } finally {
+            for (int i = 0; i < devices.length; i++) {
+                devices[i].setFullScreenWindow(null);
+                frames[i].dispose();
+            }
+        }
+
+    }
+}
--- a/jdk/test/java/awt/JAWT/JAWT.sh	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/JAWT/JAWT.sh	Wed Jul 05 20:42:36 2017 +0200
@@ -129,7 +129,7 @@
 esac
 
 echo "OS-ARCH is" ${SYST}-${ARCH}
-${TESTJAVA}${FS}jre${FS}bin${FS}java -fullversion 2>&1
+${TESTJAVA}${FS}bin${FS}java -fullversion 2>&1
 
 which ${MAKE} >${NULL} 2>&1
 if [ "$?" -ne '0' ]
@@ -156,7 +156,7 @@
 
 cp ${TESTSRC}${FS}${MAKEFILE} .
 
-JAVA=${TESTJAVA}${FS}jre${FS}bin${FS}java
+JAVA=${TESTJAVA}${FS}bin${FS}java
 JAVAC=${TESTJAVA}${FS}bin${FS}javac
 JAVAH=${TESTJAVA}${FS}bin${FS}javah
 
--- a/jdk/test/java/awt/JAWT/Makefile.unix	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/JAWT/Makefile.unix	Wed Jul 05 20:42:36 2017 +0200
@@ -32,7 +32,7 @@
 
 J_INC =		$(TESTJAVA)/include
 INCLUDES =	-I$(J_INC) -I$(J_INC)/$(SYST) -I.
-LIBS =		-L$(TESTJAVA)/jre/lib/$(ARCH) -ljawt -lX11
+LIBS =		-L$(TESTJAVA)/lib/$(ARCH) -ljawt -lX11
 
 all:		$(CLASSES) libmylib.so
 
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JButtonInGlassPaneOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JButtonInGlassPaneOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -34,6 +34,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JButtonInGlassPaneOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JButtonOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JButtonOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -34,6 +34,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JButtonOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JColorChooserOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JColorChooserOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -33,6 +33,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JColorChooserOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JComboBoxOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JComboBoxOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -44,6 +44,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JComboBoxOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JEditorPaneInGlassPaneOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JEditorPaneInGlassPaneOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -35,6 +35,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JEditorPaneInGlassPaneOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JEditorPaneOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JEditorPaneOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -33,6 +33,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JEditorPaneOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JGlassPaneInternalFrameOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JGlassPaneInternalFrameOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -46,6 +46,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JGlassPaneInternalFrameOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JGlassPaneMoveOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JGlassPaneMoveOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -47,6 +47,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JGlassPaneMoveOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JInternalFrameMoveOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JInternalFrameMoveOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -43,6 +43,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JInternalFrameMoveOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JInternalFrameOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JInternalFrameOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -42,6 +42,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JInternalFrameOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JLabelInGlassPaneOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JLabelInGlassPaneOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -35,6 +35,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JLabelInGlassPaneOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JLabelOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JLabelOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -34,6 +34,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JLabelOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JListInGlassPaneOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JListInGlassPaneOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -34,6 +34,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JListInGlassPaneOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JListOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JListOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -33,6 +33,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JListOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JMenuBarOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JMenuBarOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -49,6 +49,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JMenuBarOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JPanelInGlassPaneOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JPanelInGlassPaneOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -35,6 +35,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JPanelInGlassPaneOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JPanelOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JPanelOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -34,6 +34,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JPanelOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JPopupMenuOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JPopupMenuOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -46,6 +46,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JPopupMenuOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JProgressBarInGlassPaneOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JProgressBarInGlassPaneOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -35,6 +35,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JProgressBarInGlassPaneOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JProgressBarOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JProgressBarOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -34,6 +34,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JProgressBarOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JScrollBarInGlassPaneOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JScrollBarInGlassPaneOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -38,6 +38,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JScrollBarInGlassPaneOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JScrollBarOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JScrollBarOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -37,6 +37,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JScrollBarOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JScrollPaneOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JScrollPaneOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -44,6 +44,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JScrollPaneOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JSliderInGlassPaneOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JSliderInGlassPaneOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -35,6 +35,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JSliderInGlassPaneOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JSliderOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JSliderOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -34,6 +34,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JSliderOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JSpinnerInGlassPaneOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JSpinnerInGlassPaneOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -37,6 +37,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JSpinnerInGlassPaneOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JSpinnerOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JSpinnerOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -36,6 +36,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JSpinnerOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JSplitPaneOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JSplitPaneOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -40,7 +40,8 @@
 
 /**
  * AWT/Swing overlapping test for {@link javax.swing.JSplitPane } component.
- * <p>This test creates puts heavyweight and lightweight components into different panels and test if splitter image and components itself are drawn correctly.
+ * <p>This test puts heavyweight and lightweight components into different
+ * panels and test if splitter image and components itself are drawn correctly.
  * <p>See base class for test info.
  */
 /*
@@ -50,6 +51,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JSplitPaneOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JTableInGlassPaneOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JTableInGlassPaneOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -37,6 +37,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JTableInGlassPaneOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JTableOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JTableOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -33,6 +33,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JTableOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JTextAreaInGlassPaneOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JTextAreaInGlassPaneOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -35,6 +35,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JTextAreaInGlassPaneOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JTextAreaOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JTextAreaOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -34,6 +34,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JTextAreaOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JTextFieldInGlassPaneOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JTextFieldInGlassPaneOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -35,6 +35,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JTextFieldInGlassPaneOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JTextFieldOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JTextFieldOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -34,6 +34,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JTextFieldOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JToggleButtonInGlassPaneOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JToggleButtonInGlassPaneOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -34,6 +34,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JToggleButtonInGlassPaneOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/JToggleButtonOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/JToggleButtonOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -33,6 +33,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main JToggleButtonOverlapping
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/MixingFrameResizing.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/MixingFrameResizing.java	Wed Jul 05 20:42:36 2017 +0200
@@ -43,6 +43,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main MixingFrameResizing
  */
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/OpaqueOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/OpaqueOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -47,6 +47,7 @@
 @summary Opaque overlapping test for each AWT component
 @library ../../regtesthelpers
 @modules java.desktop/com.sun.awt
+         java.desktop/java.awt.peer
          java.desktop/sun.awt
 @build Util
 @run main OpaqueOverlapping
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/OpaqueOverlappingChoice.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/OpaqueOverlappingChoice.java	Wed Jul 05 20:42:36 2017 +0200
@@ -33,6 +33,7 @@
 @summary Opaque overlapping test for Choice AWT component
 @library ../../regtesthelpers
 @modules java.desktop/com.sun.awt
+         java.desktop/java.awt.peer
          java.desktop/sun.awt
 @build Util
 @run main OpaqueOverlappingChoice
--- a/jdk/test/java/awt/Mixing/AWT_Mixing/ViewportOverlapping.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/Mixing/AWT_Mixing/ViewportOverlapping.java	Wed Jul 05 20:42:36 2017 +0200
@@ -52,6 +52,7 @@
 @author sergey.grinev@oracle.com: area=awt.mixing
 @library ../../regtesthelpers
 @modules java.desktop/sun.awt
+         java.desktop/java.awt.peer
 @build Util
 @run main ViewportOverlapping
  */
--- a/jdk/test/java/awt/TextArea/TextAreaCaretVisibilityTest/bug7129742.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/TextArea/TextAreaCaretVisibilityTest/bug7129742.java	Wed Jul 05 20:42:36 2017 +0200
@@ -29,6 +29,8 @@
 /* @test
  * @bug 7129742
  * @summary Focus in non-editable TextArea is not shown on Linux.
+ * @modules java.desktop/sun.awt
+ *          java.desktop/java.awt.peer
  * @author Sean Chou
  */
 
--- a/jdk/test/java/awt/datatransfer/DragImage/MultiResolutionDragImageTest.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/datatransfer/DragImage/MultiResolutionDragImageTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -36,6 +36,8 @@
  * @author Hendrik Schreiber
  * @summary [macosx] Drag image of TransferHandler does not honor
  * MultiResolutionImage
+ * @modules java.desktop/sun.awt.image
+ *          java.desktop/sun.java2d
  * @run main MultiResolutionDragImageTest TEST_DRAG
  */
 public class MultiResolutionDragImageTest {
@@ -169,4 +171,4 @@
         graphics.dispose();
         return image;
     }
-}
\ No newline at end of file
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/awt/font/GlyphVector/TestLayoutFlags.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,209 @@
+/*
+ * Copyright (c) 2004, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+
+/* @test
+   @bug 4328745 5090704
+   @summary exercise getLayoutFlags, getGlyphCharIndex, getGlyphCharIndices
+ */
+
+import java.awt.*;
+import java.awt.event.*;
+import java.awt.font.*;
+import java.awt.geom.*;
+
+public class TestLayoutFlags {
+
+    static public void main(String[] args) {
+        new TestLayoutFlags().runTest();
+    }
+
+    void runTest() {
+
+        Font font = new Font("Lucida Sans", Font.PLAIN, 24);
+
+        String latin1 = "This is a latin1 string"; // none
+        String hebrew = "\u05d0\u05d1\u05d2\u05d3"; // rtl
+        String arabic = "\u0646\u0644\u0622\u0646"; // rtl + mc/g
+        String hindi = "\u0939\u093f\u0923\u094d\u0921\u0940"; // ltr + reorder
+        //      String tamil = "\u0b9c\u0bcb"; // ltr + mg/c + split
+
+        FontRenderContext frc = new FontRenderContext(null, true, true);
+
+        // get glyph char indices needs to initializes layoutFlags before use (5090704)
+        {
+          GlyphVector gv = font.createGlyphVector(frc, "abcde");
+          int ix = gv.getGlyphCharIndex(0);
+          if (ix != 0) {
+            throw new Error("glyph 0 incorrectly mapped to char " + ix);
+          }
+          int[] ixs = gv.getGlyphCharIndices(0, gv.getNumGlyphs(), null);
+          for (int i = 0; i < ixs.length; ++i) {
+            if (ixs[i] != i) {
+              throw new Error("glyph " + i + " incorrectly mapped to char " + ixs[i]);
+            }
+          }
+        }
+
+        GlyphVector latinGV = makeGlyphVector("Lucida Sans", frc, latin1, false, 1 /* ScriptRun.LATIN */);
+        GlyphVector hebrewGV = makeGlyphVector("Lucida Sans", frc, hebrew, true, 5 /* ScriptRun.HEBREW */);
+        GlyphVector arabicGV = makeGlyphVector("Lucida Sans", frc, arabic, true, 6 /* ScriptRun.ARABIC */);
+        GlyphVector hindiGV = makeGlyphVector("Lucida Sans", frc, hindi, false, 7 /* ScriptRun.DEVANAGARI */);
+        //      GlyphVector tamilGV = makeGlyphVector("Devanagari MT for IBM", frc, tamil, false, 12 /* ScriptRun.TAMIL */);
+
+        GlyphVector latinPos = font.createGlyphVector(frc, latin1);
+        Point2D pt = latinPos.getGlyphPosition(0);
+        pt.setLocation(pt.getX(), pt.getY() + 1.0);
+        latinPos.setGlyphPosition(0, pt);
+
+        GlyphVector latinTrans = font.createGlyphVector(frc, latin1);
+        latinTrans.setGlyphTransform(0, AffineTransform.getRotateInstance(.15));
+
+        test("latin", latinGV, GlyphVector.FLAG_HAS_POSITION_ADJUSTMENTS);
+        test("hebrew", hebrewGV, GlyphVector.FLAG_RUN_RTL |
+             GlyphVector.FLAG_HAS_POSITION_ADJUSTMENTS);
+        test("arabic", arabicGV, GlyphVector.FLAG_RUN_RTL |
+             GlyphVector.FLAG_HAS_POSITION_ADJUSTMENTS);
+        test("hindi", hindiGV, GlyphVector.FLAG_COMPLEX_GLYPHS |
+             GlyphVector.FLAG_HAS_POSITION_ADJUSTMENTS);
+        //      test("tamil", tamilGV, GlyphVector.FLAG_COMPLEX_GLYPHS);
+        test("pos", latinPos, GlyphVector.FLAG_HAS_POSITION_ADJUSTMENTS);
+        test("trans", latinTrans, GlyphVector.FLAG_HAS_TRANSFORMS);
+    }
+
+    GlyphVector makeGlyphVector(String fontname, FontRenderContext frc, String text, boolean rtl, int script) {
+        Font font = new Font(fontname, Font.PLAIN, 14);
+        System.out.println("asking for " + fontname + " and got " + font.getFontName());
+        int flags = rtl ? 1 : 0;
+        return font.layoutGlyphVector(frc, text.toCharArray(), 0, text.length(), flags);
+    }
+
+    void test(String name, GlyphVector gv, int expectedFlags) {
+        expectedFlags &= gv.FLAG_MASK;
+        int computedFlags = computeFlags(gv) & gv.FLAG_MASK;
+        int actualFlags = gv.getLayoutFlags() & gv.FLAG_MASK;
+
+        System.out.println("\n*** " + name + " ***");
+        System.out.println(" test flags");
+        System.out.print("expected ");
+        printFlags(expectedFlags);
+        System.out.print("computed ");
+        printFlags(computedFlags);
+        System.out.print("  actual ");
+        printFlags(actualFlags);
+
+        if (expectedFlags != actualFlags) {
+            throw new Error("layout flags in test: " + name +
+                            " expected: " + Integer.toHexString(expectedFlags) +
+                            " but got: " + Integer.toHexString(actualFlags));
+        }
+    }
+
+    static public void printFlags(int flags) {
+        System.out.print("flags:");
+        if ((flags & GlyphVector.FLAG_HAS_POSITION_ADJUSTMENTS) != 0) {
+            System.out.print(" pos");
+        }
+        if ((flags & GlyphVector.FLAG_HAS_TRANSFORMS) != 0) {
+            System.out.print(" trans");
+        }
+        if ((flags & GlyphVector.FLAG_RUN_RTL) != 0) {
+            System.out.print(" rtl");
+        }
+        if ((flags & GlyphVector.FLAG_COMPLEX_GLYPHS) != 0) {
+            System.out.print(" complex");
+        }
+        if ((flags & GlyphVector.FLAG_MASK) == 0) {
+            System.out.print(" none");
+        }
+        System.out.println();
+    }
+
+    int computeFlags(GlyphVector gv) {
+        validateCharIndexMethods(gv);
+
+        int result = 0;
+        if (glyphsAreRTL(gv)) {
+            result |= GlyphVector.FLAG_RUN_RTL;
+        }
+        if (hasComplexGlyphs(gv)) {
+            result |= GlyphVector.FLAG_COMPLEX_GLYPHS;
+        }
+
+        return result;
+    }
+
+    /**
+     * throw an exception if getGlyphCharIndices returns a different result than
+     * you get from iterating through getGlyphCharIndex one at a time.
+     */
+    void validateCharIndexMethods(GlyphVector gv) {
+        int[] indices = gv.getGlyphCharIndices(0, gv.getNumGlyphs(), null);
+        for (int i = 0; i < gv.getNumGlyphs(); ++i) {
+            if (gv.getGlyphCharIndex(i) != indices[i]) {
+                throw new Error("glyph index mismatch at " + i);
+            }
+        }
+    }
+
+    /**
+     * Return true if the glyph indices are pure ltr
+     */
+    boolean glyphsAreLTR(GlyphVector gv) {
+        int[] indices = gv.getGlyphCharIndices(0, gv.getNumGlyphs(), null);
+        for (int i = 0; i < indices.length; ++i) {
+            if (indices[i] != i) {
+                return false;
+            }
+        }
+        return true;
+    }
+
+    /**
+     * Return true if the glyph indices are pure rtl
+     */
+    boolean glyphsAreRTL(GlyphVector gv) {
+        int[] indices = gv.getGlyphCharIndices(0, gv.getNumGlyphs(), null);
+        for (int i = 0; i < indices.length; ++i) {
+            if (indices[i] != indices.length - i - 1) {
+                return false;
+            }
+        }
+        return true;
+    }
+
+    /**
+     * Return true if there is a local reordering (the run is not ltr or rtl).
+     * !!! We can't have mixed bidi runs in the glyphs.
+     */
+    boolean hasComplexGlyphs(GlyphVector gv) {
+        return !glyphsAreLTR(gv) && !glyphsAreRTL(gv);
+    }
+}
+
+/*
+rect getPixelBounds(frc, x, y)
+rect getGlyphPixelBounds(frc, int, x, y)
+getGlyphOutline(int index, x, y)
+getGlyphInfo()
+*/
--- a/jdk/test/java/awt/font/NumericShaper/ShapingTest.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/font/NumericShaper/ShapingTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2010, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2010, 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
@@ -23,7 +23,7 @@
 
 /*
  * @test
- * @bug 6842557 6943963 6959267
+ * @bug 6842557 6943963 6959267 8032446
  * @summary confirm that shaping works as expected. (Mainly for new characters which were added in Unicode 5 and 6)
  * used where appropriate.
  */
@@ -40,6 +40,7 @@
         test6842557();
         test6943963();
         test6903266();
+        test8032446();
 
         if (err) {
             throw new RuntimeException("shape() returned unexpected value.");
@@ -138,6 +139,18 @@
         checkResult("Range.MEETEI_MAYEK", ns, given, expected);
     }
 
+    private static void test8032446() {
+        NumericShaper ns = getContextualShaper(EnumSet.of(Range.SINHALA));
+        String given = "\u0d85 012";
+        String expected = "\u0d85 \u0de6\u0de7\u0de8";
+        checkResult("Range.SINHALA", ns, given, expected);
+
+        ns = getContextualShaper(EnumSet.of(Range.MYANMAR_TAI_LAING));
+        given = "\ua9e2 012";
+        expected = "\ua9e2 \ua9f0\ua9f1\ua9f2";
+        checkResult("Range.MYANMAR_TAI_LAING", ns, given, expected);
+    }
+
     private static void checkResult(String ranges, NumericShaper ns,
                                     String given, String expected) {
         char[] text = given.toCharArray();
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/awt/font/Underline/UnderlineTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,160 @@
+/*
+ * Copyright (c) 2006, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+
+/**
+ * @test
+ * @bug 6216010
+ * @summary check to see that underline thickness scales.
+ * @run main UnderlineTest
+ */
+
+import java.awt.Color;
+import java.awt.Container;
+import java.awt.Dimension;
+import java.awt.Font;
+import java.awt.Graphics;
+import java.awt.Graphics2D;
+import java.awt.GridLayout;
+import java.awt.font.FontRenderContext;
+import java.awt.font.LineMetrics;
+import java.awt.font.TextAttribute;
+import java.awt.font.TextLayout;
+import java.awt.geom.AffineTransform;
+import java.util.HashMap;
+import javax.swing.JComponent;
+import javax.swing.JFrame;
+import javax.swing.JScrollPane;
+
+public class UnderlineTest {
+    static class FontsPanel extends Container {
+        FontsPanel(Font[] fonts) {
+            setLayout(new GridLayout(0, 1));
+            for (int i = 0; i < fonts.length; ++i) {
+              add(new FontPanel(fonts[i]));
+            }
+        }
+    }
+
+    static String fps = "Stellar glyphs";
+    static Dimension fpd = new Dimension(600, 120);
+    static class FontPanel extends JComponent {
+        Font f;
+        FontPanel(Font f) {
+            this.f = f;
+            setPreferredSize(fpd);
+            setMinimumSize(fpd);
+            setMaximumSize(fpd);
+            setSize(fpd);
+        }
+
+        public void paintComponent(Graphics g) {
+            g.setColor(Color.WHITE);
+            g.fillRect(0, 0, fpd.width, fpd.height);
+
+            g.setColor(Color.RED);
+            FontRenderContext frc = ((Graphics2D)g).getFontRenderContext();
+            LineMetrics lm = f.getLineMetrics(fps, frc);
+            int h = (int)(fpd.height - 20 - lm.getAscent());
+            g.drawLine(20, h, fpd.width - 20, h);
+            h = fpd.height - 20;
+            g.drawLine(20, h, fpd.width - 20, h);
+            h = (int)(fpd.height - 20 + lm.getDescent());
+            g.drawLine(20, h, fpd.width - 20, h);
+
+            g.setColor(Color.BLACK);
+            g.setFont(f);
+            g.drawString(fps, 50, fpd.height - 20);
+        }
+    }
+
+    public static void main(String args[]) {
+        String fontName = "Lucida Sans";
+        if (args.length > 0) {
+            fontName = args[0];
+        }
+        FontRenderContext frc = new FontRenderContext(null, false, false);
+        FontRenderContext frc2 = new FontRenderContext(AffineTransform.getScaleInstance(1.5, 1.5), false, false);
+
+        Font font0 = new Font(fontName, 0, 20);
+        HashMap map = new HashMap();
+        map.put(TextAttribute.UNDERLINE, TextAttribute.UNDERLINE_ON);
+        map.put(TextAttribute.STRIKETHROUGH, TextAttribute.STRIKETHROUGH_ON);
+        Font font = font0.deriveFont(map);
+
+        System.out.println("Using font: " + font);
+
+        double rot = -Math.PI/4;
+        AffineTransform scrtx = AffineTransform.getRotateInstance(rot);
+        scrtx.scale(1, 2);
+
+        Font[] fonts = {
+            font.deriveFont(1f),
+            font.deriveFont(20f),
+            font.deriveFont(40f),
+            font.deriveFont(80f),
+            font.deriveFont(AffineTransform.getRotateInstance(rot)),
+            font.deriveFont(AffineTransform.getScaleInstance(1, 2)),
+            font.deriveFont(AffineTransform.getScaleInstance(2, 4)),
+            font.deriveFont(scrtx),
+        };
+
+        LineMetrics[] metrics = new LineMetrics[fonts.length * 2];
+        for (int i = 0; i < metrics.length; ++i) {
+            Font f = fonts[i % fonts.length];
+            FontRenderContext frcx = i < fonts.length ? frc : frc2;
+            metrics[i] = f.getLineMetrics("X", frcx);
+      //       dumpMetrics("Metrics for " + f.getSize2D() + " pt. font,\n  tx: " +
+      //       f.getTransform() + ",\n   frctx: " + frcx.getTransform(), metrics[i]);
+        }
+
+        // test for linear scale
+        // this seems to work, might need to get fancy to deal with last-significant-bit issues?
+        double ds1 = metrics[2].getStrikethroughOffset() - metrics[1].getStrikethroughOffset();
+        double du1 = metrics[2].getUnderlineThickness() - metrics[1].getUnderlineThickness();
+        double ds2 = metrics[3].getStrikethroughOffset() - metrics[2].getStrikethroughOffset();
+        double du2 = metrics[3].getUnderlineThickness() - metrics[2].getUnderlineThickness();
+        if (ds2 != ds1 * 2 || du2 != du1 * 2) {
+            throw new IllegalStateException("non-linear scale: " + ds1 + " / " + ds2 + ", " +
+                                            du1 + " / " + du2);
+        }
+
+        JFrame jf = new JFrame("Fonts");
+        jf.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
+        jf.add(new JScrollPane(new FontsPanel(fonts)));
+        jf.pack();
+        jf.setVisible(true);
+    }
+
+    static void dumpMetrics(String header, LineMetrics lm) {
+        if (header != null) {
+            System.out.println(header);
+        }
+        System.out.println("asc: " + lm.getAscent());
+        System.out.println("dsc: " + lm.getDescent());
+        System.out.println("ulo: " + lm.getUnderlineOffset());
+        System.out.println("ult: " + lm.getUnderlineThickness());
+        System.out.println("sto: " + lm.getStrikethroughOffset());
+        System.out.println("stt: " + lm.getStrikethroughThickness());
+    }
+}
--- a/jdk/test/java/awt/grab/EmbeddedFrameTest1/EmbeddedFrameTest1.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/grab/EmbeddedFrameTest1/EmbeddedFrameTest1.java	Wed Jul 05 20:42:36 2017 +0200
@@ -26,6 +26,8 @@
   @bug 6359129
   @summary REGRESSION: Popup menus dont respond to selections when extend outside Applet
   @author oleg.sukhodolsky area=awt.grab
+  @modules java.desktop/java.awt.peer
+           java.desktop/sun.awt
   @library ../../regtesthelpers
   @build Util UtilInternal
   @run main EmbeddedFrameTest1
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/awt/image/VolatileImage/BitmaskVolatileImage.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,93 @@
+/*
+ * 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.
+ */
+
+import java.awt.AlphaComposite;
+import java.awt.Color;
+import java.awt.Graphics2D;
+import java.awt.GraphicsConfiguration;
+import java.awt.GraphicsEnvironment;
+import java.awt.Image;
+import java.awt.image.BufferedImage;
+import java.awt.image.VolatileImage;
+
+import static java.awt.Transparency.BITMASK;
+
+/**
+ * @test
+ * @bug 7188942
+ * @summary We should get correct volatile image, when we use BITMASK
+ *          transparency
+ */
+public final class BitmaskVolatileImage {
+
+    public static final int S = 8;
+
+    public static void main(final String[] args) {
+        GraphicsConfiguration gc =
+                GraphicsEnvironment.getLocalGraphicsEnvironment()
+                        .getDefaultScreenDevice().getDefaultConfiguration();
+        VolatileImage vi = gc.createCompatibleVolatileImage(S, S, BITMASK);
+        BufferedImage ci = gc.createCompatibleImage(S, S, BITMASK);
+
+        int attempt = 0;
+        do {
+            if (++attempt > 10) {
+                throw new RuntimeException("Too many attempts: " + attempt);
+            }
+            vi.validate(gc);
+            test(vi, ci, gc);
+        } while (vi.contentsLost());
+    }
+
+    private static void test(VolatileImage vi, BufferedImage ci, GraphicsConfiguration gc) {
+        for (int r = 0; r <= 255; ++r) {
+            for (int a = 0; a <= 255; ++a) {
+                fill(vi, new Color(r, 0, 0, a));
+                fill(ci, new Color(r, 0, 0, a));
+                validate(ci, vi.getSnapshot());
+            }
+        }
+    }
+
+    private static void fill(Image image, Color color) {
+        Graphics2D g2d = (Graphics2D) image.getGraphics();
+        g2d.setColor(color);
+        g2d.setComposite(AlphaComposite.Src);
+        g2d.fillRect(0, 0, S, S);
+        g2d.dispose();
+    }
+
+    private static void validate(BufferedImage ci, BufferedImage snapshot) {
+        for (int y = 0; y < ci.getHeight(); y++) {
+            for (int x = 0; x < ci.getWidth(); x++) {
+                int ci_rgb = ci.getRGB(x, y);
+                int vi_rgb = snapshot.getRGB(x, y);
+                if (ci_rgb != vi_rgb) {
+                    System.err.println("Exp:" + Integer.toHexString(ci_rgb));
+                    System.err.println("Actual:" + Integer.toHexString(vi_rgb));
+                    throw new RuntimeException("Colors mismatch!");
+                }
+            }
+        }
+    }
+}
--- a/jdk/test/java/awt/xembed/server/TestXEmbedServer.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/awt/xembed/server/TestXEmbedServer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -27,6 +27,8 @@
 import java.io.*;
 import java.util.logging.*;
 import sun.awt.WindowIDProvider;
+import sun.awt.AWTAccessor;
+import sun.awt.AWTAccessor.ComponentAccessor;
 import java.awt.dnd.*;
 import java.awt.datatransfer.*;
 
@@ -182,7 +184,8 @@
         client.setBackground(new Color(30, 220, 40));
         clientCont.add(client);
         clientCont.validate();
-        WindowIDProvider pid = (WindowIDProvider)client.getPeer();
+        final ComponentAccessor acc = AWTAccessor.getComponentAccessor();
+        WindowIDProvider pid = (WindowIDProvider)acc.getPeer(client);
         log.fine("Added XEmbed server(Canvas) with X window ID " + pid.getWindow());
         Rectangle toFocusBounds = toFocus.getBounds();
         toFocusBounds.setLocation(toFocus.getLocationOnScreen());
--- a/jdk/test/java/lang/Character/CheckProp.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/lang/Character/CheckProp.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2011, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011, 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
@@ -24,7 +24,7 @@
 
 /**
  * @test
- * @bug 7037261 7070436 7198195
+ * @bug 7037261 7070436 7198195 8032446
  * @summary  Check j.l.Character.isLowerCase/isUppercase/isAlphabetic/isIdeographic
  */
 
--- a/jdk/test/java/lang/Character/CheckScript.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/lang/Character/CheckScript.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,6 +1,5 @@
-
 /*
- * Copyright (c) 2010, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2010, 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
@@ -24,7 +23,7 @@
 
 /**
  * @test
- * @bug 6945564 6959267 7033561 7070436 7198195
+ * @bug 6945564 6959267 7033561 7070436 7198195 8032446
  * @summary  Check that the j.l.Character.UnicodeScript
  */
 
--- a/jdk/test/java/lang/Character/PropList.txt	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/lang/Character/PropList.txt	Wed Jul 05 20:42:36 2017 +0200
@@ -1,8 +1,8 @@
-# PropList-6.2.0.txt
-# Date: 2012-05-23, 20:34:59 GMT [MD]
+# PropList-7.0.0.txt
+# Date: 2014-02-19, 15:51:26 GMT [MD]
 #
 # Unicode Character Database
-# Copyright (c) 1991-2012 Unicode, Inc.
+# Copyright (c) 1991-2014 Unicode, Inc.
 # For terms of use, see http://www.unicode.org/terms_of_use.html
 # For documentation, see http://www.unicode.org/reports/tr44/
 
@@ -13,7 +13,6 @@
 0085          ; White_Space # Cc       <control-0085>
 00A0          ; White_Space # Zs       NO-BREAK SPACE
 1680          ; White_Space # Zs       OGHAM SPACE MARK
-180E          ; White_Space # Zs       MONGOLIAN VOWEL SEPARATOR
 2000..200A    ; White_Space # Zs  [11] EN QUAD..HAIR SPACE
 2028          ; White_Space # Zl       LINE SEPARATOR
 2029          ; White_Space # Zp       PARAGRAPH SEPARATOR
@@ -21,14 +20,16 @@
 205F          ; White_Space # Zs       MEDIUM MATHEMATICAL SPACE
 3000          ; White_Space # Zs       IDEOGRAPHIC SPACE
 
-# Total code points: 26
+# Total code points: 25
 
 # ================================================
 
+061C          ; Bidi_Control # Cf       ARABIC LETTER MARK
 200E..200F    ; Bidi_Control # Cf   [2] LEFT-TO-RIGHT MARK..RIGHT-TO-LEFT MARK
 202A..202E    ; Bidi_Control # Cf   [5] LEFT-TO-RIGHT EMBEDDING..RIGHT-TO-LEFT OVERRIDE
+2066..2069    ; Bidi_Control # Cf   [4] LEFT-TO-RIGHT ISOLATE..POP DIRECTIONAL ISOLATE
 
-# Total code points: 7
+# Total code points: 12
 
 # ================================================
 
@@ -51,6 +52,7 @@
 2E17          ; Dash # Pd       DOUBLE OBLIQUE HYPHEN
 2E1A          ; Dash # Pd       HYPHEN WITH DIAERESIS
 2E3A..2E3B    ; Dash # Pd   [2] TWO-EM DASH..THREE-EM DASH
+2E40          ; Dash # Pd       DOUBLE HYPHEN
 301C          ; Dash # Pd       WAVE DASH
 3030          ; Dash # Pd       WAVY DASH
 30A0          ; Dash # Pd       KATAKANA-HIRAGANA DOUBLE HYPHEN
@@ -59,7 +61,7 @@
 FE63          ; Dash # Pd       SMALL HYPHEN-MINUS
 FF0D          ; Dash # Pd       FULLWIDTH HYPHEN-MINUS
 
-# Total code points: 27
+# Total code points: 28
 
 # ================================================
 
@@ -91,6 +93,7 @@
 201F          ; Quotation_Mark # Pi       DOUBLE HIGH-REVERSED-9 QUOTATION MARK
 2039          ; Quotation_Mark # Pi       SINGLE LEFT-POINTING ANGLE QUOTATION MARK
 203A          ; Quotation_Mark # Pf       SINGLE RIGHT-POINTING ANGLE QUOTATION MARK
+2E42          ; Quotation_Mark # Ps       DOUBLE LOW-REVERSED-9 QUOTATION MARK
 300C          ; Quotation_Mark # Ps       LEFT CORNER BRACKET
 300D          ; Quotation_Mark # Pe       RIGHT CORNER BRACKET
 300E          ; Quotation_Mark # Ps       LEFT WHITE CORNER BRACKET
@@ -106,7 +109,7 @@
 FF62          ; Quotation_Mark # Ps       HALFWIDTH LEFT CORNER BRACKET
 FF63          ; Quotation_Mark # Pe       HALFWIDTH RIGHT CORNER BRACKET
 
-# Total code points: 29
+# Total code points: 30
 
 # ================================================
 
@@ -136,6 +139,7 @@
 1361..1368    ; Terminal_Punctuation # Po   [8] ETHIOPIC WORDSPACE..ETHIOPIC PARAGRAPH SEPARATOR
 166D..166E    ; Terminal_Punctuation # Po   [2] CANADIAN SYLLABICS CHI SIGN..CANADIAN SYLLABICS FULL STOP
 16EB..16ED    ; Terminal_Punctuation # Po   [3] RUNIC SINGLE PUNCTUATION..RUNIC CROSS PUNCTUATION
+1735..1736    ; Terminal_Punctuation # Po   [2] PHILIPPINE SINGLE PUNCTUATION..PHILIPPINE DOUBLE PUNCTUATION
 17D4..17D6    ; Terminal_Punctuation # Po   [3] KHMER SIGN KHAN..KHMER SIGN CAMNUC PII KUUH
 17DA          ; Terminal_Punctuation # Po       KHMER SIGN KOOMUUT
 1802..1805    ; Terminal_Punctuation # Po   [4] MONGOLIAN COMMA..MONGOLIAN FOUR DOTS
@@ -149,6 +153,8 @@
 203C..203D    ; Terminal_Punctuation # Po   [2] DOUBLE EXCLAMATION MARK..INTERROBANG
 2047..2049    ; Terminal_Punctuation # Po   [3] DOUBLE QUESTION MARK..EXCLAMATION QUESTION MARK
 2E2E          ; Terminal_Punctuation # Po       REVERSED QUESTION MARK
+2E3C          ; Terminal_Punctuation # Po       STENOGRAPHIC FULL STOP
+2E41          ; Terminal_Punctuation # Po       REVERSED COMMA
 3001..3002    ; Terminal_Punctuation # Po   [2] IDEOGRAPHIC COMMA..IDEOGRAPHIC FULL STOP
 A4FE..A4FF    ; Terminal_Punctuation # Po   [2] LISU PUNCTUATION COMMA..LISU PUNCTUATION FULL STOP
 A60D..A60F    ; Terminal_Punctuation # Po   [3] VAI COMMA..VAI QUESTION MARK
@@ -174,14 +180,27 @@
 103D0         ; Terminal_Punctuation # Po       OLD PERSIAN WORD DIVIDER
 10857         ; Terminal_Punctuation # Po       IMPERIAL ARAMAIC SECTION SIGN
 1091F         ; Terminal_Punctuation # Po       PHOENICIAN WORD SEPARATOR
+10A56..10A57  ; Terminal_Punctuation # Po   [2] KHAROSHTHI PUNCTUATION DANDA..KHAROSHTHI PUNCTUATION DOUBLE DANDA
+10AF0..10AF5  ; Terminal_Punctuation # Po   [6] MANICHAEAN PUNCTUATION STAR..MANICHAEAN PUNCTUATION TWO DOTS
 10B3A..10B3F  ; Terminal_Punctuation # Po   [6] TINY TWO DOTS OVER ONE DOT PUNCTUATION..LARGE ONE RING OVER TWO RINGS PUNCTUATION
+10B99..10B9C  ; Terminal_Punctuation # Po   [4] PSALTER PAHLAVI SECTION MARK..PSALTER PAHLAVI FOUR DOTS WITH DOT
 11047..1104D  ; Terminal_Punctuation # Po   [7] BRAHMI DANDA..BRAHMI PUNCTUATION LOTUS
 110BE..110C1  ; Terminal_Punctuation # Po   [4] KAITHI SECTION MARK..KAITHI DOUBLE DANDA
 11141..11143  ; Terminal_Punctuation # Po   [3] CHAKMA DANDA..CHAKMA QUESTION MARK
 111C5..111C6  ; Terminal_Punctuation # Po   [2] SHARADA DANDA..SHARADA DOUBLE DANDA
-12470..12473  ; Terminal_Punctuation # Po   [4] CUNEIFORM PUNCTUATION SIGN OLD ASSYRIAN WORD DIVIDER..CUNEIFORM PUNCTUATION SIGN DIAGONAL TRICOLON
+111CD         ; Terminal_Punctuation # Po       SHARADA SUTRA MARK
+11238..1123C  ; Terminal_Punctuation # Po   [5] KHOJKI DANDA..KHOJKI DOUBLE SECTION MARK
+115C2..115C5  ; Terminal_Punctuation # Po   [4] SIDDHAM DANDA..SIDDHAM SEPARATOR BAR
+115C9         ; Terminal_Punctuation # Po       SIDDHAM END OF TEXT MARK
+11641..11642  ; Terminal_Punctuation # Po   [2] MODI DANDA..MODI DOUBLE DANDA
+12470..12474  ; Terminal_Punctuation # Po   [5] CUNEIFORM PUNCTUATION SIGN OLD ASSYRIAN WORD DIVIDER..CUNEIFORM PUNCTUATION SIGN DIAGONAL QUADCOLON
+16A6E..16A6F  ; Terminal_Punctuation # Po   [2] MRO DANDA..MRO DOUBLE DANDA
+16AF5         ; Terminal_Punctuation # Po       BASSA VAH FULL STOP
+16B37..16B39  ; Terminal_Punctuation # Po   [3] PAHAWH HMONG SIGN VOS THOM..PAHAWH HMONG SIGN CIM CHEEM
+16B44         ; Terminal_Punctuation # Po       PAHAWH HMONG SIGN XAUS
+1BC9F         ; Terminal_Punctuation # Po       DUPLOYAN PUNCTUATION CHINOOK FULL STOP
 
-# Total code points: 176
+# Total code points: 214
 
 # ================================================
 
@@ -230,6 +249,10 @@
 21D5..21DB    ; Other_Math # So   [7] UP DOWN DOUBLE ARROW..RIGHTWARDS TRIPLE ARROW
 21DD          ; Other_Math # So       RIGHTWARDS SQUIGGLE ARROW
 21E4..21E5    ; Other_Math # So   [2] LEFTWARDS ARROW TO BAR..RIGHTWARDS ARROW TO BAR
+2308          ; Other_Math # Ps       LEFT CEILING
+2309          ; Other_Math # Pe       RIGHT CEILING
+230A          ; Other_Math # Ps       LEFT FLOOR
+230B          ; Other_Math # Pe       RIGHT FLOOR
 23B4..23B5    ; Other_Math # So   [2] TOP SQUARE BRACKET..BOTTOM SQUARE BRACKET
 23B7          ; Other_Math # So       RADICAL SYMBOL BOTTOM
 23D0          ; Other_Math # So       VERTICAL LINE EXTENSION
@@ -358,7 +381,7 @@
 1EEA5..1EEA9  ; Other_Math # Lo   [5] ARABIC MATHEMATICAL DOUBLE-STRUCK WAW..ARABIC MATHEMATICAL DOUBLE-STRUCK YEH
 1EEAB..1EEBB  ; Other_Math # Lo  [17] ARABIC MATHEMATICAL DOUBLE-STRUCK LAM..ARABIC MATHEMATICAL DOUBLE-STRUCK GHAIN
 
-# Total code points: 1358
+# Total code points: 1362
 
 # ================================================
 
@@ -403,8 +426,7 @@
 0825..0827    ; Other_Alphabetic # Mn   [3] SAMARITAN VOWEL SIGN SHORT A..SAMARITAN VOWEL SIGN U
 0829..082C    ; Other_Alphabetic # Mn   [4] SAMARITAN VOWEL SIGN LONG I..SAMARITAN VOWEL SIGN SUKUN
 08E4..08E9    ; Other_Alphabetic # Mn   [6] ARABIC CURLY FATHA..ARABIC CURLY KASRATAN
-08F0..08FE    ; Other_Alphabetic # Mn  [15] ARABIC OPEN FATHATAN..ARABIC DAMMA WITH DOT
-0900..0902    ; Other_Alphabetic # Mn   [3] DEVANAGARI SIGN INVERTED CANDRABINDU..DEVANAGARI SIGN ANUSVARA
+08F0..0902    ; Other_Alphabetic # Mn  [19] ARABIC OPEN FATHATAN..DEVANAGARI SIGN ANUSVARA
 0903          ; Other_Alphabetic # Mc       DEVANAGARI SIGN VISARGA
 093A          ; Other_Alphabetic # Mn       DEVANAGARI VOWEL SIGN OE
 093B          ; Other_Alphabetic # Mc       DEVANAGARI VOWEL SIGN OOE
@@ -457,6 +479,7 @@
 0BC6..0BC8    ; Other_Alphabetic # Mc   [3] TAMIL VOWEL SIGN E..TAMIL VOWEL SIGN AI
 0BCA..0BCC    ; Other_Alphabetic # Mc   [3] TAMIL VOWEL SIGN O..TAMIL VOWEL SIGN AU
 0BD7          ; Other_Alphabetic # Mc       TAMIL AU LENGTH MARK
+0C00          ; Other_Alphabetic # Mn       TELUGU SIGN COMBINING CANDRABINDU ABOVE
 0C01..0C03    ; Other_Alphabetic # Mc   [3] TELUGU SIGN CANDRABINDU..TELUGU SIGN VISARGA
 0C3E..0C40    ; Other_Alphabetic # Mn   [3] TELUGU VOWEL SIGN AA..TELUGU VOWEL SIGN II
 0C41..0C44    ; Other_Alphabetic # Mc   [4] TELUGU VOWEL SIGN U..TELUGU VOWEL SIGN VOCALIC RR
@@ -464,6 +487,7 @@
 0C4A..0C4C    ; Other_Alphabetic # Mn   [3] TELUGU VOWEL SIGN O..TELUGU VOWEL SIGN AU
 0C55..0C56    ; Other_Alphabetic # Mn   [2] TELUGU LENGTH MARK..TELUGU AI LENGTH MARK
 0C62..0C63    ; Other_Alphabetic # Mn   [2] TELUGU VOWEL SIGN VOCALIC L..TELUGU VOWEL SIGN VOCALIC LL
+0C81          ; Other_Alphabetic # Mn       KANNADA SIGN CANDRABINDU
 0C82..0C83    ; Other_Alphabetic # Mc   [2] KANNADA SIGN ANUSVARA..KANNADA SIGN VISARGA
 0CBE          ; Other_Alphabetic # Mc       KANNADA VOWEL SIGN AA
 0CBF          ; Other_Alphabetic # Mn       KANNADA VOWEL SIGN I
@@ -474,6 +498,7 @@
 0CCC          ; Other_Alphabetic # Mn       KANNADA VOWEL SIGN AU
 0CD5..0CD6    ; Other_Alphabetic # Mc   [2] KANNADA LENGTH MARK..KANNADA AI LENGTH MARK
 0CE2..0CE3    ; Other_Alphabetic # Mn   [2] KANNADA VOWEL SIGN VOCALIC L..KANNADA VOWEL SIGN VOCALIC LL
+0D01          ; Other_Alphabetic # Mn       MALAYALAM SIGN CANDRABINDU
 0D02..0D03    ; Other_Alphabetic # Mc   [2] MALAYALAM SIGN ANUSVARA..MALAYALAM SIGN VISARGA
 0D3E..0D40    ; Other_Alphabetic # Mc   [3] MALAYALAM VOWEL SIGN AA..MALAYALAM VOWEL SIGN II
 0D41..0D44    ; Other_Alphabetic # Mn   [4] MALAYALAM VOWEL SIGN U..MALAYALAM VOWEL SIGN VOCALIC RR
@@ -538,7 +563,8 @@
 19B0..19C0    ; Other_Alphabetic # Mc  [17] NEW TAI LUE VOWEL SIGN VOWEL SHORTENER..NEW TAI LUE VOWEL SIGN IY
 19C8..19C9    ; Other_Alphabetic # Mc   [2] NEW TAI LUE TONE MARK-1..NEW TAI LUE TONE MARK-2
 1A17..1A18    ; Other_Alphabetic # Mn   [2] BUGINESE VOWEL SIGN I..BUGINESE VOWEL SIGN U
-1A19..1A1B    ; Other_Alphabetic # Mc   [3] BUGINESE VOWEL SIGN E..BUGINESE VOWEL SIGN AE
+1A19..1A1A    ; Other_Alphabetic # Mc   [2] BUGINESE VOWEL SIGN E..BUGINESE VOWEL SIGN O
+1A1B          ; Other_Alphabetic # Mn       BUGINESE VOWEL SIGN AE
 1A55          ; Other_Alphabetic # Mc       TAI THAM CONSONANT SIGN MEDIAL RA
 1A56          ; Other_Alphabetic # Mn       TAI THAM CONSONANT SIGN MEDIAL LA
 1A57          ; Other_Alphabetic # Mc       TAI THAM CONSONANT SIGN LA TANG LAI
@@ -564,7 +590,7 @@
 1BA2..1BA5    ; Other_Alphabetic # Mn   [4] SUNDANESE CONSONANT SIGN PANYAKRA..SUNDANESE VOWEL SIGN PANYUKU
 1BA6..1BA7    ; Other_Alphabetic # Mc   [2] SUNDANESE VOWEL SIGN PANAELAENG..SUNDANESE VOWEL SIGN PANOLONG
 1BA8..1BA9    ; Other_Alphabetic # Mn   [2] SUNDANESE VOWEL SIGN PAMEPET..SUNDANESE VOWEL SIGN PANEULEUNG
-1BAC..1BAD    ; Other_Alphabetic # Mc   [2] SUNDANESE CONSONANT SIGN PASANGAN MA..SUNDANESE CONSONANT SIGN PASANGAN WA
+1BAC..1BAD    ; Other_Alphabetic # Mn   [2] SUNDANESE CONSONANT SIGN PASANGAN MA..SUNDANESE CONSONANT SIGN PASANGAN WA
 1BE7          ; Other_Alphabetic # Mc       BATAK VOWEL SIGN E
 1BE8..1BE9    ; Other_Alphabetic # Mn   [2] BATAK VOWEL SIGN PAKPAK E..BATAK VOWEL SIGN EE
 1BEA..1BEC    ; Other_Alphabetic # Mc   [3] BATAK VOWEL SIGN I..BATAK VOWEL SIGN O
@@ -575,6 +601,7 @@
 1C2C..1C33    ; Other_Alphabetic # Mn   [8] LEPCHA VOWEL SIGN E..LEPCHA CONSONANT SIGN T
 1C34..1C35    ; Other_Alphabetic # Mc   [2] LEPCHA CONSONANT SIGN NYIN-DO..LEPCHA CONSONANT SIGN KANG
 1CF2..1CF3    ; Other_Alphabetic # Mc   [2] VEDIC SIGN ARDHAVISARGA..VEDIC SIGN ROTATED ARDHAVISARGA
+1DE7..1DF4    ; Other_Alphabetic # Mn  [14] COMBINING LATIN SMALL LETTER ALPHA..COMBINING LATIN SMALL LETTER U WITH DIAERESIS
 24B6..24E9    ; Other_Alphabetic # So  [52] CIRCLED LATIN CAPITAL LETTER A..CIRCLED LATIN SMALL LETTER Z
 2DE0..2DFF    ; Other_Alphabetic # Mn  [32] COMBINING CYRILLIC LETTER BE..COMBINING CYRILLIC LETTER IOTIFIED BIG YUS
 A674..A67B    ; Other_Alphabetic # Mn   [8] COMBINING CYRILLIC LETTER UKRAINIAN IE..COMBINING CYRILLIC LETTER OMEGA
@@ -616,6 +643,7 @@
 ABE8          ; Other_Alphabetic # Mn       MEETEI MAYEK VOWEL SIGN UNAP
 ABE9..ABEA    ; Other_Alphabetic # Mc   [2] MEETEI MAYEK VOWEL SIGN CHEINAP..MEETEI MAYEK VOWEL SIGN NUNG
 FB1E          ; Other_Alphabetic # Mn       HEBREW POINT JUDEO-SPANISH VARIKA
+10376..1037A  ; Other_Alphabetic # Mn   [5] COMBINING OLD PERMIC LETTER AN..COMBINING OLD PERMIC LETTER SII
 10A01..10A03  ; Other_Alphabetic # Mn   [3] KHAROSHTHI VOWEL SIGN I..KHAROSHTHI VOWEL SIGN VOCALIC R
 10A05..10A06  ; Other_Alphabetic # Mn   [2] KHAROSHTHI VOWEL SIGN E..KHAROSHTHI VOWEL SIGN O
 10A0C..10A0F  ; Other_Alphabetic # Mn   [4] KHAROSHTHI VOWEL LENGTH MARK..KHAROSHTHI SIGN VISARGA
@@ -636,14 +664,54 @@
 111B3..111B5  ; Other_Alphabetic # Mc   [3] SHARADA VOWEL SIGN AA..SHARADA VOWEL SIGN II
 111B6..111BE  ; Other_Alphabetic # Mn   [9] SHARADA VOWEL SIGN U..SHARADA VOWEL SIGN O
 111BF         ; Other_Alphabetic # Mc       SHARADA VOWEL SIGN AU
+1122C..1122E  ; Other_Alphabetic # Mc   [3] KHOJKI VOWEL SIGN AA..KHOJKI VOWEL SIGN II
+1122F..11231  ; Other_Alphabetic # Mn   [3] KHOJKI VOWEL SIGN U..KHOJKI VOWEL SIGN AI
+11232..11233  ; Other_Alphabetic # Mc   [2] KHOJKI VOWEL SIGN O..KHOJKI VOWEL SIGN AU
+11234         ; Other_Alphabetic # Mn       KHOJKI SIGN ANUSVARA
+11237         ; Other_Alphabetic # Mn       KHOJKI SIGN SHADDA
+112DF         ; Other_Alphabetic # Mn       KHUDAWADI SIGN ANUSVARA
+112E0..112E2  ; Other_Alphabetic # Mc   [3] KHUDAWADI VOWEL SIGN AA..KHUDAWADI VOWEL SIGN II
+112E3..112E8  ; Other_Alphabetic # Mn   [6] KHUDAWADI VOWEL SIGN U..KHUDAWADI VOWEL SIGN AU
+11301         ; Other_Alphabetic # Mn       GRANTHA SIGN CANDRABINDU
+11302..11303  ; Other_Alphabetic # Mc   [2] GRANTHA SIGN ANUSVARA..GRANTHA SIGN VISARGA
+1133E..1133F  ; Other_Alphabetic # Mc   [2] GRANTHA VOWEL SIGN AA..GRANTHA VOWEL SIGN I
+11340         ; Other_Alphabetic # Mn       GRANTHA VOWEL SIGN II
+11341..11344  ; Other_Alphabetic # Mc   [4] GRANTHA VOWEL SIGN U..GRANTHA VOWEL SIGN VOCALIC RR
+11347..11348  ; Other_Alphabetic # Mc   [2] GRANTHA VOWEL SIGN EE..GRANTHA VOWEL SIGN AI
+1134B..1134C  ; Other_Alphabetic # Mc   [2] GRANTHA VOWEL SIGN OO..GRANTHA VOWEL SIGN AU
+11357         ; Other_Alphabetic # Mc       GRANTHA AU LENGTH MARK
+11362..11363  ; Other_Alphabetic # Mc   [2] GRANTHA VOWEL SIGN VOCALIC L..GRANTHA VOWEL SIGN VOCALIC LL
+114B0..114B2  ; Other_Alphabetic # Mc   [3] TIRHUTA VOWEL SIGN AA..TIRHUTA VOWEL SIGN II
+114B3..114B8  ; Other_Alphabetic # Mn   [6] TIRHUTA VOWEL SIGN U..TIRHUTA VOWEL SIGN VOCALIC LL
+114B9         ; Other_Alphabetic # Mc       TIRHUTA VOWEL SIGN E
+114BA         ; Other_Alphabetic # Mn       TIRHUTA VOWEL SIGN SHORT E
+114BB..114BE  ; Other_Alphabetic # Mc   [4] TIRHUTA VOWEL SIGN AI..TIRHUTA VOWEL SIGN AU
+114BF..114C0  ; Other_Alphabetic # Mn   [2] TIRHUTA SIGN CANDRABINDU..TIRHUTA SIGN ANUSVARA
+114C1         ; Other_Alphabetic # Mc       TIRHUTA SIGN VISARGA
+115AF..115B1  ; Other_Alphabetic # Mc   [3] SIDDHAM VOWEL SIGN AA..SIDDHAM VOWEL SIGN II
+115B2..115B5  ; Other_Alphabetic # Mn   [4] SIDDHAM VOWEL SIGN U..SIDDHAM VOWEL SIGN VOCALIC RR
+115B8..115BB  ; Other_Alphabetic # Mc   [4] SIDDHAM VOWEL SIGN E..SIDDHAM VOWEL SIGN AU
+115BC..115BD  ; Other_Alphabetic # Mn   [2] SIDDHAM SIGN CANDRABINDU..SIDDHAM SIGN ANUSVARA
+115BE         ; Other_Alphabetic # Mc       SIDDHAM SIGN VISARGA
+11630..11632  ; Other_Alphabetic # Mc   [3] MODI VOWEL SIGN AA..MODI VOWEL SIGN II
+11633..1163A  ; Other_Alphabetic # Mn   [8] MODI VOWEL SIGN U..MODI VOWEL SIGN AI
+1163B..1163C  ; Other_Alphabetic # Mc   [2] MODI VOWEL SIGN O..MODI VOWEL SIGN AU
+1163D         ; Other_Alphabetic # Mn       MODI SIGN ANUSVARA
+1163E         ; Other_Alphabetic # Mc       MODI SIGN VISARGA
+11640         ; Other_Alphabetic # Mn       MODI SIGN ARDHACANDRA
 116AB         ; Other_Alphabetic # Mn       TAKRI SIGN ANUSVARA
 116AC         ; Other_Alphabetic # Mc       TAKRI SIGN VISARGA
 116AD         ; Other_Alphabetic # Mn       TAKRI VOWEL SIGN AA
 116AE..116AF  ; Other_Alphabetic # Mc   [2] TAKRI VOWEL SIGN I..TAKRI VOWEL SIGN II
 116B0..116B5  ; Other_Alphabetic # Mn   [6] TAKRI VOWEL SIGN U..TAKRI VOWEL SIGN AU
+16B30..16B36  ; Other_Alphabetic # Mn   [7] PAHAWH HMONG MARK CIM TUB..PAHAWH HMONG MARK CIM TAUM
 16F51..16F7E  ; Other_Alphabetic # Mc  [46] MIAO SIGN ASPIRATION..MIAO VOWEL SIGN NG
+1BC9E         ; Other_Alphabetic # Mn       DUPLOYAN DOUBLE MARK
+1F130..1F149  ; Other_Alphabetic # So  [26] SQUARED LATIN CAPITAL LETTER A..SQUARED LATIN CAPITAL LETTER Z
+1F150..1F169  ; Other_Alphabetic # So  [26] NEGATIVE CIRCLED LATIN CAPITAL LETTER A..NEGATIVE CIRCLED LATIN CAPITAL LETTER Z
+1F170..1F189  ; Other_Alphabetic # So  [26] NEGATIVE SQUARED LATIN CAPITAL LETTER A..NEGATIVE SQUARED LATIN CAPITAL LETTER Z
 
-# Total code points: 922
+# Total code points: 1116
 
 # ================================================
 
@@ -746,6 +814,7 @@
 1939..193B    ; Diacritic # Mn   [3] LIMBU SIGN MUKPHRENG..LIMBU SIGN SA-I
 1A75..1A7C    ; Diacritic # Mn   [8] TAI THAM SIGN TONE-1..TAI THAM SIGN KHUEN-LUE KARAN
 1A7F          ; Diacritic # Mn       TAI THAM COMBINING CRYPTOGRAMMIC DOT
+1AB0..1ABD    ; Diacritic # Mn  [14] COMBINING DOUBLED CIRCUMFLEX ACCENT..COMBINING PARENTHESES BELOW
 1B34          ; Diacritic # Mn       BALINESE SIGN REREKAN
 1B44          ; Diacritic # Mc       BALINESE ADEG ADEG
 1B6B..1B73    ; Diacritic # Mn   [9] BALINESE MUSICAL SYMBOL COMBINING TEGEH..BALINESE MUSICAL SYMBOL COMBINING GONG
@@ -760,8 +829,10 @@
 1CE2..1CE8    ; Diacritic # Mn   [7] VEDIC SIGN VISARGA SVARITA..VEDIC SIGN VISARGA ANUDATTA WITH TAIL
 1CED          ; Diacritic # Mn       VEDIC SIGN TIRYAK
 1CF4          ; Diacritic # Mn       VEDIC TONE CANDRA ABOVE
+1CF8..1CF9    ; Diacritic # Mn   [2] VEDIC TONE RING ABOVE..VEDIC TONE DOUBLE RING ABOVE
 1D2C..1D6A    ; Diacritic # Lm  [63] MODIFIER LETTER CAPITAL A..GREEK SUBSCRIPT SMALL LETTER CHI
 1DC4..1DCF    ; Diacritic # Mn  [12] COMBINING MACRON-ACUTE..COMBINING ZIGZAG BELOW
+1DF5          ; Diacritic # Mn       COMBINING UP TACK ABOVE
 1DFD..1DFF    ; Diacritic # Mn   [3] COMBINING ALMOST EQUAL TO BELOW..COMBINING RIGHT ARROWHEAD AND DOWN ARROWHEAD BELOW
 1FBD          ; Diacritic # Sk       GREEK KORONIS
 1FBF..1FC1    ; Diacritic # Sk   [3] GREEK PSILI..GREEK DIALYTIKA AND PERISPOMENI
@@ -779,6 +850,7 @@
 A66F          ; Diacritic # Mn       COMBINING CYRILLIC VZMET
 A67C..A67D    ; Diacritic # Mn   [2] COMBINING CYRILLIC KAVYKA..COMBINING CYRILLIC PAYEROK
 A67F          ; Diacritic # Lm       CYRILLIC PAYEROK
+A69C..A69D    ; Diacritic # Lm   [2] MODIFIER LETTER CYRILLIC HARD SIGN..MODIFIER LETTER CYRILLIC SOFT SIGN
 A6F0..A6F1    ; Diacritic # Mn   [2] BAMUM COMBINING MARK KOQNDON..BAMUM COMBINING MARK TUKWENTIS
 A717..A71F    ; Diacritic # Lm   [9] MODIFIER LETTER DOT VERTICAL BAR..MODIFIER LETTER LOW INVERTED EXCLAMATION MARK
 A720..A721    ; Diacritic # Sk   [2] MODIFIER LETTER STRESS AND HIGH TONE..MODIFIER LETTER STRESS AND LOW TONE
@@ -791,26 +863,45 @@
 A953          ; Diacritic # Mc       REJANG VIRAMA
 A9B3          ; Diacritic # Mn       JAVANESE SIGN CECAK TELU
 A9C0          ; Diacritic # Mc       JAVANESE PANGKON
+A9E5          ; Diacritic # Mn       MYANMAR SIGN SHAN SAW
 AA7B          ; Diacritic # Mc       MYANMAR SIGN PAO KAREN TONE
+AA7C          ; Diacritic # Mn       MYANMAR SIGN TAI LAING TONE-2
+AA7D          ; Diacritic # Mc       MYANMAR SIGN TAI LAING TONE-5
 AABF          ; Diacritic # Mn       TAI VIET TONE MAI EK
 AAC0          ; Diacritic # Lo       TAI VIET TONE MAI NUENG
 AAC1          ; Diacritic # Mn       TAI VIET TONE MAI THO
 AAC2          ; Diacritic # Lo       TAI VIET TONE MAI SONG
 AAF6          ; Diacritic # Mn       MEETEI MAYEK VIRAMA
+AB5B          ; Diacritic # Sk       MODIFIER BREVE WITH INVERTED BREVE
+AB5C..AB5F    ; Diacritic # Lm   [4] MODIFIER LETTER SMALL HENG..MODIFIER LETTER SMALL U WITH LEFT HOOK
 ABEC          ; Diacritic # Mc       MEETEI MAYEK LUM IYEK
 ABED          ; Diacritic # Mn       MEETEI MAYEK APUN IYEK
 FB1E          ; Diacritic # Mn       HEBREW POINT JUDEO-SPANISH VARIKA
-FE20..FE26    ; Diacritic # Mn   [7] COMBINING LIGATURE LEFT HALF..COMBINING CONJOINING MACRON
+FE20..FE2D    ; Diacritic # Mn  [14] COMBINING LIGATURE LEFT HALF..COMBINING CONJOINING MACRON BELOW
 FF3E          ; Diacritic # Sk       FULLWIDTH CIRCUMFLEX ACCENT
 FF40          ; Diacritic # Sk       FULLWIDTH GRAVE ACCENT
 FF70          ; Diacritic # Lm       HALFWIDTH KATAKANA-HIRAGANA PROLONGED SOUND MARK
 FF9E..FF9F    ; Diacritic # Lm   [2] HALFWIDTH KATAKANA VOICED SOUND MARK..HALFWIDTH KATAKANA SEMI-VOICED SOUND MARK
 FFE3          ; Diacritic # Sk       FULLWIDTH MACRON
+102E0         ; Diacritic # Mn       COPTIC EPACT THOUSANDS MARK
+10AE5..10AE6  ; Diacritic # Mn   [2] MANICHAEAN ABBREVIATION MARK ABOVE..MANICHAEAN ABBREVIATION MARK BELOW
 110B9..110BA  ; Diacritic # Mn   [2] KAITHI SIGN VIRAMA..KAITHI SIGN NUKTA
 11133..11134  ; Diacritic # Mn   [2] CHAKMA VIRAMA..CHAKMA MAAYYAA
+11173         ; Diacritic # Mn       MAHAJANI SIGN NUKTA
 111C0         ; Diacritic # Mc       SHARADA SIGN VIRAMA
+11235         ; Diacritic # Mc       KHOJKI SIGN VIRAMA
+11236         ; Diacritic # Mn       KHOJKI SIGN NUKTA
+112E9..112EA  ; Diacritic # Mn   [2] KHUDAWADI SIGN NUKTA..KHUDAWADI SIGN VIRAMA
+1133C         ; Diacritic # Mn       GRANTHA SIGN NUKTA
+1134D         ; Diacritic # Mc       GRANTHA SIGN VIRAMA
+11366..1136C  ; Diacritic # Mn   [7] COMBINING GRANTHA DIGIT ZERO..COMBINING GRANTHA DIGIT SIX
+11370..11374  ; Diacritic # Mn   [5] COMBINING GRANTHA LETTER A..COMBINING GRANTHA LETTER PA
+114C2..114C3  ; Diacritic # Mn   [2] TIRHUTA SIGN VIRAMA..TIRHUTA SIGN NUKTA
+115BF..115C0  ; Diacritic # Mn   [2] SIDDHAM SIGN VIRAMA..SIDDHAM SIGN NUKTA
+1163F         ; Diacritic # Mn       MODI SIGN VIRAMA
 116B6         ; Diacritic # Mc       TAKRI SIGN VIRAMA
 116B7         ; Diacritic # Mn       TAKRI SIGN NUKTA
+16AF0..16AF4  ; Diacritic # Mn   [5] BASSA VAH COMBINING HIGH TONE..BASSA VAH COMBINING HIGH-LOW TONE
 16F8F..16F92  ; Diacritic # Mn   [4] MIAO TONE RIGHT..MIAO TONE BELOW
 16F93..16F9F  ; Diacritic # Lm  [13] MIAO LETTER TONE-2..MIAO LETTER REFORMED TONE-8
 1D167..1D169  ; Diacritic # Mn   [3] MUSICAL SYMBOL COMBINING TREMOLO-1..MUSICAL SYMBOL COMBINING TREMOLO-3
@@ -818,8 +909,9 @@
 1D17B..1D182  ; Diacritic # Mn   [8] MUSICAL SYMBOL COMBINING ACCENT..MUSICAL SYMBOL COMBINING LOURE
 1D185..1D18B  ; Diacritic # Mn   [7] MUSICAL SYMBOL COMBINING DOIT..MUSICAL SYMBOL COMBINING TRIPLE TONGUE
 1D1AA..1D1AD  ; Diacritic # Mn   [4] MUSICAL SYMBOL COMBINING DOWN BOW..MUSICAL SYMBOL COMBINING SNAP PIZZICATO
+1E8D0..1E8D6  ; Diacritic # Mn   [7] MENDE KIKAKUI COMBINING NUMBER TEENS..MENDE KIKAKUI COMBINING NUMBER MILLIONS
 
-# Total code points: 693
+# Total code points: 766
 
 # ================================================
 
@@ -841,12 +933,16 @@
 A015          ; Extender # Lm       YI SYLLABLE WU
 A60C          ; Extender # Lm       VAI SYLLABLE LENGTHENER
 A9CF          ; Extender # Lm       JAVANESE PANGRANGKEP
+A9E6          ; Extender # Lm       MYANMAR MODIFIER LETTER SHAN REDUPLICATION
 AA70          ; Extender # Lm       MYANMAR MODIFIER LETTER KHAMTI REDUPLICATION
 AADD          ; Extender # Lm       TAI VIET SYMBOL SAM
 AAF3..AAF4    ; Extender # Lm   [2] MEETEI MAYEK SYLLABLE REPETITION MARK..MEETEI MAYEK WORD REPETITION MARK
 FF70          ; Extender # Lm       HALFWIDTH KATAKANA-HIRAGANA PROLONGED SOUND MARK
+1135D         ; Extender # Lo       GRANTHA SIGN PLUTA
+115C6..115C8  ; Extender # Po   [3] SIDDHAM REPETITION MARK-1..SIDDHAM REPETITION MARK-3
+16B42..16B43  ; Extender # Lm   [2] PAHAWH HMONG SIGN VOS NRUA..PAHAWH HMONG SIGN IB YAM
 
-# Total code points: 31
+# Total code points: 38
 
 # ================================================
 
@@ -866,17 +962,22 @@
 2170..217F    ; Other_Lowercase # Nl  [16] SMALL ROMAN NUMERAL ONE..SMALL ROMAN NUMERAL ONE THOUSAND
 24D0..24E9    ; Other_Lowercase # So  [26] CIRCLED LATIN SMALL LETTER A..CIRCLED LATIN SMALL LETTER Z
 2C7C..2C7D    ; Other_Lowercase # Lm   [2] LATIN SUBSCRIPT SMALL LETTER J..MODIFIER LETTER CAPITAL V
+A69C..A69D    ; Other_Lowercase # Lm   [2] MODIFIER LETTER CYRILLIC HARD SIGN..MODIFIER LETTER CYRILLIC SOFT SIGN
 A770          ; Other_Lowercase # Lm       MODIFIER LETTER US
 A7F8..A7F9    ; Other_Lowercase # Lm   [2] MODIFIER LETTER CAPITAL H WITH STROKE..MODIFIER LETTER SMALL LIGATURE OE
+AB5C..AB5F    ; Other_Lowercase # Lm   [4] MODIFIER LETTER SMALL HENG..MODIFIER LETTER SMALL U WITH LEFT HOOK
 
-# Total code points: 183
+# Total code points: 189
 
 # ================================================
 
 2160..216F    ; Other_Uppercase # Nl  [16] ROMAN NUMERAL ONE..ROMAN NUMERAL ONE THOUSAND
 24B6..24CF    ; Other_Uppercase # So  [26] CIRCLED LATIN CAPITAL LETTER A..CIRCLED LATIN CAPITAL LETTER Z
+1F130..1F149  ; Other_Uppercase # So  [26] SQUARED LATIN CAPITAL LETTER A..SQUARED LATIN CAPITAL LETTER Z
+1F150..1F169  ; Other_Uppercase # So  [26] NEGATIVE CIRCLED LATIN CAPITAL LETTER A..NEGATIVE CIRCLED LATIN CAPITAL LETTER Z
+1F170..1F189  ; Other_Uppercase # So  [26] NEGATIVE SQUARED LATIN CAPITAL LETTER A..NEGATIVE SQUARED LATIN CAPITAL LETTER Z
 
-# Total code points: 42
+# Total code points: 120
 
 # ================================================
 
@@ -918,10 +1019,15 @@
 200C..200D    ; Other_Grapheme_Extend # Cf   [2] ZERO WIDTH NON-JOINER..ZERO WIDTH JOINER
 302E..302F    ; Other_Grapheme_Extend # Mc   [2] HANGUL SINGLE DOT TONE MARK..HANGUL DOUBLE DOT TONE MARK
 FF9E..FF9F    ; Other_Grapheme_Extend # Lm   [2] HALFWIDTH KATAKANA VOICED SOUND MARK..HALFWIDTH KATAKANA SEMI-VOICED SOUND MARK
+1133E         ; Other_Grapheme_Extend # Mc       GRANTHA VOWEL SIGN AA
+11357         ; Other_Grapheme_Extend # Mc       GRANTHA AU LENGTH MARK
+114B0         ; Other_Grapheme_Extend # Mc       TIRHUTA VOWEL SIGN AA
+114BD         ; Other_Grapheme_Extend # Mc       TIRHUTA VOWEL SIGN SHORT O
+115AF         ; Other_Grapheme_Extend # Mc       SIDDHAM VOWEL SIGN AA
 1D165         ; Other_Grapheme_Extend # Mc       MUSICAL SYMBOL COMBINING STEM
 1D16E..1D172  ; Other_Grapheme_Extend # Mc   [5] MUSICAL SYMBOL COMBINING FLAG-1..MUSICAL SYMBOL COMBINING FLAG-5
 
-# Total code points: 25
+# Total code points: 30
 
 # ================================================
 
@@ -966,7 +1072,7 @@
 034F          ; Other_Default_Ignorable_Code_Point # Mn       COMBINING GRAPHEME JOINER
 115F..1160    ; Other_Default_Ignorable_Code_Point # Lo   [2] HANGUL CHOSEONG FILLER..HANGUL JUNGSEONG FILLER
 17B4..17B5    ; Other_Default_Ignorable_Code_Point # Mn   [2] KHMER VOWEL INHERENT AQ..KHMER VOWEL INHERENT AA
-2065..2069    ; Other_Default_Ignorable_Code_Point # Cn   [5] <reserved-2065>..<reserved-2069>
+2065          ; Other_Default_Ignorable_Code_Point # Cn       <reserved-2065>
 3164          ; Other_Default_Ignorable_Code_Point # Lo       HANGUL FILLER
 FFA0          ; Other_Default_Ignorable_Code_Point # Lo       HALFWIDTH HANGUL FILLER
 FFF0..FFF8    ; Other_Default_Ignorable_Code_Point # Cn   [9] <reserved-FFF0>..<reserved-FFF8>
@@ -975,7 +1081,7 @@
 E0080..E00FF  ; Other_Default_Ignorable_Code_Point # Cn [128] <reserved-E0080>..<reserved-E00FF>
 E01F0..E0FFF  ; Other_Default_Ignorable_Code_Point # Cn [3600] <reserved-E01F0>..<reserved-E0FFF>
 
-# Total code points: 3780
+# Total code points: 3776
 
 # ================================================
 
@@ -1060,8 +1166,6 @@
 0021          ; STerm # Po       EXCLAMATION MARK
 002E          ; STerm # Po       FULL STOP
 003F          ; STerm # Po       QUESTION MARK
-055C          ; STerm # Po       ARMENIAN EXCLAMATION MARK
-055E          ; STerm # Po       ARMENIAN QUESTION MARK
 0589          ; STerm # Po       ARMENIAN FULL STOP
 061F          ; STerm # Po       ARABIC QUESTION MARK
 06D4          ; STerm # Po       ARABIC FULL STOP
@@ -1084,6 +1188,7 @@
 203C..203D    ; STerm # Po   [2] DOUBLE EXCLAMATION MARK..INTERROBANG
 2047..2049    ; STerm # Po   [3] DOUBLE QUESTION MARK..EXCLAMATION QUESTION MARK
 2E2E          ; STerm # Po       REVERSED QUESTION MARK
+2E3C          ; STerm # Po       STENOGRAPHIC FULL STOP
 3002          ; STerm # Po       IDEOGRAPHIC FULL STOP
 A4FF          ; STerm # Po       LISU PUNCTUATION FULL STOP
 A60E..A60F    ; STerm # Po   [2] VAI FULL STOP..VAI QUESTION MARK
@@ -1107,8 +1212,19 @@
 110BE..110C1  ; STerm # Po   [4] KAITHI SECTION MARK..KAITHI DOUBLE DANDA
 11141..11143  ; STerm # Po   [3] CHAKMA DANDA..CHAKMA QUESTION MARK
 111C5..111C6  ; STerm # Po   [2] SHARADA DANDA..SHARADA DOUBLE DANDA
+111CD         ; STerm # Po       SHARADA SUTRA MARK
+11238..11239  ; STerm # Po   [2] KHOJKI DANDA..KHOJKI DOUBLE DANDA
+1123B..1123C  ; STerm # Po   [2] KHOJKI SECTION MARK..KHOJKI DOUBLE SECTION MARK
+115C2..115C3  ; STerm # Po   [2] SIDDHAM DANDA..SIDDHAM DOUBLE DANDA
+115C9         ; STerm # Po       SIDDHAM END OF TEXT MARK
+11641..11642  ; STerm # Po   [2] MODI DANDA..MODI DOUBLE DANDA
+16A6E..16A6F  ; STerm # Po   [2] MRO DANDA..MRO DOUBLE DANDA
+16AF5         ; STerm # Po       BASSA VAH FULL STOP
+16B37..16B38  ; STerm # Po   [2] PAHAWH HMONG SIGN VOS THOM..PAHAWH HMONG SIGN VOS TSHAB CEEB
+16B44         ; STerm # Po       PAHAWH HMONG SIGN XAUS
+1BC9F         ; STerm # Po       DUPLOYAN PUNCTUATION CHINOOK FULL STOP
 
-# Total code points: 83
+# Total code points: 99
 
 # ================================================
 
@@ -1210,7 +1326,10 @@
 21D5..21F3    ; Pattern_Syntax # So  [31] UP DOWN DOUBLE ARROW..UP DOWN WHITE ARROW
 21F4..22FF    ; Pattern_Syntax # Sm [268] RIGHT ARROW WITH SMALL CIRCLE..Z NOTATION BAG MEMBERSHIP
 2300..2307    ; Pattern_Syntax # So   [8] DIAMETER SIGN..WAVY LINE
-2308..230B    ; Pattern_Syntax # Sm   [4] LEFT CEILING..RIGHT FLOOR
+2308          ; Pattern_Syntax # Ps       LEFT CEILING
+2309          ; Pattern_Syntax # Pe       RIGHT CEILING
+230A          ; Pattern_Syntax # Ps       LEFT FLOOR
+230B          ; Pattern_Syntax # Pe       RIGHT FLOOR
 230C..231F    ; Pattern_Syntax # So  [20] BOTTOM RIGHT CROP..BOTTOM RIGHT CORNER
 2320..2321    ; Pattern_Syntax # Sm   [2] TOP HALF INTEGRAL..BOTTOM HALF INTEGRAL
 2322..2328    ; Pattern_Syntax # So   [7] FROWN..KEYBOARD
@@ -1222,8 +1341,8 @@
 239B..23B3    ; Pattern_Syntax # Sm  [25] LEFT PARENTHESIS UPPER HOOK..SUMMATION BOTTOM
 23B4..23DB    ; Pattern_Syntax # So  [40] TOP SQUARE BRACKET..FUSE
 23DC..23E1    ; Pattern_Syntax # Sm   [6] TOP PARENTHESIS..BOTTOM TORTOISE SHELL BRACKET
-23E2..23F3    ; Pattern_Syntax # So  [18] WHITE TRAPEZIUM..HOURGLASS WITH FLOWING SAND
-23F4..23FF    ; Pattern_Syntax # Cn  [12] <reserved-23F4>..<reserved-23FF>
+23E2..23FA    ; Pattern_Syntax # So  [25] WHITE TRAPEZIUM..BLACK CIRCLE FOR RECORD
+23FB..23FF    ; Pattern_Syntax # Cn   [5] <reserved-23FB>..<reserved-23FF>
 2400..2426    ; Pattern_Syntax # So  [39] SYMBOL FOR NULL..SYMBOL FOR SUBSTITUTE FORM TWO
 2427..243F    ; Pattern_Syntax # Cn  [25] <reserved-2427>..<reserved-243F>
 2440..244A    ; Pattern_Syntax # So  [11] OCR HOOK..OCR DOUBLE BACKSLASH
@@ -1236,9 +1355,7 @@
 25F8..25FF    ; Pattern_Syntax # Sm   [8] UPPER LEFT TRIANGLE..LOWER RIGHT TRIANGLE
 2600..266E    ; Pattern_Syntax # So [111] BLACK SUN WITH RAYS..MUSIC NATURAL SIGN
 266F          ; Pattern_Syntax # Sm       MUSIC SHARP SIGN
-2670..26FF    ; Pattern_Syntax # So [144] WEST SYRIAC CROSS..WHITE FLAG WITH HORIZONTAL MIDDLE BLACK STRIPE
-2700          ; Pattern_Syntax # Cn       <reserved-2700>
-2701..2767    ; Pattern_Syntax # So [103] UPPER BLADE SCISSORS..ROTATED FLORAL HEART BULLET
+2670..2767    ; Pattern_Syntax # So [248] WEST SYRIAC CROSS..ROTATED FLORAL HEART BULLET
 2768          ; Pattern_Syntax # Ps       MEDIUM LEFT PARENTHESIS ORNAMENT
 2769          ; Pattern_Syntax # Pe       MEDIUM RIGHT PARENTHESIS ORNAMENT
 276A          ; Pattern_Syntax # Ps       MEDIUM FLATTENED LEFT PARENTHESIS ORNAMENT
@@ -1306,9 +1423,16 @@
 2B30..2B44    ; Pattern_Syntax # Sm  [21] LEFT ARROW WITH SMALL CIRCLE..RIGHTWARDS ARROW THROUGH SUPERSET
 2B45..2B46    ; Pattern_Syntax # So   [2] LEFTWARDS QUADRUPLE ARROW..RIGHTWARDS QUADRUPLE ARROW
 2B47..2B4C    ; Pattern_Syntax # Sm   [6] REVERSE TILDE OPERATOR ABOVE RIGHTWARDS ARROW..RIGHTWARDS ARROW ABOVE REVERSE TILDE OPERATOR
-2B4D..2B4F    ; Pattern_Syntax # Cn   [3] <reserved-2B4D>..<reserved-2B4F>
-2B50..2B59    ; Pattern_Syntax # So  [10] WHITE MEDIUM STAR..HEAVY CIRCLED SALTIRE
-2B5A..2BFF    ; Pattern_Syntax # Cn [166] <reserved-2B5A>..<reserved-2BFF>
+2B4D..2B73    ; Pattern_Syntax # So  [39] DOWNWARDS TRIANGLE-HEADED ZIGZAG ARROW..DOWNWARDS TRIANGLE-HEADED ARROW TO BAR
+2B74..2B75    ; Pattern_Syntax # Cn   [2] <reserved-2B74>..<reserved-2B75>
+2B76..2B95    ; Pattern_Syntax # So  [32] NORTH WEST TRIANGLE-HEADED ARROW TO BAR..RIGHTWARDS BLACK ARROW
+2B96..2B97    ; Pattern_Syntax # Cn   [2] <reserved-2B96>..<reserved-2B97>
+2B98..2BB9    ; Pattern_Syntax # So  [34] THREE-D TOP-LIGHTED LEFTWARDS EQUILATERAL ARROWHEAD..UP ARROWHEAD IN A RECTANGLE BOX
+2BBA..2BBC    ; Pattern_Syntax # Cn   [3] <reserved-2BBA>..<reserved-2BBC>
+2BBD..2BC8    ; Pattern_Syntax # So  [12] BALLOT BOX WITH LIGHT X..BLACK MEDIUM RIGHT-POINTING TRIANGLE CENTRED
+2BC9          ; Pattern_Syntax # Cn       <reserved-2BC9>
+2BCA..2BD1    ; Pattern_Syntax # So   [8] TOP HALF BLACK CIRCLE..UNCERTAINTY SIGN
+2BD2..2BFF    ; Pattern_Syntax # Cn  [46] <reserved-2BD2>..<reserved-2BFF>
 2E00..2E01    ; Pattern_Syntax # Po   [2] RIGHT ANGLE SUBSTITUTION MARKER..RIGHT ANGLE DOTTED SUBSTITUTION MARKER
 2E02          ; Pattern_Syntax # Pi       LEFT SUBSTITUTION BRACKET
 2E03          ; Pattern_Syntax # Pf       RIGHT SUBSTITUTION BRACKET
@@ -1342,7 +1466,11 @@
 2E2F          ; Pattern_Syntax # Lm       VERTICAL TILDE
 2E30..2E39    ; Pattern_Syntax # Po  [10] RING POINT..TOP HALF SECTION SIGN
 2E3A..2E3B    ; Pattern_Syntax # Pd   [2] TWO-EM DASH..THREE-EM DASH
-2E3C..2E7F    ; Pattern_Syntax # Cn  [68] <reserved-2E3C>..<reserved-2E7F>
+2E3C..2E3F    ; Pattern_Syntax # Po   [4] STENOGRAPHIC FULL STOP..CAPITULUM
+2E40          ; Pattern_Syntax # Pd       DOUBLE HYPHEN
+2E41          ; Pattern_Syntax # Po       REVERSED COMMA
+2E42          ; Pattern_Syntax # Ps       DOUBLE LOW-REVERSED-9 QUOTATION MARK
+2E43..2E7F    ; Pattern_Syntax # Cn  [61] <reserved-2E43>..<reserved-2E7F>
 3001..3003    ; Pattern_Syntax # Po   [3] IDEOGRAPHIC COMMA..DITTO MARK
 3008          ; Pattern_Syntax # Ps       LEFT ANGLE BRACKET
 3009          ; Pattern_Syntax # Pe       RIGHT ANGLE BRACKET
@@ -1368,8 +1496,8 @@
 301E..301F    ; Pattern_Syntax # Pe   [2] DOUBLE PRIME QUOTATION MARK..LOW DOUBLE PRIME QUOTATION MARK
 3020          ; Pattern_Syntax # So       POSTAL MARK FACE
 3030          ; Pattern_Syntax # Pd       WAVY DASH
-FD3E          ; Pattern_Syntax # Ps       ORNATE LEFT PARENTHESIS
-FD3F          ; Pattern_Syntax # Pe       ORNATE RIGHT PARENTHESIS
+FD3E          ; Pattern_Syntax # Pe       ORNATE LEFT PARENTHESIS
+FD3F          ; Pattern_Syntax # Ps       ORNATE RIGHT PARENTHESIS
 FE45..FE46    ; Pattern_Syntax # Po   [2] SESAME DOT..WHITE SESAME DOT
 
 # Total code points: 2760
--- a/jdk/test/java/lang/Character/PropertyValueAliases.txt	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/lang/Character/PropertyValueAliases.txt	Wed Jul 05 20:42:36 2017 +0200
@@ -1,8 +1,8 @@
-# PropertyValueAliases-6.2.0.txt
-# Date: 2012-08-14, 16:05:11 GMT [MD]
+# PropertyValueAliases-7.0.0.txt
+# Date: 2014-05-14, 23:55:16 GMT [MD]
 #
 # Unicode Character Database
-# Copyright (c) 1991-2012 Unicode, Inc.
+# Copyright (c) 1991-2014 Unicode, Inc.
 # For terms of use, see http://www.unicode.org/terms_of_use.html
 # For documentation, see http://www.unicode.org/reports/tr44/
 #
@@ -32,13 +32,14 @@
 #
 # Loose matching should be applied to all property names and property values, with
 # the exception of String Property values. With loose matching of property names and
-# values, the case distinctions, whitespace, and '_' are ignored. For Numeric Property
-# values, numeric equivalencies are applied: thus "01.00" is equivalent to "1".
+# values, the case distinctions, whitespace, hyphens, and '_' are ignored.
+# For Numeric Property values, numeric equivalence is applied: thus "01.00"
+# is equivalent to "1".
 #
 # NOTE: Property value names are NOT unique across properties. For example:
 #
 #   AL means Arabic Letter for the Bidi_Class property, and
-#   AL means Above_Left for the Combining_Class property, and
+#   AL means Above_Left for the Canonical_Combining_Class property, and
 #   AL means Alphabetic for the Line_Break property.
 #
 # In addition, some property names may be the same as some property value names.
@@ -74,6 +75,8 @@
 age; 6.0                              ; V6_0
 age; 6.1                              ; V6_1
 age; 6.2                              ; V6_2
+age; 6.3                              ; V6_3
+age; 7.0                              ; V7_0
 age; NA                               ; Unassigned
 
 # Alphabetic (Alpha)
@@ -91,14 +94,18 @@
 bc ; EN                               ; European_Number
 bc ; ES                               ; European_Separator
 bc ; ET                               ; European_Terminator
+bc ; FSI                              ; First_Strong_Isolate
 bc ; L                                ; Left_To_Right
 bc ; LRE                              ; Left_To_Right_Embedding
+bc ; LRI                              ; Left_To_Right_Isolate
 bc ; LRO                              ; Left_To_Right_Override
 bc ; NSM                              ; Nonspacing_Mark
 bc ; ON                               ; Other_Neutral
 bc ; PDF                              ; Pop_Directional_Format
+bc ; PDI                              ; Pop_Directional_Isolate
 bc ; R                                ; Right_To_Left
 bc ; RLE                              ; Right_To_Left_Embedding
+bc ; RLI                              ; Right_To_Left_Isolate
 bc ; RLO                              ; Right_To_Left_Override
 bc ; S                                ; Segment_Separator
 bc ; WS                               ; White_Space
@@ -117,6 +124,17 @@
 
 # @missing: 0000..10FFFF; Bidi_Mirroring_Glyph; <none>
 
+# Bidi_Paired_Bracket (bpb)
+
+# @missing: 0000..10FFFF; Bidi_Paired_Bracket; <none>
+
+# Bidi_Paired_Bracket_Type (bpt)
+
+bpt; c                                ; Close
+bpt; n                                ; None
+bpt; o                                ; Open
+# @missing: 0000..10FFFF; Bidi_Paired_Bracket_Type; n
+
 # Block (blk)
 
 blk; Aegean_Numbers                   ; Aegean_Numbers
@@ -138,6 +156,7 @@
 blk; Balinese                         ; Balinese
 blk; Bamum                            ; Bamum
 blk; Bamum_Sup                        ; Bamum_Supplement
+blk; Bassa_Vah                        ; Bassa_Vah
 blk; Batak                            ; Batak
 blk; Bengali                          ; Bengali
 blk; Block_Elements                   ; Block_Elements
@@ -150,6 +169,7 @@
 blk; Buhid                            ; Buhid
 blk; Byzantine_Music                  ; Byzantine_Musical_Symbols
 blk; Carian                           ; Carian
+blk; Caucasian_Albanian               ; Caucasian_Albanian
 blk; Chakma                           ; Chakma
 blk; Cham                             ; Cham
 blk; Cherokee                         ; Cherokee
@@ -168,6 +188,7 @@
 blk; Compat_Jamo                      ; Hangul_Compatibility_Jamo
 blk; Control_Pictures                 ; Control_Pictures
 blk; Coptic                           ; Coptic
+blk; Coptic_Epact_Numbers             ; Coptic_Epact_Numbers
 blk; Counting_Rod                     ; Counting_Rod_Numerals
 blk; Cuneiform                        ; Cuneiform
 blk; Cuneiform_Numbers                ; Cuneiform_Numbers_And_Punctuation
@@ -181,11 +202,14 @@
 blk; Devanagari                       ; Devanagari
 blk; Devanagari_Ext                   ; Devanagari_Extended
 blk; Diacriticals                     ; Combining_Diacritical_Marks
+blk; Diacriticals_Ext                 ; Combining_Diacritical_Marks_Extended
 blk; Diacriticals_For_Symbols         ; Combining_Diacritical_Marks_For_Symbols; Combining_Marks_For_Symbols
 blk; Diacriticals_Sup                 ; Combining_Diacritical_Marks_Supplement
 blk; Dingbats                         ; Dingbats
 blk; Domino                           ; Domino_Tiles
+blk; Duployan                         ; Duployan
 blk; Egyptian_Hieroglyphs             ; Egyptian_Hieroglyphs
+blk; Elbasan                          ; Elbasan
 blk; Emoticons                        ; Emoticons
 blk; Enclosed_Alphanum                ; Enclosed_Alphanumerics
 blk; Enclosed_Alphanum_Sup            ; Enclosed_Alphanumeric_Supplement
@@ -196,10 +220,12 @@
 blk; Ethiopic_Ext_A                   ; Ethiopic_Extended_A
 blk; Ethiopic_Sup                     ; Ethiopic_Supplement
 blk; Geometric_Shapes                 ; Geometric_Shapes
+blk; Geometric_Shapes_Ext             ; Geometric_Shapes_Extended
 blk; Georgian                         ; Georgian
 blk; Georgian_Sup                     ; Georgian_Supplement
 blk; Glagolitic                       ; Glagolitic
 blk; Gothic                           ; Gothic
+blk; Grantha                          ; Grantha
 blk; Greek                            ; Greek_And_Coptic
 blk; Greek_Ext                        ; Greek_Extended
 blk; Gujarati                         ; Gujarati
@@ -233,6 +259,8 @@
 blk; Kharoshthi                       ; Kharoshthi
 blk; Khmer                            ; Khmer
 blk; Khmer_Symbols                    ; Khmer_Symbols
+blk; Khojki                           ; Khojki
+blk; Khudawadi                        ; Khudawadi
 blk; Lao                              ; Lao
 blk; Latin_1_Sup                      ; Latin_1_Supplement               ; Latin_1
 blk; Latin_Ext_A                      ; Latin_Extended_A
@@ -240,22 +268,27 @@
 blk; Latin_Ext_B                      ; Latin_Extended_B
 blk; Latin_Ext_C                      ; Latin_Extended_C
 blk; Latin_Ext_D                      ; Latin_Extended_D
+blk; Latin_Ext_E                      ; Latin_Extended_E
 blk; Lepcha                           ; Lepcha
 blk; Letterlike_Symbols               ; Letterlike_Symbols
 blk; Limbu                            ; Limbu
+blk; Linear_A                         ; Linear_A
 blk; Linear_B_Ideograms               ; Linear_B_Ideograms
 blk; Linear_B_Syllabary               ; Linear_B_Syllabary
 blk; Lisu                             ; Lisu
 blk; Low_Surrogates                   ; Low_Surrogates
 blk; Lycian                           ; Lycian
 blk; Lydian                           ; Lydian
+blk; Mahajani                         ; Mahajani
 blk; Mahjong                          ; Mahjong_Tiles
 blk; Malayalam                        ; Malayalam
 blk; Mandaic                          ; Mandaic
+blk; Manichaean                       ; Manichaean
 blk; Math_Alphanum                    ; Mathematical_Alphanumeric_Symbols
 blk; Math_Operators                   ; Mathematical_Operators
 blk; Meetei_Mayek                     ; Meetei_Mayek
 blk; Meetei_Mayek_Ext                 ; Meetei_Mayek_Extensions
+blk; Mende_Kikakui                    ; Mende_Kikakui
 blk; Meroitic_Cursive                 ; Meroitic_Cursive
 blk; Meroitic_Hieroglyphs             ; Meroitic_Hieroglyphs
 blk; Miao                             ; Miao
@@ -265,12 +298,16 @@
 blk; Misc_Pictographs                 ; Miscellaneous_Symbols_And_Pictographs
 blk; Misc_Symbols                     ; Miscellaneous_Symbols
 blk; Misc_Technical                   ; Miscellaneous_Technical
+blk; Modi                             ; Modi
 blk; Modifier_Letters                 ; Spacing_Modifier_Letters
 blk; Modifier_Tone_Letters            ; Modifier_Tone_Letters
 blk; Mongolian                        ; Mongolian
+blk; Mro                              ; Mro
 blk; Music                            ; Musical_Symbols
 blk; Myanmar                          ; Myanmar
 blk; Myanmar_Ext_A                    ; Myanmar_Extended_A
+blk; Myanmar_Ext_B                    ; Myanmar_Extended_B
+blk; Nabataean                        ; Nabataean
 blk; NB                               ; No_Block
 blk; New_Tai_Lue                      ; New_Tai_Lue
 blk; NKo                              ; NKo
@@ -279,17 +316,24 @@
 blk; Ogham                            ; Ogham
 blk; Ol_Chiki                         ; Ol_Chiki
 blk; Old_Italic                       ; Old_Italic
+blk; Old_North_Arabian                ; Old_North_Arabian
+blk; Old_Permic                       ; Old_Permic
 blk; Old_Persian                      ; Old_Persian
 blk; Old_South_Arabian                ; Old_South_Arabian
 blk; Old_Turkic                       ; Old_Turkic
 blk; Oriya                            ; Oriya
+blk; Ornamental_Dingbats              ; Ornamental_Dingbats
 blk; Osmanya                          ; Osmanya
+blk; Pahawh_Hmong                     ; Pahawh_Hmong
+blk; Palmyrene                        ; Palmyrene
+blk; Pau_Cin_Hau                      ; Pau_Cin_Hau
 blk; Phags_Pa                         ; Phags_Pa
 blk; Phaistos                         ; Phaistos_Disc
 blk; Phoenician                       ; Phoenician
 blk; Phonetic_Ext                     ; Phonetic_Extensions
 blk; Phonetic_Ext_Sup                 ; Phonetic_Extensions_Supplement
 blk; Playing_Cards                    ; Playing_Cards
+blk; Psalter_Pahlavi                  ; Psalter_Pahlavi
 blk; PUA                              ; Private_Use_Area                 ; Private_Use
 blk; Punctuation                      ; General_Punctuation
 blk; Rejang                           ; Rejang
@@ -299,7 +343,10 @@
 blk; Saurashtra                       ; Saurashtra
 blk; Sharada                          ; Sharada
 blk; Shavian                          ; Shavian
+blk; Shorthand_Format_Controls        ; Shorthand_Format_Controls
+blk; Siddham                          ; Siddham
 blk; Sinhala                          ; Sinhala
+blk; Sinhala_Archaic_Numbers          ; Sinhala_Archaic_Numbers
 blk; Small_Forms                      ; Small_Form_Variants
 blk; Sora_Sompeng                     ; Sora_Sompeng
 blk; Specials                         ; Specials
@@ -307,6 +354,7 @@
 blk; Sundanese_Sup                    ; Sundanese_Supplement
 blk; Sup_Arrows_A                     ; Supplemental_Arrows_A
 blk; Sup_Arrows_B                     ; Supplemental_Arrows_B
+blk; Sup_Arrows_C                     ; Supplemental_Arrows_C
 blk; Sup_Math_Operators               ; Supplemental_Mathematical_Operators
 blk; Sup_PUA_A                        ; Supplementary_Private_Use_Area_A
 blk; Sup_PUA_B                        ; Supplementary_Private_Use_Area_B
@@ -328,6 +376,7 @@
 blk; Thai                             ; Thai
 blk; Tibetan                          ; Tibetan
 blk; Tifinagh                         ; Tifinagh
+blk; Tirhuta                          ; Tirhuta
 blk; Transport_And_Map                ; Transport_And_Map_Symbols
 blk; UCAS                             ; Unified_Canadian_Aboriginal_Syllabics; Canadian_Syllabics
 blk; UCAS_Ext                         ; Unified_Canadian_Aboriginal_Syllabics_Extended
@@ -337,6 +386,7 @@
 blk; Vertical_Forms                   ; Vertical_Forms
 blk; VS                               ; Variation_Selectors
 blk; VS_Sup                           ; Variation_Selectors_Supplement
+blk; Warang_Citi                      ; Warang_Citi
 blk; Yi_Radicals                      ; Yi_Radicals
 blk; Yi_Syllables                     ; Yi_Syllables
 blk; Yijing                           ; Yijing_Hexagram_Symbols
@@ -578,6 +628,7 @@
 gc ; Zl                               ; Line_Separator
 gc ; Zp                               ; Paragraph_Separator
 gc ; Zs                               ; Space_Separator
+# @missing: 0000..10FFFF; General_Category; Unassigned
 
 # Grapheme_Base (Gr_Base)
 
@@ -662,7 +713,6 @@
 
 InMC; Bottom                          ; Bottom
 InMC; Bottom_And_Right                ; Bottom_And_Right
-InMC; Invisible                       ; Invisible
 InMC; Left                            ; Left
 InMC; Left_And_Right                  ; Left_And_Right
 InMC; NA                              ; NA
@@ -680,17 +730,27 @@
 
 InSC; Avagraha                        ; Avagraha
 InSC; Bindu                           ; Bindu
+InSC; Brahmi_Joining_Number           ; Brahmi_Joining_Number
+InSC; Cantillation_Mark               ; Cantillation_Mark
 InSC; Consonant                       ; Consonant
 InSC; Consonant_Dead                  ; Consonant_Dead
 InSC; Consonant_Final                 ; Consonant_Final
 InSC; Consonant_Head_Letter           ; Consonant_Head_Letter
 InSC; Consonant_Medial                ; Consonant_Medial
 InSC; Consonant_Placeholder           ; Consonant_Placeholder
-InSC; Consonant_Repha                 ; Consonant_Repha
+InSC; Consonant_Preceding_Repha       ; Consonant_Preceding_Repha
 InSC; Consonant_Subjoined             ; Consonant_Subjoined
+InSC; Consonant_Succeeding_Repha      ; Consonant_Succeeding_Repha
+InSC; Gemination_Mark                 ; Gemination_Mark
+InSC; Invisible_Stacker               ; Invisible_Stacker
+InSC; Joiner                          ; Joiner
 InSC; Modifying_Letter                ; Modifying_Letter
+InSC; Non_Joiner                      ; Non_Joiner
 InSC; Nukta                           ; Nukta
+InSC; Number                          ; Number
+InSC; Number_Joiner                   ; Number_Joiner
 InSC; Other                           ; Other
+InSC; Pure_Killer                     ; Pure_Killer
 InSC; Register_Shifter                ; Register_Shifter
 InSC; Tone_Letter                     ; Tone_Letter
 InSC; Tone_Mark                       ; Tone_Mark
@@ -702,7 +762,6 @@
 
 # Jamo_Short_Name (JSN)
 
-# @missing: 0000..10FFFF; Jamo_Short_Name; <none>
 JSN; A                                ; A
 JSN; AE                               ; AE
 JSN; B                                ; B
@@ -755,6 +814,7 @@
 JSN; YI                               ; YI
 JSN; YO                               ; YO
 JSN; YU                               ; YU
+# @missing: 0000..10FFFF; Jamo_Short_Name; <none>
 
 # Join_Control (Join_C)
 
@@ -789,6 +849,33 @@
 jg ; Knotted_Heh                      ; Knotted_Heh
 jg ; Lam                              ; Lam
 jg ; Lamadh                           ; Lamadh
+jg ; Manichaean_Aleph                 ; Manichaean_Aleph
+jg ; Manichaean_Ayin                  ; Manichaean_Ayin
+jg ; Manichaean_Beth                  ; Manichaean_Beth
+jg ; Manichaean_Daleth                ; Manichaean_Daleth
+jg ; Manichaean_Dhamedh               ; Manichaean_Dhamedh
+jg ; Manichaean_Five                  ; Manichaean_Five
+jg ; Manichaean_Gimel                 ; Manichaean_Gimel
+jg ; Manichaean_Heth                  ; Manichaean_Heth
+jg ; Manichaean_Hundred               ; Manichaean_Hundred
+jg ; Manichaean_Kaph                  ; Manichaean_Kaph
+jg ; Manichaean_Lamedh                ; Manichaean_Lamedh
+jg ; Manichaean_Mem                   ; Manichaean_Mem
+jg ; Manichaean_Nun                   ; Manichaean_Nun
+jg ; Manichaean_One                   ; Manichaean_One
+jg ; Manichaean_Pe                    ; Manichaean_Pe
+jg ; Manichaean_Qoph                  ; Manichaean_Qoph
+jg ; Manichaean_Resh                  ; Manichaean_Resh
+jg ; Manichaean_Sadhe                 ; Manichaean_Sadhe
+jg ; Manichaean_Samekh                ; Manichaean_Samekh
+jg ; Manichaean_Taw                   ; Manichaean_Taw
+jg ; Manichaean_Ten                   ; Manichaean_Ten
+jg ; Manichaean_Teth                  ; Manichaean_Teth
+jg ; Manichaean_Thamedh               ; Manichaean_Thamedh
+jg ; Manichaean_Twenty                ; Manichaean_Twenty
+jg ; Manichaean_Waw                   ; Manichaean_Waw
+jg ; Manichaean_Yodh                  ; Manichaean_Yodh
+jg ; Manichaean_Zayin                 ; Manichaean_Zayin
 jg ; Meem                             ; Meem
 jg ; Mim                              ; Mim
 jg ; No_Joining_Group                 ; No_Joining_Group
@@ -806,6 +893,7 @@
 jg ; Seen                             ; Seen
 jg ; Semkath                          ; Semkath
 jg ; Shin                             ; Shin
+jg ; Straight_Waw                     ; Straight_Waw
 jg ; Swash_Kaf                        ; Swash_Kaf
 jg ; Syriac_Waw                       ; Syriac_Waw
 jg ; Tah                              ; Tah
@@ -884,6 +972,10 @@
 Lower; N                              ; No                               ; F                                ; False
 Lower; Y                              ; Yes                              ; T                                ; True
 
+# Lowercase_Mapping (lc)
+
+# @missing: 0000..10FFFF; Lowercase_Mapping; <code point>
+
 # Math (Math)
 
 Math; N                               ; No                               ; F                                ; False
@@ -1006,12 +1098,14 @@
 
 # Script (sc)
 
+sc ; Aghb                             ; Caucasian_Albanian
 sc ; Arab                             ; Arabic
 sc ; Armi                             ; Imperial_Aramaic
 sc ; Armn                             ; Armenian
 sc ; Avst                             ; Avestan
 sc ; Bali                             ; Balinese
 sc ; Bamu                             ; Bamum
+sc ; Bass                             ; Bassa_Vah
 sc ; Batk                             ; Batak
 sc ; Beng                             ; Bengali
 sc ; Bopo                             ; Bopomofo
@@ -1029,11 +1123,14 @@
 sc ; Cyrl                             ; Cyrillic
 sc ; Deva                             ; Devanagari
 sc ; Dsrt                             ; Deseret
+sc ; Dupl                             ; Duployan
 sc ; Egyp                             ; Egyptian_Hieroglyphs
+sc ; Elba                             ; Elbasan
 sc ; Ethi                             ; Ethiopic
 sc ; Geor                             ; Georgian
 sc ; Glag                             ; Glagolitic
 sc ; Goth                             ; Gothic
+sc ; Gran                             ; Grantha
 sc ; Grek                             ; Greek
 sc ; Gujr                             ; Gujarati
 sc ; Guru                             ; Gurmukhi
@@ -1042,6 +1139,7 @@
 sc ; Hano                             ; Hanunoo
 sc ; Hebr                             ; Hebrew
 sc ; Hira                             ; Hiragana
+sc ; Hmng                             ; Pahawh_Hmong
 sc ; Hrkt                             ; Katakana_Or_Hiragana
 sc ; Ital                             ; Old_Italic
 sc ; Java                             ; Javanese
@@ -1049,6 +1147,7 @@
 sc ; Kana                             ; Katakana
 sc ; Khar                             ; Kharoshthi
 sc ; Khmr                             ; Khmer
+sc ; Khoj                             ; Khojki
 sc ; Knda                             ; Kannada
 sc ; Kthi                             ; Kaithi
 sc ; Lana                             ; Tai_Tham
@@ -1056,25 +1155,37 @@
 sc ; Latn                             ; Latin
 sc ; Lepc                             ; Lepcha
 sc ; Limb                             ; Limbu
+sc ; Lina                             ; Linear_A
 sc ; Linb                             ; Linear_B
 sc ; Lisu                             ; Lisu
 sc ; Lyci                             ; Lycian
 sc ; Lydi                             ; Lydian
+sc ; Mahj                             ; Mahajani
 sc ; Mand                             ; Mandaic
+sc ; Mani                             ; Manichaean
+sc ; Mend                             ; Mende_Kikakui
 sc ; Merc                             ; Meroitic_Cursive
 sc ; Mero                             ; Meroitic_Hieroglyphs
 sc ; Mlym                             ; Malayalam
+sc ; Modi                             ; Modi
 sc ; Mong                             ; Mongolian
+sc ; Mroo                             ; Mro
 sc ; Mtei                             ; Meetei_Mayek
 sc ; Mymr                             ; Myanmar
+sc ; Narb                             ; Old_North_Arabian
+sc ; Nbat                             ; Nabataean
 sc ; Nkoo                             ; Nko
 sc ; Ogam                             ; Ogham
 sc ; Olck                             ; Ol_Chiki
 sc ; Orkh                             ; Old_Turkic
 sc ; Orya                             ; Oriya
 sc ; Osma                             ; Osmanya
+sc ; Palm                             ; Palmyrene
+sc ; Pauc                             ; Pau_Cin_Hau
+sc ; Perm                             ; Old_Permic
 sc ; Phag                             ; Phags_Pa
 sc ; Phli                             ; Inscriptional_Pahlavi
+sc ; Phlp                             ; Psalter_Pahlavi
 sc ; Phnx                             ; Phoenician
 sc ; Plrd                             ; Miao
 sc ; Prti                             ; Inscriptional_Parthian
@@ -1085,6 +1196,8 @@
 sc ; Saur                             ; Saurashtra
 sc ; Shaw                             ; Shavian
 sc ; Shrd                             ; Sharada
+sc ; Sidd                             ; Siddham
+sc ; Sind                             ; Khudawadi
 sc ; Sinh                             ; Sinhala
 sc ; Sora                             ; Sora_Sompeng
 sc ; Sund                             ; Sundanese
@@ -1102,8 +1215,10 @@
 sc ; Thaa                             ; Thaana
 sc ; Thai                             ; Thai
 sc ; Tibt                             ; Tibetan
+sc ; Tirh                             ; Tirhuta
 sc ; Ugar                             ; Ugaritic
 sc ; Vaii                             ; Vai
+sc ; Wara                             ; Warang_Citi
 sc ; Xpeo                             ; Old_Persian
 sc ; Xsux                             ; Cuneiform
 sc ; Yiii                             ; Yi
@@ -1159,6 +1274,10 @@
 Term; N                               ; No                               ; F                                ; False
 Term; Y                               ; Yes                              ; T                                ; True
 
+# Titlecase_Mapping (tc)
+
+# @missing: 0000..10FFFF; Titlecase_Mapping; <code point>
+
 # Unicode_1_Name (na1)
 
 # @missing: 0000..10FFFF; Unicode_1_Name; <none>
@@ -1173,6 +1292,10 @@
 Upper; N                              ; No                               ; F                                ; False
 Upper; Y                              ; Yes                              ; T                                ; True
 
+# Uppercase_Mapping (uc)
+
+# @missing: 0000..10FFFF; Uppercase_Mapping; <code point>
+
 # Variation_Selector (VS)
 
 VS ; N                                ; No                               ; F                                ; False
@@ -1186,9 +1309,11 @@
 # Word_Break (WB)
 
 WB ; CR                               ; CR
+WB ; DQ                               ; Double_Quote
 WB ; EX                               ; ExtendNumLet
 WB ; Extend                           ; Extend
 WB ; FO                               ; Format
+WB ; HL                               ; Hebrew_Letter
 WB ; KA                               ; Katakana
 WB ; LE                               ; ALetter
 WB ; LF                               ; LF
@@ -1198,6 +1323,7 @@
 WB ; NL                               ; Newline
 WB ; NU                               ; Numeric
 WB ; RI                               ; Regional_Indicator
+WB ; SQ                               ; Single_Quote
 WB ; XX                               ; Other
 
 # XID_Continue (XIDC)
--- a/jdk/test/java/lang/Character/Scripts.txt	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/lang/Character/Scripts.txt	Wed Jul 05 20:42:36 2017 +0200
@@ -1,8 +1,8 @@
-# Scripts-6.2.0.txt
-# Date: 2012-06-04, 17:21:29 GMT [MD]
+# Scripts-7.0.0.txt
+# Date: 2014-05-15, 00:11:35 GMT [MD]
 #
 # Unicode Character Database
-# Copyright (c) 1991-2012 Unicode, Inc.
+# Copyright (c) 1991-2014 Unicode, Inc.
 # For terms of use, see http://www.unicode.org/terms_of_use.html
 # For documentation, see http://www.unicode.org/reports/tr44/
 
@@ -83,8 +83,10 @@
 0385          ; Common # Sk       GREEK DIALYTIKA TONOS
 0387          ; Common # Po       GREEK ANO TELEIA
 0589          ; Common # Po       ARMENIAN FULL STOP
+0605          ; Common # Cf       ARABIC NUMBER MARK ABOVE
 060C          ; Common # Po       ARABIC COMMA
 061B          ; Common # Po       ARABIC SEMICOLON
+061C          ; Common # Cf       ARABIC LETTER MARK
 061F          ; Common # Po       ARABIC QUESTION MARK
 0640          ; Common # Lm       ARABIC TATWEEL
 0660..0669    ; Common # Nd  [10] ARABIC-INDIC DIGIT ZERO..ARABIC-INDIC DIGIT NINE
@@ -136,7 +138,7 @@
 2055..205E    ; Common # Po  [10] FLOWER PUNCTUATION MARK..VERTICAL FOUR DOTS
 205F          ; Common # Zs       MEDIUM MATHEMATICAL SPACE
 2060..2064    ; Common # Cf   [5] WORD JOINER..INVISIBLE PLUS
-206A..206F    ; Common # Cf   [6] INHIBIT SYMMETRIC SWAPPING..NOMINAL DIGIT SHAPES
+2066..206F    ; Common # Cf  [10] LEFT-TO-RIGHT ISOLATE..NOMINAL DIGIT SHAPES
 2070          ; Common # No       SUPERSCRIPT ZERO
 2074..2079    ; Common # No   [6] SUPERSCRIPT FOUR..SUPERSCRIPT NINE
 207A..207C    ; Common # Sm   [3] SUPERSCRIPT PLUS SIGN..SUPERSCRIPT EQUALS SIGN
@@ -146,7 +148,7 @@
 208A..208C    ; Common # Sm   [3] SUBSCRIPT PLUS SIGN..SUBSCRIPT EQUALS SIGN
 208D          ; Common # Ps       SUBSCRIPT LEFT PARENTHESIS
 208E          ; Common # Pe       SUBSCRIPT RIGHT PARENTHESIS
-20A0..20BA    ; Common # Sc  [27] EURO-CURRENCY SIGN..TURKISH LIRA SIGN
+20A0..20BD    ; Common # Sc  [30] EURO-CURRENCY SIGN..RUBLE SIGN
 2100..2101    ; Common # So   [2] ACCOUNT OF..ADDRESSED TO THE SUBJECT
 2102          ; Common # L&       DOUBLE-STRUCK CAPITAL C
 2103..2106    ; Common # So   [4] DEGREE CELSIUS..CADA UNA
@@ -200,7 +202,10 @@
 21D5..21F3    ; Common # So  [31] UP DOWN DOUBLE ARROW..UP DOWN WHITE ARROW
 21F4..22FF    ; Common # Sm [268] RIGHT ARROW WITH SMALL CIRCLE..Z NOTATION BAG MEMBERSHIP
 2300..2307    ; Common # So   [8] DIAMETER SIGN..WAVY LINE
-2308..230B    ; Common # Sm   [4] LEFT CEILING..RIGHT FLOOR
+2308          ; Common # Ps       LEFT CEILING
+2309          ; Common # Pe       RIGHT CEILING
+230A          ; Common # Ps       LEFT FLOOR
+230B          ; Common # Pe       RIGHT FLOOR
 230C..231F    ; Common # So  [20] BOTTOM RIGHT CROP..BOTTOM RIGHT CORNER
 2320..2321    ; Common # Sm   [2] TOP HALF INTEGRAL..BOTTOM HALF INTEGRAL
 2322..2328    ; Common # So   [7] FROWN..KEYBOARD
@@ -212,7 +217,7 @@
 239B..23B3    ; Common # Sm  [25] LEFT PARENTHESIS UPPER HOOK..SUMMATION BOTTOM
 23B4..23DB    ; Common # So  [40] TOP SQUARE BRACKET..FUSE
 23DC..23E1    ; Common # Sm   [6] TOP PARENTHESIS..BOTTOM TORTOISE SHELL BRACKET
-23E2..23F3    ; Common # So  [18] WHITE TRAPEZIUM..HOURGLASS WITH FLOWING SAND
+23E2..23FA    ; Common # So  [25] WHITE TRAPEZIUM..BLACK CIRCLE FOR RECORD
 2400..2426    ; Common # So  [39] SYMBOL FOR NULL..SYMBOL FOR SUBSTITUTE FORM TWO
 2440..244A    ; Common # So  [11] OCR HOOK..OCR DOUBLE BACKSLASH
 2460..249B    ; Common # No  [60] CIRCLED DIGIT ONE..NUMBER TWENTY FULL STOP
@@ -226,8 +231,7 @@
 25F8..25FF    ; Common # Sm   [8] UPPER LEFT TRIANGLE..LOWER RIGHT TRIANGLE
 2600..266E    ; Common # So [111] BLACK SUN WITH RAYS..MUSIC NATURAL SIGN
 266F          ; Common # Sm       MUSIC SHARP SIGN
-2670..26FF    ; Common # So [144] WEST SYRIAC CROSS..WHITE FLAG WITH HORIZONTAL MIDDLE BLACK STRIPE
-2701..2767    ; Common # So [103] UPPER BLADE SCISSORS..ROTATED FLORAL HEART BULLET
+2670..2767    ; Common # So [248] WEST SYRIAC CROSS..ROTATED FLORAL HEART BULLET
 2768          ; Common # Ps       MEDIUM LEFT PARENTHESIS ORNAMENT
 2769          ; Common # Pe       MEDIUM RIGHT PARENTHESIS ORNAMENT
 276A          ; Common # Ps       MEDIUM FLATTENED LEFT PARENTHESIS ORNAMENT
@@ -295,7 +299,11 @@
 2B30..2B44    ; Common # Sm  [21] LEFT ARROW WITH SMALL CIRCLE..RIGHTWARDS ARROW THROUGH SUPERSET
 2B45..2B46    ; Common # So   [2] LEFTWARDS QUADRUPLE ARROW..RIGHTWARDS QUADRUPLE ARROW
 2B47..2B4C    ; Common # Sm   [6] REVERSE TILDE OPERATOR ABOVE RIGHTWARDS ARROW..RIGHTWARDS ARROW ABOVE REVERSE TILDE OPERATOR
-2B50..2B59    ; Common # So  [10] WHITE MEDIUM STAR..HEAVY CIRCLED SALTIRE
+2B4D..2B73    ; Common # So  [39] DOWNWARDS TRIANGLE-HEADED ZIGZAG ARROW..DOWNWARDS TRIANGLE-HEADED ARROW TO BAR
+2B76..2B95    ; Common # So  [32] NORTH WEST TRIANGLE-HEADED ARROW TO BAR..RIGHTWARDS BLACK ARROW
+2B98..2BB9    ; Common # So  [34] THREE-D TOP-LIGHTED LEFTWARDS EQUILATERAL ARROWHEAD..UP ARROWHEAD IN A RECTANGLE BOX
+2BBD..2BC8    ; Common # So  [12] BALLOT BOX WITH LIGHT X..BLACK MEDIUM RIGHT-POINTING TRIANGLE CENTRED
+2BCA..2BD1    ; Common # So   [8] TOP HALF BLACK CIRCLE..UNCERTAINTY SIGN
 2E00..2E01    ; Common # Po   [2] RIGHT ANGLE SUBSTITUTION MARKER..RIGHT ANGLE DOTTED SUBSTITUTION MARKER
 2E02          ; Common # Pi       LEFT SUBSTITUTION BRACKET
 2E03          ; Common # Pf       RIGHT SUBSTITUTION BRACKET
@@ -329,6 +337,10 @@
 2E2F          ; Common # Lm       VERTICAL TILDE
 2E30..2E39    ; Common # Po  [10] RING POINT..TOP HALF SECTION SIGN
 2E3A..2E3B    ; Common # Pd   [2] TWO-EM DASH..THREE-EM DASH
+2E3C..2E3F    ; Common # Po   [4] STENOGRAPHIC FULL STOP..CAPITULUM
+2E40          ; Common # Pd       DOUBLE HYPHEN
+2E41          ; Common # Po       REVERSED COMMA
+2E42          ; Common # Ps       DOUBLE LOW-REVERSED-9 QUOTATION MARK
 2FF0..2FFB    ; Common # So  [12] IDEOGRAPHIC DESCRIPTION CHARACTER LEFT TO RIGHT..IDEOGRAPHIC DESCRIPTION CHARACTER OVERLAID
 3000          ; Common # Zs       IDEOGRAPHIC SPACE
 3001..3003    ; Common # Po   [3] IDEOGRAPHIC COMMA..DITTO MARK
@@ -392,9 +404,11 @@
 A836..A837    ; Common # So   [2] NORTH INDIC QUARTER MARK..NORTH INDIC PLACEHOLDER MARK
 A838          ; Common # Sc       NORTH INDIC RUPEE MARK
 A839          ; Common # So       NORTH INDIC QUANTITY MARK
-FD3E          ; Common # Ps       ORNATE LEFT PARENTHESIS
-FD3F          ; Common # Pe       ORNATE RIGHT PARENTHESIS
-FDFD          ; Common # So       ARABIC LIGATURE BISMILLAH AR-RAHMAN AR-RAHEEM
+A92E          ; Common # Po       KAYAH LI SIGN CWI
+A9CF          ; Common # Lm       JAVANESE PANGRANGKEP
+AB5B          ; Common # Sk       MODIFIER BREVE WITH INVERTED BREVE
+FD3E          ; Common # Pe       ORNATE LEFT PARENTHESIS
+FD3F          ; Common # Ps       ORNATE RIGHT PARENTHESIS
 FE10..FE16    ; Common # Po   [7] PRESENTATION FORM FOR VERTICAL COMMA..PRESENTATION FORM FOR VERTICAL QUESTION MARK
 FE17          ; Common # Ps       PRESENTATION FORM FOR VERTICAL LEFT WHITE LENTICULAR BRACKET
 FE18          ; Common # Pe       PRESENTATION FORM FOR VERTICAL RIGHT WHITE LENTICULAR BRAKCET
@@ -487,6 +501,8 @@
 10137..1013F  ; Common # So   [9] AEGEAN WEIGHT BASE UNIT..AEGEAN MEASURE THIRD SUBUNIT
 10190..1019B  ; Common # So  [12] ROMAN SEXTANS SIGN..ROMAN CENTURIAL SIGN
 101D0..101FC  ; Common # So  [45] PHAISTOS DISC SIGN PEDESTRIAN..PHAISTOS DISC SIGN WAVY BAND
+102E1..102FB  ; Common # No  [27] COPTIC EPACT DIGIT ONE..COPTIC EPACT NUMBER NINE HUNDRED
+1BCA0..1BCA3  ; Common # Cf   [4] SHORTHAND FORMAT LETTER OVERLAP..SHORTHAND FORMAT UP STEP
 1D000..1D0F5  ; Common # So [246] BYZANTINE MUSICAL SYMBOL PSILI..BYZANTINE MUSICAL SYMBOL GORGON NEO KATO
 1D100..1D126  ; Common # So  [39] MUSICAL SYMBOL SINGLE BARLINE..MUSICAL SYMBOL DRUM CLEF-2
 1D129..1D164  ; Common # So  [60] MUSICAL SYMBOL MULTIPLE MEASURE REST..MUSICAL SYMBOL ONE HUNDRED TWENTY-EIGHTH NOTE
@@ -543,10 +559,10 @@
 1F000..1F02B  ; Common # So  [44] MAHJONG TILE EAST WIND..MAHJONG TILE BACK
 1F030..1F093  ; Common # So [100] DOMINO TILE HORIZONTAL BACK..DOMINO TILE VERTICAL-06-06
 1F0A0..1F0AE  ; Common # So  [15] PLAYING CARD BACK..PLAYING CARD KING OF SPADES
-1F0B1..1F0BE  ; Common # So  [14] PLAYING CARD ACE OF HEARTS..PLAYING CARD KING OF HEARTS
+1F0B1..1F0BF  ; Common # So  [15] PLAYING CARD ACE OF HEARTS..PLAYING CARD RED JOKER
 1F0C1..1F0CF  ; Common # So  [15] PLAYING CARD ACE OF DIAMONDS..PLAYING CARD BLACK JOKER
-1F0D1..1F0DF  ; Common # So  [15] PLAYING CARD ACE OF CLUBS..PLAYING CARD WHITE JOKER
-1F100..1F10A  ; Common # No  [11] DIGIT ZERO FULL STOP..DIGIT NINE COMMA
+1F0D1..1F0F5  ; Common # So  [37] PLAYING CARD ACE OF CLUBS..PLAYING CARD TRUMP-21
+1F100..1F10C  ; Common # No  [13] DIGIT ZERO FULL STOP..DINGBAT NEGATIVE CIRCLED SANS-SERIF DIGIT ZERO
 1F110..1F12E  ; Common # So  [31] PARENTHESIZED LATIN CAPITAL LETTER A..CIRCLED WZ
 1F130..1F16B  ; Common # So  [60] SQUARED LATIN CAPITAL LETTER A..RAISED MD SIGN
 1F170..1F19A  ; Common # So  [43] NEGATIVE SQUARED LATIN CAPITAL LETTER A..SQUARED VS
@@ -555,28 +571,29 @@
 1F210..1F23A  ; Common # So  [43] SQUARED CJK UNIFIED IDEOGRAPH-624B..SQUARED CJK UNIFIED IDEOGRAPH-55B6
 1F240..1F248  ; Common # So   [9] TORTOISE SHELL BRACKETED CJK UNIFIED IDEOGRAPH-672C..TORTOISE SHELL BRACKETED CJK UNIFIED IDEOGRAPH-6557
 1F250..1F251  ; Common # So   [2] CIRCLED IDEOGRAPH ADVANTAGE..CIRCLED IDEOGRAPH ACCEPT
-1F300..1F320  ; Common # So  [33] CYCLONE..SHOOTING STAR
-1F330..1F335  ; Common # So   [6] CHESTNUT..CACTUS
-1F337..1F37C  ; Common # So  [70] TULIP..BABY BOTTLE
-1F380..1F393  ; Common # So  [20] RIBBON..GRADUATION CAP
-1F3A0..1F3C4  ; Common # So  [37] CAROUSEL HORSE..SURFER
-1F3C6..1F3CA  ; Common # So   [5] TROPHY..SWIMMER
-1F3E0..1F3F0  ; Common # So  [17] HOUSE BUILDING..EUROPEAN CASTLE
-1F400..1F43E  ; Common # So  [63] RAT..PAW PRINTS
-1F440         ; Common # So       EYES
-1F442..1F4F7  ; Common # So [182] EAR..CAMERA
-1F4F9..1F4FC  ; Common # So   [4] VIDEO CAMERA..VIDEOCASSETTE
-1F500..1F53D  ; Common # So  [62] TWISTED RIGHTWARDS ARROWS..DOWN-POINTING SMALL RED TRIANGLE
-1F540..1F543  ; Common # So   [4] CIRCLED CROSS POMMEE..NOTCHED LEFT SEMICIRCLE WITH THREE DOTS
-1F550..1F567  ; Common # So  [24] CLOCK FACE ONE OCLOCK..CLOCK FACE TWELVE-THIRTY
-1F5FB..1F640  ; Common # So  [70] MOUNT FUJI..WEARY CAT FACE
-1F645..1F64F  ; Common # So  [11] FACE WITH NO GOOD GESTURE..PERSON WITH FOLDED HANDS
-1F680..1F6C5  ; Common # So  [70] ROCKET..LEFT LUGGAGE
+1F300..1F32C  ; Common # So  [45] CYCLONE..WIND BLOWING FACE
+1F330..1F37D  ; Common # So  [78] CHESTNUT..FORK AND KNIFE WITH PLATE
+1F380..1F3CE  ; Common # So  [79] RIBBON..RACING CAR
+1F3D4..1F3F7  ; Common # So  [36] SNOW CAPPED MOUNTAIN..LABEL
+1F400..1F4FE  ; Common # So [255] RAT..PORTABLE STEREO
+1F500..1F54A  ; Common # So  [75] TWISTED RIGHTWARDS ARROWS..DOVE OF PEACE
+1F550..1F579  ; Common # So  [42] CLOCK FACE ONE OCLOCK..JOYSTICK
+1F57B..1F5A3  ; Common # So  [41] LEFT HAND TELEPHONE RECEIVER..BLACK DOWN POINTING BACKHAND INDEX
+1F5A5..1F642  ; Common # So [158] DESKTOP COMPUTER..SLIGHTLY SMILING FACE
+1F645..1F6CF  ; Common # So [139] FACE WITH NO GOOD GESTURE..BED
+1F6E0..1F6EC  ; Common # So  [13] HAMMER AND WRENCH..AIRPLANE ARRIVING
+1F6F0..1F6F3  ; Common # So   [4] SATELLITE..PASSENGER SHIP
 1F700..1F773  ; Common # So [116] ALCHEMICAL SYMBOL FOR QUINTESSENCE..ALCHEMICAL SYMBOL FOR HALF OUNCE
+1F780..1F7D4  ; Common # So  [85] BLACK LEFT-POINTING ISOSCELES RIGHT TRIANGLE..HEAVY TWELVE POINTED PINWHEEL STAR
+1F800..1F80B  ; Common # So  [12] LEFTWARDS ARROW WITH SMALL TRIANGLE ARROWHEAD..DOWNWARDS ARROW WITH LARGE TRIANGLE ARROWHEAD
+1F810..1F847  ; Common # So  [56] LEFTWARDS ARROW WITH SMALL EQUILATERAL ARROWHEAD..DOWNWARDS HEAVY ARROW
+1F850..1F859  ; Common # So  [10] LEFTWARDS SANS-SERIF ARROW..UP DOWN SANS-SERIF ARROW
+1F860..1F887  ; Common # So  [40] WIDE-HEADED LEFTWARDS LIGHT BARB ARROW..WIDE-HEADED SOUTH WEST VERY HEAVY BARB ARROW
+1F890..1F8AD  ; Common # So  [30] LEFTWARDS TRIANGLE ARROWHEAD..WHITE ARROW SHAFT WIDTH TWO THIRDS
 E0001         ; Common # Cf       LANGUAGE TAG
 E0020..E007F  ; Common # Cf  [96] TAG SPACE..CANCEL TAG
 
-# Total code points: 6413
+# Total code points: 7129
 
 # ================================================
 
@@ -618,16 +635,20 @@
 A770          ; Latin # Lm       MODIFIER LETTER US
 A771..A787    ; Latin # L&  [23] LATIN SMALL LETTER DUM..LATIN SMALL LETTER INSULAR T
 A78B..A78E    ; Latin # L&   [4] LATIN CAPITAL LETTER SALTILLO..LATIN SMALL LETTER L WITH RETROFLEX HOOK AND BELT
-A790..A793    ; Latin # L&   [4] LATIN CAPITAL LETTER N WITH DESCENDER..LATIN SMALL LETTER C WITH BAR
-A7A0..A7AA    ; Latin # L&  [11] LATIN CAPITAL LETTER G WITH OBLIQUE STROKE..LATIN CAPITAL LETTER H WITH HOOK
+A790..A7AD    ; Latin # L&  [30] LATIN CAPITAL LETTER N WITH DESCENDER..LATIN CAPITAL LETTER L WITH BELT
+A7B0..A7B1    ; Latin # L&   [2] LATIN CAPITAL LETTER TURNED K..LATIN CAPITAL LETTER TURNED T
+A7F7          ; Latin # Lo       LATIN EPIGRAPHIC LETTER SIDEWAYS I
 A7F8..A7F9    ; Latin # Lm   [2] MODIFIER LETTER CAPITAL H WITH STROKE..MODIFIER LETTER SMALL LIGATURE OE
 A7FA          ; Latin # L&       LATIN LETTER SMALL CAPITAL TURNED M
 A7FB..A7FF    ; Latin # Lo   [5] LATIN EPIGRAPHIC LETTER REVERSED F..LATIN EPIGRAPHIC LETTER ARCHAIC M
+AB30..AB5A    ; Latin # L&  [43] LATIN SMALL LETTER BARRED ALPHA..LATIN SMALL LETTER Y WITH SHORT RIGHT LEG
+AB5C..AB5F    ; Latin # Lm   [4] MODIFIER LETTER SMALL HENG..MODIFIER LETTER SMALL U WITH LEFT HOOK
+AB64          ; Latin # L&       LATIN SMALL LETTER INVERTED ALPHA
 FB00..FB06    ; Latin # L&   [7] LATIN SMALL LIGATURE FF..LATIN SMALL LIGATURE ST
 FF21..FF3A    ; Latin # L&  [26] FULLWIDTH LATIN CAPITAL LETTER A..FULLWIDTH LATIN CAPITAL LETTER Z
 FF41..FF5A    ; Latin # L&  [26] FULLWIDTH LATIN SMALL LETTER A..FULLWIDTH LATIN SMALL LETTER Z
 
-# Total code points: 1272
+# Total code points: 1338
 
 # ================================================
 
@@ -636,6 +657,7 @@
 0376..0377    ; Greek # L&   [2] GREEK CAPITAL LETTER PAMPHYLIAN DIGAMMA..GREEK SMALL LETTER PAMPHYLIAN DIGAMMA
 037A          ; Greek # Lm       GREEK YPOGEGRAMMENI
 037B..037D    ; Greek # L&   [3] GREEK SMALL REVERSED LUNATE SIGMA SYMBOL..GREEK SMALL REVERSED DOTTED LUNATE SIGMA SYMBOL
+037F          ; Greek # L&       GREEK CAPITAL LETTER YOT
 0384          ; Greek # Sk       GREEK TONOS
 0386          ; Greek # L&       GREEK CAPITAL LETTER ALPHA WITH TONOS
 0388..038A    ; Greek # L&   [3] GREEK CAPITAL LETTER EPSILON WITH TONOS..GREEK CAPITAL LETTER IOTA WITH TONOS
@@ -675,15 +697,18 @@
 1FF6..1FFC    ; Greek # L&   [7] GREEK SMALL LETTER OMEGA WITH PERISPOMENI..GREEK CAPITAL LETTER OMEGA WITH PROSGEGRAMMENI
 1FFD..1FFE    ; Greek # Sk   [2] GREEK OXIA..GREEK DASIA
 2126          ; Greek # L&       OHM SIGN
+AB65          ; Greek # L&       GREEK LETTER SMALL CAPITAL OMEGA
 10140..10174  ; Greek # Nl  [53] GREEK ACROPHONIC ATTIC ONE QUARTER..GREEK ACROPHONIC STRATIAN FIFTY MNAS
 10175..10178  ; Greek # No   [4] GREEK ONE HALF SIGN..GREEK THREE QUARTERS SIGN
 10179..10189  ; Greek # So  [17] GREEK YEAR SIGN..GREEK TRYBLION BASE SIGN
-1018A         ; Greek # No       GREEK ZERO SIGN
+1018A..1018B  ; Greek # No   [2] GREEK ZERO SIGN..GREEK ONE QUARTER SIGN
+1018C         ; Greek # So       GREEK SINUSOID SIGN
+101A0         ; Greek # So       GREEK SYMBOL TAU RHO
 1D200..1D241  ; Greek # So  [66] GREEK VOCAL NOTATION SYMBOL-1..GREEK INSTRUMENTAL NOTATION SYMBOL-54
 1D242..1D244  ; Greek # Mn   [3] COMBINING GREEK MUSICAL TRISEME..COMBINING GREEK MUSICAL PENTASEME
 1D245         ; Greek # So       GREEK MUSICAL LEIMMA
 
-# Total code points: 511
+# Total code points: 516
 
 # ================================================
 
@@ -692,7 +717,7 @@
 0483..0484    ; Cyrillic # Mn   [2] COMBINING CYRILLIC TITLO..COMBINING CYRILLIC PALATALIZATION
 0487          ; Cyrillic # Mn       COMBINING CYRILLIC POKRYTIE
 0488..0489    ; Cyrillic # Me   [2] COMBINING CYRILLIC HUNDRED THOUSANDS SIGN..COMBINING CYRILLIC MILLIONS SIGN
-048A..0527    ; Cyrillic # L& [158] CYRILLIC CAPITAL LETTER SHORT I WITH TAIL..CYRILLIC SMALL LETTER SHHA WITH DESCENDER
+048A..052F    ; Cyrillic # L& [166] CYRILLIC CAPITAL LETTER SHORT I WITH TAIL..CYRILLIC SMALL LETTER EL WITH DESCENDER
 1D2B          ; Cyrillic # L&       CYRILLIC LETTER SMALL CAPITAL EL
 1D78          ; Cyrillic # Lm       MODIFIER LETTER CYRILLIC EN
 2DE0..2DFF    ; Cyrillic # Mn  [32] COMBINING CYRILLIC LETTER BE..COMBINING CYRILLIC LETTER IOTIFIED BIG YUS
@@ -704,10 +729,11 @@
 A674..A67D    ; Cyrillic # Mn  [10] COMBINING CYRILLIC LETTER UKRAINIAN IE..COMBINING CYRILLIC PAYEROK
 A67E          ; Cyrillic # Po       CYRILLIC KAVYKA
 A67F          ; Cyrillic # Lm       CYRILLIC PAYEROK
-A680..A697    ; Cyrillic # L&  [24] CYRILLIC CAPITAL LETTER DWE..CYRILLIC SMALL LETTER SHWE
+A680..A69B    ; Cyrillic # L&  [28] CYRILLIC CAPITAL LETTER DWE..CYRILLIC SMALL LETTER CROSSED O
+A69C..A69D    ; Cyrillic # Lm   [2] MODIFIER LETTER CYRILLIC HARD SIGN..MODIFIER LETTER CYRILLIC SOFT SIGN
 A69F          ; Cyrillic # Mn       COMBINING CYRILLIC LETTER IOTIFIED E
 
-# Total code points: 417
+# Total code points: 431
 
 # ================================================
 
@@ -716,10 +742,11 @@
 055A..055F    ; Armenian # Po   [6] ARMENIAN APOSTROPHE..ARMENIAN ABBREVIATION MARK
 0561..0587    ; Armenian # L&  [39] ARMENIAN SMALL LETTER AYB..ARMENIAN SMALL LIGATURE ECH YIWN
 058A          ; Armenian # Pd       ARMENIAN HYPHEN
+058D..058E    ; Armenian # So   [2] RIGHT-FACING ARMENIAN ETERNITY SIGN..LEFT-FACING ARMENIAN ETERNITY SIGN
 058F          ; Armenian # Sc       ARMENIAN DRAM SIGN
 FB13..FB17    ; Armenian # L&   [5] ARMENIAN SMALL LIGATURE MEN NOW..ARMENIAN SMALL LIGATURE MEN XEH
 
-# Total code points: 91
+# Total code points: 93
 
 # ================================================
 
@@ -779,9 +806,8 @@
 06FD..06FE    ; Arabic # So   [2] ARABIC SIGN SINDHI AMPERSAND..ARABIC SIGN SINDHI POSTPOSITION MEN
 06FF          ; Arabic # Lo       ARABIC LETTER HEH WITH INVERTED V
 0750..077F    ; Arabic # Lo  [48] ARABIC LETTER BEH WITH THREE DOTS HORIZONTALLY BELOW..ARABIC LETTER KAF WITH TWO DOTS ABOVE
-08A0          ; Arabic # Lo       ARABIC LETTER BEH WITH SMALL V BELOW
-08A2..08AC    ; Arabic # Lo  [11] ARABIC LETTER JEEM WITH TWO DOTS ABOVE..ARABIC LETTER ROHINGYA YEH
-08E4..08FE    ; Arabic # Mn  [27] ARABIC CURLY FATHA..ARABIC DAMMA WITH DOT
+08A0..08B2    ; Arabic # Lo  [19] ARABIC LETTER BEH WITH SMALL V BELOW..ARABIC LETTER ZAIN WITH INVERTED V ABOVE
+08E4..08FF    ; Arabic # Mn  [28] ARABIC CURLY FATHA..ARABIC MARK SIDEWAYS NOON GHUNNA
 FB50..FBB1    ; Arabic # Lo  [98] ARABIC LETTER ALEF WASLA ISOLATED FORM..ARABIC LETTER YEH BARREE WITH HAMZA ABOVE FINAL FORM
 FBB2..FBC1    ; Arabic # Sk  [16] ARABIC SYMBOL DOT ABOVE..ARABIC SYMBOL SMALL TAH BELOW
 FBD3..FD3D    ; Arabic # Lo [363] ARABIC LETTER NG ISOLATED FORM..ARABIC LIGATURE ALEF WITH FATHATAN ISOLATED FORM
@@ -789,6 +815,7 @@
 FD92..FDC7    ; Arabic # Lo  [54] ARABIC LIGATURE MEEM WITH JEEM WITH KHAH INITIAL FORM..ARABIC LIGATURE NOON WITH JEEM WITH YEH FINAL FORM
 FDF0..FDFB    ; Arabic # Lo  [12] ARABIC LIGATURE SALLA USED AS KORANIC STOP SIGN ISOLATED FORM..ARABIC LIGATURE JALLAJALALOUHOU
 FDFC          ; Arabic # Sc       RIAL SIGN
+FDFD          ; Arabic # So       ARABIC LIGATURE BISMILLAH AR-RAHMAN AR-RAHEEM
 FE70..FE74    ; Arabic # Lo   [5] ARABIC FATHATAN ISOLATED FORM..ARABIC KASRATAN ISOLATED FORM
 FE76..FEFC    ; Arabic # Lo [135] ARABIC FATHA ISOLATED FORM..ARABIC LIGATURE LAM WITH ALEF FINAL FORM
 10E60..10E7E  ; Arabic # No  [31] RUMI DIGIT ONE..RUMI FRACTION TWO THIRDS
@@ -827,7 +854,7 @@
 1EEAB..1EEBB  ; Arabic # Lo  [17] ARABIC MATHEMATICAL DOUBLE-STRUCK LAM..ARABIC MATHEMATICAL DOUBLE-STRUCK GHAIN
 1EEF0..1EEF1  ; Arabic # Sm   [2] ARABIC MATHEMATICAL OPERATOR MEEM WITH HAH WITH TATWEEL..ARABIC MATHEMATICAL OPERATOR HAH WITH DAL
 
-# Total code points: 1235
+# Total code points: 1244
 
 # ================================================
 
@@ -870,17 +897,17 @@
 0966..096F    ; Devanagari # Nd  [10] DEVANAGARI DIGIT ZERO..DEVANAGARI DIGIT NINE
 0970          ; Devanagari # Po       DEVANAGARI ABBREVIATION SIGN
 0971          ; Devanagari # Lm       DEVANAGARI SIGN HIGH SPACING DOT
-0972..0977    ; Devanagari # Lo   [6] DEVANAGARI LETTER CANDRA A..DEVANAGARI LETTER UUE
-0979..097F    ; Devanagari # Lo   [7] DEVANAGARI LETTER ZHA..DEVANAGARI LETTER BBA
+0972..097F    ; Devanagari # Lo  [14] DEVANAGARI LETTER CANDRA A..DEVANAGARI LETTER BBA
 A8E0..A8F1    ; Devanagari # Mn  [18] COMBINING DEVANAGARI DIGIT ZERO..COMBINING DEVANAGARI SIGN AVAGRAHA
 A8F2..A8F7    ; Devanagari # Lo   [6] DEVANAGARI SIGN SPACING CANDRABINDU..DEVANAGARI SIGN CANDRABINDU AVAGRAHA
 A8F8..A8FA    ; Devanagari # Po   [3] DEVANAGARI SIGN PUSHPIKA..DEVANAGARI CARET
 A8FB          ; Devanagari # Lo       DEVANAGARI HEADSTROKE
 
-# Total code points: 151
+# Total code points: 152
 
 # ================================================
 
+0980          ; Bengali # Lo       BENGALI ANJI
 0981          ; Bengali # Mn       BENGALI SIGN CANDRABINDU
 0982..0983    ; Bengali # Mc   [2] BENGALI SIGN ANUSVARA..BENGALI SIGN VISARGA
 0985..098C    ; Bengali # Lo   [8] BENGALI LETTER A..BENGALI LETTER VOCALIC L
@@ -908,7 +935,7 @@
 09FA          ; Bengali # So       BENGALI ISSHAR
 09FB          ; Bengali # Sc       BENGALI GANDA MARK
 
-# Total code points: 92
+# Total code points: 93
 
 # ================================================
 
@@ -1025,12 +1052,12 @@
 
 # ================================================
 
+0C00          ; Telugu # Mn       TELUGU SIGN COMBINING CANDRABINDU ABOVE
 0C01..0C03    ; Telugu # Mc   [3] TELUGU SIGN CANDRABINDU..TELUGU SIGN VISARGA
 0C05..0C0C    ; Telugu # Lo   [8] TELUGU LETTER A..TELUGU LETTER VOCALIC L
 0C0E..0C10    ; Telugu # Lo   [3] TELUGU LETTER E..TELUGU LETTER AI
 0C12..0C28    ; Telugu # Lo  [23] TELUGU LETTER O..TELUGU LETTER NA
-0C2A..0C33    ; Telugu # Lo  [10] TELUGU LETTER PA..TELUGU LETTER LLA
-0C35..0C39    ; Telugu # Lo   [5] TELUGU LETTER VA..TELUGU LETTER HA
+0C2A..0C39    ; Telugu # Lo  [16] TELUGU LETTER PA..TELUGU LETTER HA
 0C3D          ; Telugu # Lo       TELUGU SIGN AVAGRAHA
 0C3E..0C40    ; Telugu # Mn   [3] TELUGU VOWEL SIGN AA..TELUGU VOWEL SIGN II
 0C41..0C44    ; Telugu # Mc   [4] TELUGU VOWEL SIGN U..TELUGU VOWEL SIGN VOCALIC RR
@@ -1044,10 +1071,11 @@
 0C78..0C7E    ; Telugu # No   [7] TELUGU FRACTION DIGIT ZERO FOR ODD POWERS OF FOUR..TELUGU FRACTION DIGIT THREE FOR EVEN POWERS OF FOUR
 0C7F          ; Telugu # So       TELUGU SIGN TUUMU
 
-# Total code points: 93
+# Total code points: 95
 
 # ================================================
 
+0C81          ; Kannada # Mn       KANNADA SIGN CANDRABINDU
 0C82..0C83    ; Kannada # Mc   [2] KANNADA SIGN ANUSVARA..KANNADA SIGN VISARGA
 0C85..0C8C    ; Kannada # Lo   [8] KANNADA LETTER A..KANNADA LETTER VOCALIC L
 0C8E..0C90    ; Kannada # Lo   [3] KANNADA LETTER E..KANNADA LETTER AI
@@ -1070,10 +1098,11 @@
 0CE6..0CEF    ; Kannada # Nd  [10] KANNADA DIGIT ZERO..KANNADA DIGIT NINE
 0CF1..0CF2    ; Kannada # Lo   [2] KANNADA SIGN JIHVAMULIYA..KANNADA SIGN UPADHMANIYA
 
-# Total code points: 86
+# Total code points: 87
 
 # ================================================
 
+0D01          ; Malayalam # Mn       MALAYALAM SIGN CANDRABINDU
 0D02..0D03    ; Malayalam # Mc   [2] MALAYALAM SIGN ANUSVARA..MALAYALAM SIGN VISARGA
 0D05..0D0C    ; Malayalam # Lo   [8] MALAYALAM LETTER A..MALAYALAM LETTER VOCALIC L
 0D0E..0D10    ; Malayalam # Lo   [3] MALAYALAM LETTER E..MALAYALAM LETTER AI
@@ -1093,7 +1122,7 @@
 0D79          ; Malayalam # So       MALAYALAM DATE MARK
 0D7A..0D7F    ; Malayalam # Lo   [6] MALAYALAM LETTER CHILLU NN..MALAYALAM LETTER CHILLU K
 
-# Total code points: 98
+# Total code points: 99
 
 # ================================================
 
@@ -1108,10 +1137,12 @@
 0DD2..0DD4    ; Sinhala # Mn   [3] SINHALA VOWEL SIGN KETTI IS-PILLA..SINHALA VOWEL SIGN KETTI PAA-PILLA
 0DD6          ; Sinhala # Mn       SINHALA VOWEL SIGN DIGA PAA-PILLA
 0DD8..0DDF    ; Sinhala # Mc   [8] SINHALA VOWEL SIGN GAETTA-PILLA..SINHALA VOWEL SIGN GAYANUKITTA
+0DE6..0DEF    ; Sinhala # Nd  [10] SINHALA LITH DIGIT ZERO..SINHALA LITH DIGIT NINE
 0DF2..0DF3    ; Sinhala # Mc   [2] SINHALA VOWEL SIGN DIGA GAETTA-PILLA..SINHALA VOWEL SIGN DIGA GAYANUKITTA
 0DF4          ; Sinhala # Po       SINHALA PUNCTUATION KUNDDALIYA
+111E1..111F4  ; Sinhala # No  [20] SINHALA ARCHAIC DIGIT ONE..SINHALA ARCHAIC NUMBER ONE THOUSAND
 
-# Total code points: 80
+# Total code points: 110
 
 # ================================================
 
@@ -1234,14 +1265,23 @@
 109A..109C    ; Myanmar # Mc   [3] MYANMAR SIGN KHAMTI TONE-1..MYANMAR VOWEL SIGN AITON A
 109D          ; Myanmar # Mn       MYANMAR VOWEL SIGN AITON AI
 109E..109F    ; Myanmar # So   [2] MYANMAR SYMBOL SHAN ONE..MYANMAR SYMBOL SHAN EXCLAMATION
+A9E0..A9E4    ; Myanmar # Lo   [5] MYANMAR LETTER SHAN GHA..MYANMAR LETTER SHAN BHA
+A9E5          ; Myanmar # Mn       MYANMAR SIGN SHAN SAW
+A9E6          ; Myanmar # Lm       MYANMAR MODIFIER LETTER SHAN REDUPLICATION
+A9E7..A9EF    ; Myanmar # Lo   [9] MYANMAR LETTER TAI LAING NYA..MYANMAR LETTER TAI LAING NNA
+A9F0..A9F9    ; Myanmar # Nd  [10] MYANMAR TAI LAING DIGIT ZERO..MYANMAR TAI LAING DIGIT NINE
+A9FA..A9FE    ; Myanmar # Lo   [5] MYANMAR LETTER TAI LAING LLA..MYANMAR LETTER TAI LAING BHA
 AA60..AA6F    ; Myanmar # Lo  [16] MYANMAR LETTER KHAMTI GA..MYANMAR LETTER KHAMTI FA
 AA70          ; Myanmar # Lm       MYANMAR MODIFIER LETTER KHAMTI REDUPLICATION
 AA71..AA76    ; Myanmar # Lo   [6] MYANMAR LETTER KHAMTI XA..MYANMAR LOGOGRAM KHAMTI HM
 AA77..AA79    ; Myanmar # So   [3] MYANMAR SYMBOL AITON EXCLAMATION..MYANMAR SYMBOL AITON TWO
 AA7A          ; Myanmar # Lo       MYANMAR LETTER AITON RA
 AA7B          ; Myanmar # Mc       MYANMAR SIGN PAO KAREN TONE
+AA7C          ; Myanmar # Mn       MYANMAR SIGN TAI LAING TONE-2
+AA7D          ; Myanmar # Mc       MYANMAR SIGN TAI LAING TONE-5
+AA7E..AA7F    ; Myanmar # Lo   [2] MYANMAR LETTER SHWE PALAUNG CHA..MYANMAR LETTER SHWE PALAUNG SHA
 
-# Total code points: 188
+# Total code points: 223
 
 # ================================================
 
@@ -1345,8 +1385,9 @@
 
 16A0..16EA    ; Runic # Lo  [75] RUNIC LETTER FEHU FEOH FE F..RUNIC LETTER X
 16EE..16F0    ; Runic # Nl   [3] RUNIC ARLAUG SYMBOL..RUNIC BELGTHOR SYMBOL
+16F1..16F8    ; Runic # Lo   [8] RUNIC LETTER K..RUNIC LETTER FRANKS CASKET AESC
 
-# Total code points: 78
+# Total code points: 86
 
 # ================================================
 
@@ -1377,7 +1418,7 @@
 1806          ; Mongolian # Pd       MONGOLIAN TODO SOFT HYPHEN
 1807..180A    ; Mongolian # Po   [4] MONGOLIAN SIBE SYLLABLE BOUNDARY MARKER..MONGOLIAN NIRUGU
 180B..180D    ; Mongolian # Mn   [3] MONGOLIAN FREE VARIATION SELECTOR ONE..MONGOLIAN FREE VARIATION SELECTOR THREE
-180E          ; Mongolian # Zs       MONGOLIAN VOWEL SEPARATOR
+180E          ; Mongolian # Cf       MONGOLIAN VOWEL SEPARATOR
 1810..1819    ; Mongolian # Nd  [10] MONGOLIAN DIGIT ZERO..MONGOLIAN DIGIT NINE
 1820..1842    ; Mongolian # Lo  [35] MONGOLIAN LETTER A..MONGOLIAN LETTER CHI
 1843          ; Mongolian # Lm       MONGOLIAN LETTER TODO LONG VOWEL SIGN
@@ -1452,10 +1493,10 @@
 
 # ================================================
 
-10300..1031E  ; Old_Italic # Lo  [31] OLD ITALIC LETTER A..OLD ITALIC LETTER UU
+10300..1031F  ; Old_Italic # Lo  [32] OLD ITALIC LETTER A..OLD ITALIC LETTER ESS
 10320..10323  ; Old_Italic # No   [4] OLD ITALIC NUMERAL ONE..OLD ITALIC NUMERAL FIFTY
 
-# Total code points: 35
+# Total code points: 36
 
 # ================================================
 
@@ -1479,12 +1520,15 @@
 064B..0655    ; Inherited # Mn  [11] ARABIC FATHATAN..ARABIC HAMZA BELOW
 0670          ; Inherited # Mn       ARABIC LETTER SUPERSCRIPT ALEF
 0951..0952    ; Inherited # Mn   [2] DEVANAGARI STRESS SIGN UDATTA..DEVANAGARI STRESS SIGN ANUDATTA
+1AB0..1ABD    ; Inherited # Mn  [14] COMBINING DOUBLED CIRCUMFLEX ACCENT..COMBINING PARENTHESES BELOW
+1ABE          ; Inherited # Me       COMBINING PARENTHESES OVERLAY
 1CD0..1CD2    ; Inherited # Mn   [3] VEDIC TONE KARSHANA..VEDIC TONE PRENKHA
 1CD4..1CE0    ; Inherited # Mn  [13] VEDIC SIGN YAJURVEDIC MIDLINE SVARITA..VEDIC TONE RIGVEDIC KASHMIRI INDEPENDENT SVARITA
 1CE2..1CE8    ; Inherited # Mn   [7] VEDIC SIGN VISARGA SVARITA..VEDIC SIGN VISARGA ANUDATTA WITH TAIL
 1CED          ; Inherited # Mn       VEDIC SIGN TIRYAK
 1CF4          ; Inherited # Mn       VEDIC TONE CANDRA ABOVE
-1DC0..1DE6    ; Inherited # Mn  [39] COMBINING DOTTED GRAVE ACCENT..COMBINING LATIN SMALL LETTER Z
+1CF8..1CF9    ; Inherited # Mn   [2] VEDIC TONE RING ABOVE..VEDIC TONE DOUBLE RING ABOVE
+1DC0..1DF5    ; Inherited # Mn  [54] COMBINING DOTTED GRAVE ACCENT..COMBINING UP TACK ABOVE
 1DFC..1DFF    ; Inherited # Mn   [4] COMBINING DOUBLE INVERTED BREVE BELOW..COMBINING RIGHT ARROWHEAD AND DOWN ARROWHEAD BELOW
 200C..200D    ; Inherited # Cf   [2] ZERO WIDTH NON-JOINER..ZERO WIDTH JOINER
 20D0..20DC    ; Inherited # Mn  [13] COMBINING LEFT HARPOON ABOVE..COMBINING FOUR DOTS ABOVE
@@ -1495,15 +1539,16 @@
 302A..302D    ; Inherited # Mn   [4] IDEOGRAPHIC LEVEL TONE MARK..IDEOGRAPHIC ENTERING TONE MARK
 3099..309A    ; Inherited # Mn   [2] COMBINING KATAKANA-HIRAGANA VOICED SOUND MARK..COMBINING KATAKANA-HIRAGANA SEMI-VOICED SOUND MARK
 FE00..FE0F    ; Inherited # Mn  [16] VARIATION SELECTOR-1..VARIATION SELECTOR-16
-FE20..FE26    ; Inherited # Mn   [7] COMBINING LIGATURE LEFT HALF..COMBINING CONJOINING MACRON
+FE20..FE2D    ; Inherited # Mn  [14] COMBINING LIGATURE LEFT HALF..COMBINING CONJOINING MACRON BELOW
 101FD         ; Inherited # Mn       PHAISTOS DISC SIGN COMBINING OBLIQUE STROKE
+102E0         ; Inherited # Mn       COPTIC EPACT THOUSANDS MARK
 1D167..1D169  ; Inherited # Mn   [3] MUSICAL SYMBOL COMBINING TREMOLO-1..MUSICAL SYMBOL COMBINING TREMOLO-3
 1D17B..1D182  ; Inherited # Mn   [8] MUSICAL SYMBOL COMBINING ACCENT..MUSICAL SYMBOL COMBINING LOURE
 1D185..1D18B  ; Inherited # Mn   [7] MUSICAL SYMBOL COMBINING DOIT..MUSICAL SYMBOL COMBINING TRIPLE TONGUE
 1D1AA..1D1AD  ; Inherited # Mn   [4] MUSICAL SYMBOL COMBINING DOWN BOW..MUSICAL SYMBOL COMBINING SNAP PIZZICATO
 E0100..E01EF  ; Inherited # Mn [240] VARIATION SELECTOR-17..VARIATION SELECTOR-256
 
-# Total code points: 523
+# Total code points: 563
 
 # ================================================
 
@@ -1537,7 +1582,7 @@
 
 # ================================================
 
-1900..191C    ; Limbu # Lo  [29] LIMBU VOWEL-CARRIER LETTER..LIMBU LETTER HA
+1900..191E    ; Limbu # Lo  [31] LIMBU VOWEL-CARRIER LETTER..LIMBU LETTER TRA
 1920..1922    ; Limbu # Mn   [3] LIMBU VOWEL SIGN A..LIMBU VOWEL SIGN U
 1923..1926    ; Limbu # Mc   [4] LIMBU VOWEL SIGN EE..LIMBU VOWEL SIGN AU
 1927..1928    ; Limbu # Mn   [2] LIMBU VOWEL SIGN E..LIMBU VOWEL SIGN O
@@ -1550,7 +1595,7 @@
 1944..1945    ; Limbu # Po   [2] LIMBU EXCLAMATION MARK..LIMBU QUESTION MARK
 1946..194F    ; Limbu # Nd  [10] LIMBU DIGIT ZERO..LIMBU DIGIT NINE
 
-# Total code points: 66
+# Total code points: 68
 
 # ================================================
 
@@ -1612,7 +1657,8 @@
 
 1A00..1A16    ; Buginese # Lo  [23] BUGINESE LETTER KA..BUGINESE LETTER HA
 1A17..1A18    ; Buginese # Mn   [2] BUGINESE VOWEL SIGN I..BUGINESE VOWEL SIGN U
-1A19..1A1B    ; Buginese # Mc   [3] BUGINESE VOWEL SIGN E..BUGINESE VOWEL SIGN AE
+1A19..1A1A    ; Buginese # Mc   [2] BUGINESE VOWEL SIGN E..BUGINESE VOWEL SIGN O
+1A1B          ; Buginese # Mn       BUGINESE VOWEL SIGN AE
 1A1E..1A1F    ; Buginese # Po   [2] BUGINESE PALLAWA..BUGINESE END OF SECTION
 
 # Total code points: 30
@@ -1724,11 +1770,11 @@
 
 # ================================================
 
-12000..1236E  ; Cuneiform # Lo [879] CUNEIFORM SIGN A..CUNEIFORM SIGN ZUM
-12400..12462  ; Cuneiform # Nl  [99] CUNEIFORM NUMERIC SIGN TWO ASH..CUNEIFORM NUMERIC SIGN OLD ASSYRIAN ONE QUARTER
-12470..12473  ; Cuneiform # Po   [4] CUNEIFORM PUNCTUATION SIGN OLD ASSYRIAN WORD DIVIDER..CUNEIFORM PUNCTUATION SIGN DIAGONAL TRICOLON
+12000..12398  ; Cuneiform # Lo [921] CUNEIFORM SIGN A..CUNEIFORM SIGN UM TIMES ME
+12400..1246E  ; Cuneiform # Nl [111] CUNEIFORM NUMERIC SIGN TWO ASH..CUNEIFORM NUMERIC SIGN NINE U VARIANT FORM
+12470..12474  ; Cuneiform # Po   [5] CUNEIFORM PUNCTUATION SIGN OLD ASSYRIAN WORD DIVIDER..CUNEIFORM PUNCTUATION SIGN DIAGONAL QUADCOLON
 
-# Total code points: 982
+# Total code points: 1037
 
 # ================================================
 
@@ -1767,8 +1813,7 @@
 1BA6..1BA7    ; Sundanese # Mc   [2] SUNDANESE VOWEL SIGN PANAELAENG..SUNDANESE VOWEL SIGN PANOLONG
 1BA8..1BA9    ; Sundanese # Mn   [2] SUNDANESE VOWEL SIGN PAMEPET..SUNDANESE VOWEL SIGN PANEULEUNG
 1BAA          ; Sundanese # Mc       SUNDANESE SIGN PAMAAEH
-1BAB          ; Sundanese # Mn       SUNDANESE SIGN VIRAMA
-1BAC..1BAD    ; Sundanese # Mc   [2] SUNDANESE CONSONANT SIGN PASANGAN MA..SUNDANESE CONSONANT SIGN PASANGAN WA
+1BAB..1BAD    ; Sundanese # Mn   [3] SUNDANESE SIGN VIRAMA..SUNDANESE CONSONANT SIGN PASANGAN WA
 1BAE..1BAF    ; Sundanese # Lo   [2] SUNDANESE LETTER KHA..SUNDANESE LETTER SYA
 1BB0..1BB9    ; Sundanese # Nd  [10] SUNDANESE DIGIT ZERO..SUNDANESE DIGIT NINE
 1BBA..1BBF    ; Sundanese # Lo   [6] SUNDANESE AVAGRAHA..SUNDANESE LETTER FINAL M
@@ -1825,9 +1870,9 @@
 A900..A909    ; Kayah_Li # Nd  [10] KAYAH LI DIGIT ZERO..KAYAH LI DIGIT NINE
 A90A..A925    ; Kayah_Li # Lo  [28] KAYAH LI LETTER KA..KAYAH LI LETTER OO
 A926..A92D    ; Kayah_Li # Mn   [8] KAYAH LI VOWEL UE..KAYAH LI TONE CALYA PLOPHU
-A92E..A92F    ; Kayah_Li # Po   [2] KAYAH LI SIGN CWI..KAYAH LI SIGN SHYA
+A92F          ; Kayah_Li # Po       KAYAH LI SIGN SHYA
 
-# Total code points: 48
+# Total code points: 47
 
 # ================================================
 
@@ -1974,11 +2019,10 @@
 A9BC          ; Javanese # Mn       JAVANESE VOWEL SIGN PEPET
 A9BD..A9C0    ; Javanese # Mc   [4] JAVANESE CONSONANT SIGN KERET..JAVANESE PANGKON
 A9C1..A9CD    ; Javanese # Po  [13] JAVANESE LEFT RERENGGAN..JAVANESE TURNED PADA PISELEH
-A9CF          ; Javanese # Lm       JAVANESE PANGRANGKEP
 A9D0..A9D9    ; Javanese # Nd  [10] JAVANESE DIGIT ZERO..JAVANESE DIGIT NINE
 A9DE..A9DF    ; Javanese # Po   [2] JAVANESE PADA TIRTA TUMETES..JAVANESE PADA ISEN-ISEN
 
-# Total code points: 91
+# Total code points: 90
 
 # ================================================
 
@@ -2080,8 +2124,9 @@
 11047..1104D  ; Brahmi # Po   [7] BRAHMI DANDA..BRAHMI PUNCTUATION LOTUS
 11052..11065  ; Brahmi # No  [20] BRAHMI NUMBER ONE..BRAHMI NUMBER ONE THOUSAND
 11066..1106F  ; Brahmi # Nd  [10] BRAHMI DIGIT ZERO..BRAHMI DIGIT NINE
+1107F         ; Brahmi # Mn       BRAHMI NUMBER JOINER
 
-# Total code points: 108
+# Total code points: 109
 
 # ================================================
 
@@ -2136,9 +2181,11 @@
 111BF..111C0  ; Sharada # Mc   [2] SHARADA VOWEL SIGN AU..SHARADA SIGN VIRAMA
 111C1..111C4  ; Sharada # Lo   [4] SHARADA SIGN AVAGRAHA..SHARADA OM
 111C5..111C8  ; Sharada # Po   [4] SHARADA DANDA..SHARADA SEPARATOR
+111CD         ; Sharada # Po       SHARADA SUTRA MARK
 111D0..111D9  ; Sharada # Nd  [10] SHARADA DIGIT ZERO..SHARADA DIGIT NINE
+111DA         ; Sharada # Lo       SHARADA EKAM
 
-# Total code points: 83
+# Total code points: 85
 
 # ================================================
 
@@ -2161,4 +2208,244 @@
 
 # Total code points: 66
 
+# ================================================
+
+10530..10563  ; Caucasian_Albanian # Lo  [52] CAUCASIAN ALBANIAN LETTER ALT..CAUCASIAN ALBANIAN LETTER KIW
+1056F         ; Caucasian_Albanian # Po       CAUCASIAN ALBANIAN CITATION MARK
+
+# Total code points: 53
+
+# ================================================
+
+16AD0..16AED  ; Bassa_Vah # Lo  [30] BASSA VAH LETTER ENNI..BASSA VAH LETTER I
+16AF0..16AF4  ; Bassa_Vah # Mn   [5] BASSA VAH COMBINING HIGH TONE..BASSA VAH COMBINING HIGH-LOW TONE
+16AF5         ; Bassa_Vah # Po       BASSA VAH FULL STOP
+
+# Total code points: 36
+
+# ================================================
+
+1BC00..1BC6A  ; Duployan # Lo [107] DUPLOYAN LETTER H..DUPLOYAN LETTER VOCALIC M
+1BC70..1BC7C  ; Duployan # Lo  [13] DUPLOYAN AFFIX LEFT HORIZONTAL SECANT..DUPLOYAN AFFIX ATTACHED TANGENT HOOK
+1BC80..1BC88  ; Duployan # Lo   [9] DUPLOYAN AFFIX HIGH ACUTE..DUPLOYAN AFFIX HIGH VERTICAL
+1BC90..1BC99  ; Duployan # Lo  [10] DUPLOYAN AFFIX LOW ACUTE..DUPLOYAN AFFIX LOW ARROW
+1BC9C         ; Duployan # So       DUPLOYAN SIGN O WITH CROSS
+1BC9D..1BC9E  ; Duployan # Mn   [2] DUPLOYAN THICK LETTER SELECTOR..DUPLOYAN DOUBLE MARK
+1BC9F         ; Duployan # Po       DUPLOYAN PUNCTUATION CHINOOK FULL STOP
+
+# Total code points: 143
+
+# ================================================
+
+10500..10527  ; Elbasan # Lo  [40] ELBASAN LETTER A..ELBASAN LETTER KHE
+
+# Total code points: 40
+
+# ================================================
+
+11301         ; Grantha # Mn       GRANTHA SIGN CANDRABINDU
+11302..11303  ; Grantha # Mc   [2] GRANTHA SIGN ANUSVARA..GRANTHA SIGN VISARGA
+11305..1130C  ; Grantha # Lo   [8] GRANTHA LETTER A..GRANTHA LETTER VOCALIC L
+1130F..11310  ; Grantha # Lo   [2] GRANTHA LETTER EE..GRANTHA LETTER AI
+11313..11328  ; Grantha # Lo  [22] GRANTHA LETTER OO..GRANTHA LETTER NA
+1132A..11330  ; Grantha # Lo   [7] GRANTHA LETTER PA..GRANTHA LETTER RA
+11332..11333  ; Grantha # Lo   [2] GRANTHA LETTER LA..GRANTHA LETTER LLA
+11335..11339  ; Grantha # Lo   [5] GRANTHA LETTER VA..GRANTHA LETTER HA
+1133C         ; Grantha # Mn       GRANTHA SIGN NUKTA
+1133D         ; Grantha # Lo       GRANTHA SIGN AVAGRAHA
+1133E..1133F  ; Grantha # Mc   [2] GRANTHA VOWEL SIGN AA..GRANTHA VOWEL SIGN I
+11340         ; Grantha # Mn       GRANTHA VOWEL SIGN II
+11341..11344  ; Grantha # Mc   [4] GRANTHA VOWEL SIGN U..GRANTHA VOWEL SIGN VOCALIC RR
+11347..11348  ; Grantha # Mc   [2] GRANTHA VOWEL SIGN EE..GRANTHA VOWEL SIGN AI
+1134B..1134D  ; Grantha # Mc   [3] GRANTHA VOWEL SIGN OO..GRANTHA SIGN VIRAMA
+11357         ; Grantha # Mc       GRANTHA AU LENGTH MARK
+1135D..11361  ; Grantha # Lo   [5] GRANTHA SIGN PLUTA..GRANTHA LETTER VOCALIC LL
+11362..11363  ; Grantha # Mc   [2] GRANTHA VOWEL SIGN VOCALIC L..GRANTHA VOWEL SIGN VOCALIC LL
+11366..1136C  ; Grantha # Mn   [7] COMBINING GRANTHA DIGIT ZERO..COMBINING GRANTHA DIGIT SIX
+11370..11374  ; Grantha # Mn   [5] COMBINING GRANTHA LETTER A..COMBINING GRANTHA LETTER PA
+
+# Total code points: 83
+
+# ================================================
+
+16B00..16B2F  ; Pahawh_Hmong # Lo  [48] PAHAWH HMONG VOWEL KEEB..PAHAWH HMONG CONSONANT CAU
+16B30..16B36  ; Pahawh_Hmong # Mn   [7] PAHAWH HMONG MARK CIM TUB..PAHAWH HMONG MARK CIM TAUM
+16B37..16B3B  ; Pahawh_Hmong # Po   [5] PAHAWH HMONG SIGN VOS THOM..PAHAWH HMONG SIGN VOS FEEM
+16B3C..16B3F  ; Pahawh_Hmong # So   [4] PAHAWH HMONG SIGN XYEEM NTXIV..PAHAWH HMONG SIGN XYEEM FAIB
+16B40..16B43  ; Pahawh_Hmong # Lm   [4] PAHAWH HMONG SIGN VOS SEEV..PAHAWH HMONG SIGN IB YAM
+16B44         ; Pahawh_Hmong # Po       PAHAWH HMONG SIGN XAUS
+16B45         ; Pahawh_Hmong # So       PAHAWH HMONG SIGN CIM TSOV ROG
+16B50..16B59  ; Pahawh_Hmong # Nd  [10] PAHAWH HMONG DIGIT ZERO..PAHAWH HMONG DIGIT NINE
+16B5B..16B61  ; Pahawh_Hmong # No   [7] PAHAWH HMONG NUMBER TENS..PAHAWH HMONG NUMBER TRILLIONS
+16B63..16B77  ; Pahawh_Hmong # Lo  [21] PAHAWH HMONG SIGN VOS LUB..PAHAWH HMONG SIGN CIM NRES TOS
+16B7D..16B8F  ; Pahawh_Hmong # Lo  [19] PAHAWH HMONG CLAN SIGN TSHEEJ..PAHAWH HMONG CLAN SIGN VWJ
+
+# Total code points: 127
+
+# ================================================
+
+11200..11211  ; Khojki # Lo  [18] KHOJKI LETTER A..KHOJKI LETTER JJA
+11213..1122B  ; Khojki # Lo  [25] KHOJKI LETTER NYA..KHOJKI LETTER LLA
+1122C..1122E  ; Khojki # Mc   [3] KHOJKI VOWEL SIGN AA..KHOJKI VOWEL SIGN II
+1122F..11231  ; Khojki # Mn   [3] KHOJKI VOWEL SIGN U..KHOJKI VOWEL SIGN AI
+11232..11233  ; Khojki # Mc   [2] KHOJKI VOWEL SIGN O..KHOJKI VOWEL SIGN AU
+11234         ; Khojki # Mn       KHOJKI SIGN ANUSVARA
+11235         ; Khojki # Mc       KHOJKI SIGN VIRAMA
+11236..11237  ; Khojki # Mn   [2] KHOJKI SIGN NUKTA..KHOJKI SIGN SHADDA
+11238..1123D  ; Khojki # Po   [6] KHOJKI DANDA..KHOJKI ABBREVIATION SIGN
+
+# Total code points: 61
+
+# ================================================
+
+10600..10736  ; Linear_A # Lo [311] LINEAR A SIGN AB001..LINEAR A SIGN A664
+10740..10755  ; Linear_A # Lo  [22] LINEAR A SIGN A701 A..LINEAR A SIGN A732 JE
+10760..10767  ; Linear_A # Lo   [8] LINEAR A SIGN A800..LINEAR A SIGN A807
+
+# Total code points: 341
+
+# ================================================
+
+11150..11172  ; Mahajani # Lo  [35] MAHAJANI LETTER A..MAHAJANI LETTER RRA
+11173         ; Mahajani # Mn       MAHAJANI SIGN NUKTA
+11174..11175  ; Mahajani # Po   [2] MAHAJANI ABBREVIATION SIGN..MAHAJANI SECTION MARK
+11176         ; Mahajani # Lo       MAHAJANI LIGATURE SHRI
+
+# Total code points: 39
+
+# ================================================
+
+10AC0..10AC7  ; Manichaean # Lo   [8] MANICHAEAN LETTER ALEPH..MANICHAEAN LETTER WAW
+10AC8         ; Manichaean # So       MANICHAEAN SIGN UD
+10AC9..10AE4  ; Manichaean # Lo  [28] MANICHAEAN LETTER ZAYIN..MANICHAEAN LETTER TAW
+10AE5..10AE6  ; Manichaean # Mn   [2] MANICHAEAN ABBREVIATION MARK ABOVE..MANICHAEAN ABBREVIATION MARK BELOW
+10AEB..10AEF  ; Manichaean # No   [5] MANICHAEAN NUMBER ONE..MANICHAEAN NUMBER ONE HUNDRED
+10AF0..10AF6  ; Manichaean # Po   [7] MANICHAEAN PUNCTUATION STAR..MANICHAEAN PUNCTUATION LINE FILLER
+
+# Total code points: 51
+
+# ================================================
+
+1E800..1E8C4  ; Mende_Kikakui # Lo [197] MENDE KIKAKUI SYLLABLE M001 KI..MENDE KIKAKUI SYLLABLE M060 NYON
+1E8C7..1E8CF  ; Mende_Kikakui # No   [9] MENDE KIKAKUI DIGIT ONE..MENDE KIKAKUI DIGIT NINE
+1E8D0..1E8D6  ; Mende_Kikakui # Mn   [7] MENDE KIKAKUI COMBINING NUMBER TEENS..MENDE KIKAKUI COMBINING NUMBER MILLIONS
+
+# Total code points: 213
+
+# ================================================
+
+11600..1162F  ; Modi # Lo  [48] MODI LETTER A..MODI LETTER LLA
+11630..11632  ; Modi # Mc   [3] MODI VOWEL SIGN AA..MODI VOWEL SIGN II
+11633..1163A  ; Modi # Mn   [8] MODI VOWEL SIGN U..MODI VOWEL SIGN AI
+1163B..1163C  ; Modi # Mc   [2] MODI VOWEL SIGN O..MODI VOWEL SIGN AU
+1163D         ; Modi # Mn       MODI SIGN ANUSVARA
+1163E         ; Modi # Mc       MODI SIGN VISARGA
+1163F..11640  ; Modi # Mn   [2] MODI SIGN VIRAMA..MODI SIGN ARDHACANDRA
+11641..11643  ; Modi # Po   [3] MODI DANDA..MODI ABBREVIATION SIGN
+11644         ; Modi # Lo       MODI SIGN HUVA
+11650..11659  ; Modi # Nd  [10] MODI DIGIT ZERO..MODI DIGIT NINE
+
+# Total code points: 79
+
+# ================================================
+
+16A40..16A5E  ; Mro # Lo  [31] MRO LETTER TA..MRO LETTER TEK
+16A60..16A69  ; Mro # Nd  [10] MRO DIGIT ZERO..MRO DIGIT NINE
+16A6E..16A6F  ; Mro # Po   [2] MRO DANDA..MRO DOUBLE DANDA
+
+# Total code points: 43
+
+# ================================================
+
+10A80..10A9C  ; Old_North_Arabian # Lo  [29] OLD NORTH ARABIAN LETTER HEH..OLD NORTH ARABIAN LETTER ZAH
+10A9D..10A9F  ; Old_North_Arabian # No   [3] OLD NORTH ARABIAN NUMBER ONE..OLD NORTH ARABIAN NUMBER TWENTY
+
+# Total code points: 32
+
+# ================================================
+
+10880..1089E  ; Nabataean # Lo  [31] NABATAEAN LETTER FINAL ALEPH..NABATAEAN LETTER TAW
+108A7..108AF  ; Nabataean # No   [9] NABATAEAN NUMBER ONE..NABATAEAN NUMBER ONE HUNDRED
+
+# Total code points: 40
+
+# ================================================
+
+10860..10876  ; Palmyrene # Lo  [23] PALMYRENE LETTER ALEPH..PALMYRENE LETTER TAW
+10877..10878  ; Palmyrene # So   [2] PALMYRENE LEFT-POINTING FLEURON..PALMYRENE RIGHT-POINTING FLEURON
+10879..1087F  ; Palmyrene # No   [7] PALMYRENE NUMBER ONE..PALMYRENE NUMBER TWENTY
+
+# Total code points: 32
+
+# ================================================
+
+11AC0..11AF8  ; Pau_Cin_Hau # Lo  [57] PAU CIN HAU LETTER PA..PAU CIN HAU GLOTTAL STOP FINAL
+
+# Total code points: 57
+
+# ================================================
+
+10350..10375  ; Old_Permic # Lo  [38] OLD PERMIC LETTER AN..OLD PERMIC LETTER IA
+10376..1037A  ; Old_Permic # Mn   [5] COMBINING OLD PERMIC LETTER AN..COMBINING OLD PERMIC LETTER SII
+
+# Total code points: 43
+
+# ================================================
+
+10B80..10B91  ; Psalter_Pahlavi # Lo  [18] PSALTER PAHLAVI LETTER ALEPH..PSALTER PAHLAVI LETTER TAW
+10B99..10B9C  ; Psalter_Pahlavi # Po   [4] PSALTER PAHLAVI SECTION MARK..PSALTER PAHLAVI FOUR DOTS WITH DOT
+10BA9..10BAF  ; Psalter_Pahlavi # No   [7] PSALTER PAHLAVI NUMBER ONE..PSALTER PAHLAVI NUMBER ONE HUNDRED
+
+# Total code points: 29
+
+# ================================================
+
+11580..115AE  ; Siddham # Lo  [47] SIDDHAM LETTER A..SIDDHAM LETTER HA
+115AF..115B1  ; Siddham # Mc   [3] SIDDHAM VOWEL SIGN AA..SIDDHAM VOWEL SIGN II
+115B2..115B5  ; Siddham # Mn   [4] SIDDHAM VOWEL SIGN U..SIDDHAM VOWEL SIGN VOCALIC RR
+115B8..115BB  ; Siddham # Mc   [4] SIDDHAM VOWEL SIGN E..SIDDHAM VOWEL SIGN AU
+115BC..115BD  ; Siddham # Mn   [2] SIDDHAM SIGN CANDRABINDU..SIDDHAM SIGN ANUSVARA
+115BE         ; Siddham # Mc       SIDDHAM SIGN VISARGA
+115BF..115C0  ; Siddham # Mn   [2] SIDDHAM SIGN VIRAMA..SIDDHAM SIGN NUKTA
+115C1..115C9  ; Siddham # Po   [9] SIDDHAM SIGN SIDDHAM..SIDDHAM END OF TEXT MARK
+
+# Total code points: 72
+
+# ================================================
+
+112B0..112DE  ; Khudawadi # Lo  [47] KHUDAWADI LETTER A..KHUDAWADI LETTER HA
+112DF         ; Khudawadi # Mn       KHUDAWADI SIGN ANUSVARA
+112E0..112E2  ; Khudawadi # Mc   [3] KHUDAWADI VOWEL SIGN AA..KHUDAWADI VOWEL SIGN II
+112E3..112EA  ; Khudawadi # Mn   [8] KHUDAWADI VOWEL SIGN U..KHUDAWADI SIGN VIRAMA
+112F0..112F9  ; Khudawadi # Nd  [10] KHUDAWADI DIGIT ZERO..KHUDAWADI DIGIT NINE
+
+# Total code points: 69
+
+# ================================================
+
+11480..114AF  ; Tirhuta # Lo  [48] TIRHUTA ANJI..TIRHUTA LETTER HA
+114B0..114B2  ; Tirhuta # Mc   [3] TIRHUTA VOWEL SIGN AA..TIRHUTA VOWEL SIGN II
+114B3..114B8  ; Tirhuta # Mn   [6] TIRHUTA VOWEL SIGN U..TIRHUTA VOWEL SIGN VOCALIC LL
+114B9         ; Tirhuta # Mc       TIRHUTA VOWEL SIGN E
+114BA         ; Tirhuta # Mn       TIRHUTA VOWEL SIGN SHORT E
+114BB..114BE  ; Tirhuta # Mc   [4] TIRHUTA VOWEL SIGN AI..TIRHUTA VOWEL SIGN AU
+114BF..114C0  ; Tirhuta # Mn   [2] TIRHUTA SIGN CANDRABINDU..TIRHUTA SIGN ANUSVARA
+114C1         ; Tirhuta # Mc       TIRHUTA SIGN VISARGA
+114C2..114C3  ; Tirhuta # Mn   [2] TIRHUTA SIGN VIRAMA..TIRHUTA SIGN NUKTA
+114C4..114C5  ; Tirhuta # Lo   [2] TIRHUTA SIGN AVAGRAHA..TIRHUTA GVANG
+114C6         ; Tirhuta # Po       TIRHUTA ABBREVIATION SIGN
+114C7         ; Tirhuta # Lo       TIRHUTA OM
+114D0..114D9  ; Tirhuta # Nd  [10] TIRHUTA DIGIT ZERO..TIRHUTA DIGIT NINE
+
+# Total code points: 82
+
+# ================================================
+
+118A0..118DF  ; Warang_Citi # L&  [64] WARANG CITI CAPITAL LETTER NGAA..WARANG CITI SMALL LETTER VIYO
+118E0..118E9  ; Warang_Citi # Nd  [10] WARANG CITI DIGIT ZERO..WARANG CITI DIGIT NINE
+118EA..118F2  ; Warang_Citi # No   [9] WARANG CITI NUMBER TEN..WARANG CITI NUMBER NINETY
+118FF         ; Warang_Citi # Lo       WARANG CITI OM
+
+# Total code points: 84
+
 # EOF
--- a/jdk/test/java/lang/Class/getDeclaredField/FieldSetAccessibleTest.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/lang/Class/getDeclaredField/FieldSetAccessibleTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -221,8 +221,8 @@
 
         Stream<String> build() {
             return roots.stream().flatMap(this::toStream)
-                    .filter(x -> x.getNameCount() > 1)
-                    .map( x-> x.subpath(1, x.getNameCount()))
+                    .filter(x -> x.getNameCount() > 2)
+                    .map( x-> x.subpath(2, x.getNameCount()))
                     .map( x -> x.toString())
                     .filter(s -> s.endsWith(".class"));
         }
--- a/jdk/test/java/lang/ProcessHandle/TreeTest.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/lang/ProcessHandle/TreeTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -210,7 +210,6 @@
             printf(" p1: %s%n", p1.getPid());
 
             List<ProcessHandle> subprocesses = getChildren(self);
-            subprocesses.forEach(ProcessUtil::printProcess);
             long count = subprocesses.size();
             Assert.assertEquals(count, 1, "Wrong number of spawned children");
 
@@ -220,8 +219,6 @@
 
             // Wait for the new processes and save the list
             subprocesses = waitForAllChildren(p1Handle, newChildren);
-            printDeep(p1Handle, "allChildren");
-
             Assert.assertEquals(subprocesses.size(), newChildren, "Wrong number of children");
 
             p1.children().filter(TreeTest::isNotWindowsConsole)
@@ -230,25 +227,17 @@
             self.children().filter(TreeTest::isNotWindowsConsole)
                     .forEach(ProcessHandle::destroyForcibly);
 
-            do {
-                Thread.sleep(500L);      // It will happen but don't burn the cpu
-                Object[] children = self.allChildren()
-                        .filter(TreeTest::isNotWindowsConsole)
-                        .toArray();
-                count = children.length;
-                printf(" waiting for subprocesses of %s to terminate," +
-                                " expected: 0, current: %d, children: %s%n", self, count,
-                        Arrays.toString(children));
-                printDeep(self, "");
-            } while (count > 0);
+            for (ProcessHandle p : subprocesses) {
+                while (p.isAlive()) {
+                    Thread.sleep(100L);  // It will happen but don't burn the cpu
+                }
+            }
 
-            boolean ex1 = p1.waitFor(5, TimeUnit.SECONDS);
-            Assert.assertTrue(ex1, "Subprocess should have exited: " + p1);
-
-            for (ProcessHandle p : subprocesses) {
-                Assert.assertFalse(p.isAlive(), "Destroyed process.isAlive: " + p +
-                        ", parent: " + p.parent() +
-                        ", info: " + p.info().toString());
+            List<ProcessHandle> remaining = getAllChildren(self);
+            remaining.retainAll(subprocesses);
+            if (remaining.size() > 0) {
+                remaining.forEach(p -> printProcess(p, "     remaining: "));
+                Assert.fail("Subprocess(es) should have exited");
             }
 
         } catch (IOException ioe) {
--- a/jdk/test/java/lang/reflect/Generics/ThreadSafety.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/lang/reflect/Generics/ThreadSafety.java	Wed Jul 05 20:42:36 2017 +0200
@@ -28,8 +28,11 @@
  * @run testng ThreadSafety
  */
 
+import java.io.File;
 import java.net.URL;
 import java.net.URLClassLoader;
+import java.nio.file.Path;
+import java.nio.file.Paths;
 import java.util.Collections;
 import java.util.concurrent.BrokenBarrierException;
 import java.util.concurrent.Callable;
@@ -71,9 +74,13 @@
     /** published via data race */
     private Class<?> racyClass = Object.class;
 
-    private URL[] urls = ((URLClassLoader) ThreadSafety.class.getClassLoader()).getURLs();
-
     private Class<?> createNewEmptyGenericSubclassClass() throws Exception {
+        String[] cpaths = System.getProperty("test.classes", ".")
+                                .split(File.pathSeparator);
+        URL[] urls = new URL[cpaths.length];
+        for (int i=0; i < cpaths.length; i++) {
+            urls[i] = Paths.get(cpaths[i]).toUri().toURL();
+        }
         URLClassLoader ucl = new URLClassLoader(urls, null);
         return Class.forName("ThreadSafety$EmptyClass$EmptyGenericSubclass", true, ucl);
     }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/net/URLConnection/ContentHandlers/ContentHandlersTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,371 @@
+/*
+ * 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.
+ */
+
+import java.io.BufferedReader;
+import java.io.BufferedWriter;
+import java.io.File;
+import java.io.FileReader;
+import java.io.FileWriter;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.io.Reader;
+import java.io.SequenceInputStream;
+import java.io.StringWriter;
+import java.io.Writer;
+import java.nio.file.Files;
+import java.nio.file.Path;
+import java.nio.file.Paths;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+import java.util.function.Function;
+import java.util.stream.Collectors;
+import java.util.stream.Stream;
+
+import static java.lang.String.format;
+import static java.util.Arrays.asList;
+import static java.util.Collections.emptyMap;
+import static java.util.Collections.singleton;
+import static java.util.Collections.singletonMap;
+
+/*
+ * @test
+ * @bug 8064925
+ * @summary Basic test for ContentHandler. Ensures discovery paths for content
+ *          handlers follow a particular order.
+ */
+public class ContentHandlersTest {
+
+    public static void main(String[] args) throws Throwable {
+        step1_ContentHandlerFactory();
+        step2_ServiceLoader();
+        step3_UserDefined();
+        step4_BuiltIn();
+    }
+
+    private static void step1_ContentHandlerFactory() throws IOException {
+        String factoryClassFqn = "net.java.openjdk.test.TestContentHandlerFactory";
+
+        Path tmp = Files.createDirectory(Paths.get("ContentHandlersTest-1"));
+
+        Path src = templatesHome().resolve("test.template");
+        Path dst = tmp.resolve("Test.java");
+        Files.copy(src, dst);
+
+        Path build = Files.createDirectory(tmp.resolve("build"));
+
+        Path dst1 = fromTemplate(templatesHome().resolve("broken_factory.template"),
+                factoryClassFqn, tmp);
+
+        javac(build, dst, dst1);
+
+        Result r = java(emptyMap(), singleton(build), "Test", factoryClassFqn);
+
+        if (r.exitValue == 0 || !r.output.startsWith(
+                stackTraceStringForBrokenFactory(factoryClassFqn))) {
+            throw new RuntimeException(
+                    "Expected a different kind of failure: " + r.output);
+        }
+    }
+
+    private static void step2_ServiceLoader() throws IOException {
+        String factoryClassFqn = "net.java.openjdk.test.TestContentHandlerFactory";
+
+        Path tmp = Files.createDirectory(Paths.get("ContentHandlersTest-2"));
+
+        Path src = templatesHome().resolve("test.template");
+        Path dst = tmp.resolve("Test.java");
+        Files.copy(src, dst);
+
+        Path dst1 = fromTemplate(templatesHome().resolve("broken_constructor_factory.template"),
+                factoryClassFqn, tmp);
+
+        Path build = Files.createDirectory(tmp.resolve("build"));
+
+        javac(build, dst);
+
+        Path explodedJar = Files.createDirectory(tmp.resolve("exploded-jar"));
+        Path services = Files.createDirectories(explodedJar.resolve("META-INF")
+                .resolve("services"));
+
+        Path s = services.resolve("java.net.ContentHandlerFactory");
+
+        try (FileWriter fw = new FileWriter(s.toFile())) {
+            fw.write(factoryClassFqn);
+        }
+
+        javac(explodedJar, dst1);
+        jar(tmp.resolve("test.jar"), explodedJar);
+
+        Files.copy(tmp.resolve("test.jar"), build.resolve("test.jar"));
+
+        Result r = java(emptyMap(), asList(build.resolve("test.jar"), build), "Test");
+
+        if (r.exitValue == 0 || !verifyOutput(r.output, factoryClassFqn))
+            throw new RuntimeException(r.output);
+    }
+
+    private static void step3_UserDefined() throws IOException {
+        String packagePrefix = "net.java.openjdk.test";
+        String fqn = packagePrefix + ".text.plain";
+
+        Path tmp = Files.createDirectory(Paths.get("ContentHandlersTest-3"));
+
+        Path src = templatesHome().resolve("test.template");
+        Path dst = tmp.resolve("Test.java");
+        Files.copy(src, dst);
+
+        Path dst1 = fromTemplate(templatesHome().resolve("plain.template"),
+                fqn, tmp);
+
+        Path build = Files.createDirectory(tmp.resolve("build"));
+
+        javac(build, dst);
+
+        Path classes = Files.createDirectory(tmp.resolve("classes"));
+
+        javac(classes, dst1);
+
+        Map<String, String> m = singletonMap("java.content.handler.pkgs", packagePrefix);
+        Result r = java(m, asList(build, classes), "Test");
+
+        if (r.exitValue != 0 || !r.output.contains(fqn))
+            throw new RuntimeException(r.output);
+    }
+
+    private static void step4_BuiltIn() throws IOException {
+        Path tmp = Files.createDirectory(Paths.get("ContentHandlersTest-4"));
+
+        Path src = templatesHome().resolve("test.template");
+        Path dst = tmp.resolve("Test.java");
+        Files.copy(src, dst);
+
+        Path build = Files.createDirectory(tmp.resolve("build"));
+
+        javac(build, dst);
+
+        Result r = java(emptyMap(), singleton(build), "Test");
+
+        if (r.exitValue != 0 || !r.output.contains("sun.net.www.content.text.PlainTextInputStream"))
+            throw new RuntimeException(r.output);
+    }
+
+    private static String stackTraceStringForBrokenFactory(String fqn) {
+        return "Exception in thread \"main\" java.lang.RuntimeException: " +
+                "This is a broken factory. It is supposed to throw this exception.";
+    }
+
+    private static Path fromTemplate(Path srcTemplate,
+                                     String factoryFqn,
+                                     Path dstFolder) throws IOException {
+
+        String factorySimpleName, packageName;
+        int i = factoryFqn.lastIndexOf('.');
+        if (i < 0) {
+            packageName = "";
+            factorySimpleName = factoryFqn;
+        } else {
+            packageName = factoryFqn.substring(0, i);
+            factorySimpleName = factoryFqn.substring(i + 1);
+        }
+
+        Path result = dstFolder.resolve(factorySimpleName + ".java");
+        File dst = result.toFile();
+        File src = srcTemplate.toFile();
+        try (BufferedReader r = new BufferedReader(new FileReader(src));
+             BufferedWriter w = new BufferedWriter(new FileWriter(dst))) {
+
+            List<String> lines = processTemplate(packageName, factorySimpleName,
+                    r.lines()).collect(Collectors.toList());
+
+            Iterator<String> it = lines.iterator();
+            if (it.hasNext())
+                w.write(it.next());
+            while (it.hasNext()) {
+                w.newLine();
+                w.write(it.next());
+            }
+        }
+        return result;
+    }
+
+    private static Stream<String> processTemplate(String packageName,
+                                                  String factorySimpleName,
+                                                  Stream<String> lines) {
+        Function<String, String> pckg;
+
+        if (packageName.isEmpty()) {
+            pckg = s -> s.contains("$package") ? "" : s;
+        } else {
+            pckg = s -> s.replaceAll("\\$package", packageName);
+        }
+
+        Function<String, String> factory
+                = s -> s.replaceAll("\\$className", factorySimpleName);
+
+        return lines.map(pckg).map(factory);
+    }
+
+    // IMO, that's the easiest way that gives you a fair amount of confidence in
+    // that j.u.ServiceLoader is loading a factory rather than Class.forName
+    private static boolean verifyOutput(String output, String fqn) {
+        String s1 = String.format("java.util.ServiceConfigurationError: " +
+                "java.net.ContentHandlerFactory: " +
+                "Provider %s could not be instantiated", fqn);
+
+        return output.contains(s1);
+    }
+
+    private static void jar(Path jarName, Path jarRoot) {
+        String jar = getJDKTool("jar");
+        ProcessBuilder p = new ProcessBuilder(jar, "cf", jarName.toString(),
+                "-C", jarRoot.toString(), ".");
+        quickFail(run(p));
+    }
+
+    private static void javac(Path compilationOutput, Path... sourceFiles) {
+        String javac = getJDKTool("javac");
+        List<String> commands = new ArrayList<>();
+        commands.addAll(asList(javac, "-d", compilationOutput.toString()));
+        List<Path> paths = asList(sourceFiles);
+        commands.addAll(paths.stream()
+                .map(Path::toString)
+                .collect(Collectors.toList()));
+        quickFail(run(new ProcessBuilder(commands)));
+    }
+
+    private static void quickFail(Result r) {
+        if (r.exitValue != 0)
+            throw new RuntimeException(r.output);
+    }
+
+    private static Result java(Map<String, String> properties,
+                               Collection<Path> classpath,
+                               String classname, String... args) {
+
+        String java = getJDKTool("java");
+
+        List<String> commands = new ArrayList<>();
+        commands.add(java);
+        commands.addAll(properties.entrySet()
+                .stream()
+                .map(e -> "-D" + e.getKey() + "=" + e.getValue())
+                .collect(Collectors.toList()));
+
+        String cp = classpath.stream()
+                .map(Path::toString)
+                .collect(Collectors.joining(File.pathSeparator));
+        commands.add("-cp");
+        commands.add(cp);
+        commands.add(classname);
+        commands.addAll(Arrays.asList(args));
+
+        return run(new ProcessBuilder(commands));
+    }
+
+    private static Result run(ProcessBuilder b) {
+        Process p;
+        try {
+            p = b.start();
+        } catch (IOException e) {
+            throw new RuntimeException(
+                    format("Couldn't start process '%s'", b.command()), e);
+        }
+
+        String output;
+        try {
+            output = toString(p.getInputStream(), p.getErrorStream());
+        } catch (IOException e) {
+            throw new RuntimeException(
+                    format("Couldn't read process output '%s'", b.command()), e);
+        }
+
+        try {
+            p.waitFor();
+        } catch (InterruptedException e) {
+            throw new RuntimeException(
+                    format("Process hasn't finished '%s'", b.command()), e);
+        }
+
+        return new Result(p.exitValue(), output);
+    }
+
+    private static String getJDKTool(String name) {
+        String testJdk = System.getProperty("test.jdk");
+        if (testJdk == null)
+            throw new RuntimeException("Please provide test.jdk property at a startup");
+        return testJdk + File.separator + "bin" + File.separator + name;
+    }
+
+    private static Path templatesHome() {
+        String testSrc = System.getProperty("test.src");
+        if (testSrc == null)
+            throw new RuntimeException("Please provide test.src property at a startup");
+        return Paths.get(testSrc);
+    }
+
+    private static String toString(InputStream... src) throws IOException {
+        StringWriter dst = new StringWriter();
+        Reader concatenated =
+                new InputStreamReader(
+                        new SequenceInputStream(
+                                Collections.enumeration(asList(src))));
+        copy(concatenated, dst);
+        return dst.toString();
+    }
+
+    private static void copy(Reader src, Writer dst) throws IOException {
+        int len;
+        char[] buf = new char[1024];
+        try {
+            while ((len = src.read(buf)) != -1)
+                dst.write(buf, 0, len);
+        } finally {
+            try {
+                src.close();
+            } catch (IOException ignored1) {
+            } finally {
+                try {
+                    dst.close();
+                } catch (IOException ignored2) {
+                }
+            }
+        }
+    }
+
+    private static class Result {
+
+        final int exitValue;
+        final String output;
+
+        private Result(int exitValue, String output) {
+            this.exitValue = exitValue;
+            this.output = output;
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/net/URLConnection/ContentHandlers/broken_constructor_factory.template	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,40 @@
+/*
+ * 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 $package;
+
+import java.net.ContentHandler;
+import java.net.ContentHandlerFactory;
+
+public class $className implements ContentHandlerFactory {
+
+    public $className() {
+        throw new RuntimeException(
+                "This is a broken factory. It is supposed to throw this exception.");
+    }
+
+    @Override
+    public ContentHandler createContentHandler(String mimetype) {
+        throw new RuntimeException( "This method is not supposed to be called.");
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/net/URLConnection/ContentHandlers/broken_factory.template	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,36 @@
+/*
+ * 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 $package;
+
+import java.net.ContentHandler;
+import java.net.ContentHandlerFactory;
+
+public class $className implements ContentHandlerFactory {
+
+    @Override
+    public ContentHandler createContentHandler(String mimetype) {
+        throw new RuntimeException(
+                "This is a broken factory. It is supposed to throw this exception.");
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/net/URLConnection/ContentHandlers/plain.template	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,37 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package $package;
+
+import java.io.IOException;
+import java.net.ContentHandler;
+import java.net.URLConnection;
+
+public final class $className extends ContentHandler {
+
+    @Override
+    public Object getContent(URLConnection urlc) throws IOException {
+        return this;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/net/URLConnection/ContentHandlers/test.template	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,79 @@
+/*
+ * 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.
+ */
+
+import java.io.ByteArrayInputStream;
+import java.io.InputStream;
+import java.net.ContentHandlerFactory;
+import java.net.URL;
+import java.net.URLConnection;
+import java.net.URLStreamHandler;
+import java.net.URLStreamHandlerFactory;
+
+public class Test {
+
+    public static void main(String[] args) throws Exception {
+        if (args.length > 0) {
+            String fqn = args[0];
+
+            @SuppressWarnings("unchecked")
+            Class<? extends ContentHandlerFactory> c =
+                    (Class<? extends ContentHandlerFactory>) Class.forName(fqn);
+
+            ContentHandlerFactory f = c.newInstance();
+
+            URLConnection.setContentHandlerFactory(f);
+        }
+
+        // One does not simply use a ContentHandler...
+        // From an end user perspective ContentHandler is used indirectly
+        // and it's more like SPI rather than API. So there's a certain amount
+        // of preparations needs to be done beforehand.
+
+        URLStreamHandlerFactory streamHandlerFactory =
+                (protocol) ->
+                        new URLStreamHandler() {
+                            @Override
+                            protected URLConnection openConnection(URL u) {
+                                return newUrlConnection(u);
+                            }
+                        };
+
+        URL.setURLStreamHandlerFactory(streamHandlerFactory);
+
+        // Finally
+        Object content = new URL("whatever:").getContent();
+
+        System.out.println("Content class is: " + content.getClass());
+    }
+
+    private static URLConnection newUrlConnection(URL u) {
+        return new URLConnection(u) {
+            @Override public void connect() { }
+
+            @Override
+            public InputStream getInputStream() { return null; }
+
+            @Override public String getContentType() { return "text/plain"; }
+        };
+    }
+}
--- a/jdk/test/java/nio/Buffer/LimitDirectMemory.sh	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/nio/Buffer/LimitDirectMemory.sh	Wed Jul 05 20:42:36 2017 +0200
@@ -28,6 +28,7 @@
 # @summary Test option to limit direct memory allocation
 #
 # @build LimitDirectMemory
+# @ignore JDK-8129343
 # @run shell LimitDirectMemory.sh
 
 TMP1=tmp_$$
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/nio/Buffer/Order-X.java.template	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,59 @@
+/*
+ * 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.
+ */
+
+/* Type-specific source code for unit test
+ *
+ * Regenerate the OrderX classes via genOrder.sh whenever this file changes.
+ * We check in the generated source files so that the test tree can be used
+ * independently of the rest of the source tree.
+ */
+
+#warn This file is preprocessed before being compiled
+
+import java.nio.*;
+
+public class Order$Type$ extends Order {
+    private static void ck$Type$Buffer($Type$Buffer buf, ByteOrder expected) {
+        ck(buf.asReadOnlyBuffer().order(), expected);
+        ck(buf.duplicate().order(), expected);
+        ck(buf.slice().order(), expected);
+    }
+
+    static void ck$Type$Buffer() {
+        $type$[] array = new $type$[LENGTH];
+        $Type$Buffer buf = $Type$Buffer.wrap(array);
+        ck(buf.order(), nord);
+        ck$Type$Buffer(buf, nord);
+
+        buf = $Type$Buffer.wrap(array, LENGTH/2, LENGTH/2);
+        ck(buf.order(), nord);
+        ck$Type$Buffer(buf, nord);
+
+        buf = $Type$Buffer.allocate(LENGTH);
+        ck(buf.order(), nord);
+        ck$Type$Buffer(buf, nord);
+
+        ck$Type$Buffer(ByteBuffer.allocate(LENGTH).as$Type$Buffer(), be);
+        ck$Type$Buffer(ByteBuffer.allocateDirect(LENGTH).as$Type$Buffer(), be);
+    }
+}
--- a/jdk/test/java/nio/Buffer/Order.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/nio/Buffer/Order.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2001, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2001, 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
@@ -22,10 +22,10 @@
  */
 
 /* @test
+ * @bug 8065570
  * @summary Unit test for X-Buffer.order methods
  */
 
-import java.io.*;
 import java.nio.*;
 
 
@@ -35,6 +35,8 @@
     static final ByteOrder le = ByteOrder.LITTLE_ENDIAN;
     static final ByteOrder nord = ByteOrder.nativeOrder();
 
+    protected static final int LENGTH = 16;
+
     static void ck(ByteOrder ord, ByteOrder expected) {
         if (ord != expected)
             throw new RuntimeException("Got " + ord
@@ -55,18 +57,33 @@
         ckViews(bb, be);
         bb.order(le);
         ckViews(bb, le);
+
+        if (bb.hasArray()) {
+            byte[] array = bb.array();
+            ck(ByteBuffer.wrap(array, LENGTH/2, LENGTH/2).order(), be);
+            ck(ByteBuffer.wrap(array).order(), be);
+            ck(bb.asReadOnlyBuffer().order(), be);
+            ck(bb.duplicate().order(), be);
+            ck(bb.slice().order(), be);
+        }
     }
 
     public static void main(String args[]) throws Exception {
 
-        ck(ByteBuffer.allocate(10).order(), be);
-        ck(ByteBuffer.allocateDirect(10).order(), be);
-        ck(ByteBuffer.allocate(10).order(be).order(), be);
-        ck(ByteBuffer.allocate(10).order(le).order(), le);
+        ck(ByteBuffer.allocate(LENGTH).order(), be);
+        ck(ByteBuffer.allocateDirect(LENGTH).order(), be);
+        ck(ByteBuffer.allocate(LENGTH).order(be).order(), be);
+        ck(ByteBuffer.allocate(LENGTH).order(le).order(), le);
 
-        ckByteBuffer(ByteBuffer.allocate(10));
-        ckByteBuffer(ByteBuffer.allocateDirect(10));
+        ckByteBuffer(ByteBuffer.allocate(LENGTH));
+        ckByteBuffer(ByteBuffer.allocateDirect(LENGTH));
 
+        OrderChar.ckCharBuffer();
+        OrderShort.ckShortBuffer();
+        OrderInt.ckIntBuffer();
+        OrderLong.ckLongBuffer();
+        OrderFloat.ckFloatBuffer();
+        OrderDouble.ckDoubleBuffer();
     }
 
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/nio/Buffer/OrderChar.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,59 @@
+/*
+ * 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.
+ */
+
+/* Type-specific source code for unit test
+ *
+ * Regenerate the OrderX classes via genOrder.sh whenever this file changes.
+ * We check in the generated source files so that the test tree can be used
+ * independently of the rest of the source tree.
+ */
+
+// -- This file was mechanically generated: Do not edit! -- //
+
+import java.nio.*;
+
+public class OrderChar extends Order {
+    private static void ckCharBuffer(CharBuffer buf, ByteOrder expected) {
+        ck(buf.asReadOnlyBuffer().order(), expected);
+        ck(buf.duplicate().order(), expected);
+        ck(buf.slice().order(), expected);
+    }
+
+    static void ckCharBuffer() {
+        char[] array = new char[LENGTH];
+        CharBuffer buf = CharBuffer.wrap(array);
+        ck(buf.order(), nord);
+        ckCharBuffer(buf, nord);
+
+        buf = CharBuffer.wrap(array, LENGTH/2, LENGTH/2);
+        ck(buf.order(), nord);
+        ckCharBuffer(buf, nord);
+
+        buf = CharBuffer.allocate(LENGTH);
+        ck(buf.order(), nord);
+        ckCharBuffer(buf, nord);
+
+        ckCharBuffer(ByteBuffer.allocate(LENGTH).asCharBuffer(), be);
+        ckCharBuffer(ByteBuffer.allocateDirect(LENGTH).asCharBuffer(), be);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/nio/Buffer/OrderDouble.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,59 @@
+/*
+ * 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.
+ */
+
+/* Type-specific source code for unit test
+ *
+ * Regenerate the OrderX classes via genOrder.sh whenever this file changes.
+ * We check in the generated source files so that the test tree can be used
+ * independently of the rest of the source tree.
+ */
+
+// -- This file was mechanically generated: Do not edit! -- //
+
+import java.nio.*;
+
+public class OrderDouble extends Order {
+    private static void ckDoubleBuffer(DoubleBuffer buf, ByteOrder expected) {
+        ck(buf.asReadOnlyBuffer().order(), expected);
+        ck(buf.duplicate().order(), expected);
+        ck(buf.slice().order(), expected);
+    }
+
+    static void ckDoubleBuffer() {
+        double[] array = new double[LENGTH];
+        DoubleBuffer buf = DoubleBuffer.wrap(array);
+        ck(buf.order(), nord);
+        ckDoubleBuffer(buf, nord);
+
+        buf = DoubleBuffer.wrap(array, LENGTH/2, LENGTH/2);
+        ck(buf.order(), nord);
+        ckDoubleBuffer(buf, nord);
+
+        buf = DoubleBuffer.allocate(LENGTH);
+        ck(buf.order(), nord);
+        ckDoubleBuffer(buf, nord);
+
+        ckDoubleBuffer(ByteBuffer.allocate(LENGTH).asDoubleBuffer(), be);
+        ckDoubleBuffer(ByteBuffer.allocateDirect(LENGTH).asDoubleBuffer(), be);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/nio/Buffer/OrderFloat.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,59 @@
+/*
+ * 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.
+ */
+
+/* Type-specific source code for unit test
+ *
+ * Regenerate the OrderX classes via genOrder.sh whenever this file changes.
+ * We check in the generated source files so that the test tree can be used
+ * independently of the rest of the source tree.
+ */
+
+// -- This file was mechanically generated: Do not edit! -- //
+
+import java.nio.*;
+
+public class OrderFloat extends Order {
+    private static void ckFloatBuffer(FloatBuffer buf, ByteOrder expected) {
+        ck(buf.asReadOnlyBuffer().order(), expected);
+        ck(buf.duplicate().order(), expected);
+        ck(buf.slice().order(), expected);
+    }
+
+    static void ckFloatBuffer() {
+        float[] array = new float[LENGTH];
+        FloatBuffer buf = FloatBuffer.wrap(array);
+        ck(buf.order(), nord);
+        ckFloatBuffer(buf, nord);
+
+        buf = FloatBuffer.wrap(array, LENGTH/2, LENGTH/2);
+        ck(buf.order(), nord);
+        ckFloatBuffer(buf, nord);
+
+        buf = FloatBuffer.allocate(LENGTH);
+        ck(buf.order(), nord);
+        ckFloatBuffer(buf, nord);
+
+        ckFloatBuffer(ByteBuffer.allocate(LENGTH).asFloatBuffer(), be);
+        ckFloatBuffer(ByteBuffer.allocateDirect(LENGTH).asFloatBuffer(), be);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/nio/Buffer/OrderInt.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,59 @@
+/*
+ * 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.
+ */
+
+/* Type-specific source code for unit test
+ *
+ * Regenerate the OrderX classes via genOrder.sh whenever this file changes.
+ * We check in the generated source files so that the test tree can be used
+ * independently of the rest of the source tree.
+ */
+
+// -- This file was mechanically generated: Do not edit! -- //
+
+import java.nio.*;
+
+public class OrderInt extends Order {
+    private static void ckIntBuffer(IntBuffer buf, ByteOrder expected) {
+        ck(buf.asReadOnlyBuffer().order(), expected);
+        ck(buf.duplicate().order(), expected);
+        ck(buf.slice().order(), expected);
+    }
+
+    static void ckIntBuffer() {
+        int[] array = new int[LENGTH];
+        IntBuffer buf = IntBuffer.wrap(array);
+        ck(buf.order(), nord);
+        ckIntBuffer(buf, nord);
+
+        buf = IntBuffer.wrap(array, LENGTH/2, LENGTH/2);
+        ck(buf.order(), nord);
+        ckIntBuffer(buf, nord);
+
+        buf = IntBuffer.allocate(LENGTH);
+        ck(buf.order(), nord);
+        ckIntBuffer(buf, nord);
+
+        ckIntBuffer(ByteBuffer.allocate(LENGTH).asIntBuffer(), be);
+        ckIntBuffer(ByteBuffer.allocateDirect(LENGTH).asIntBuffer(), be);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/nio/Buffer/OrderLong.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,59 @@
+/*
+ * 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.
+ */
+
+/* Type-specific source code for unit test
+ *
+ * Regenerate the OrderX classes via genOrder.sh whenever this file changes.
+ * We check in the generated source files so that the test tree can be used
+ * independently of the rest of the source tree.
+ */
+
+// -- This file was mechanically generated: Do not edit! -- //
+
+import java.nio.*;
+
+public class OrderLong extends Order {
+    private static void ckLongBuffer(LongBuffer buf, ByteOrder expected) {
+        ck(buf.asReadOnlyBuffer().order(), expected);
+        ck(buf.duplicate().order(), expected);
+        ck(buf.slice().order(), expected);
+    }
+
+    static void ckLongBuffer() {
+        long[] array = new long[LENGTH];
+        LongBuffer buf = LongBuffer.wrap(array);
+        ck(buf.order(), nord);
+        ckLongBuffer(buf, nord);
+
+        buf = LongBuffer.wrap(array, LENGTH/2, LENGTH/2);
+        ck(buf.order(), nord);
+        ckLongBuffer(buf, nord);
+
+        buf = LongBuffer.allocate(LENGTH);
+        ck(buf.order(), nord);
+        ckLongBuffer(buf, nord);
+
+        ckLongBuffer(ByteBuffer.allocate(LENGTH).asLongBuffer(), be);
+        ckLongBuffer(ByteBuffer.allocateDirect(LENGTH).asLongBuffer(), be);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/nio/Buffer/OrderShort.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,59 @@
+/*
+ * 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.
+ */
+
+/* Type-specific source code for unit test
+ *
+ * Regenerate the OrderX classes via genOrder.sh whenever this file changes.
+ * We check in the generated source files so that the test tree can be used
+ * independently of the rest of the source tree.
+ */
+
+// -- This file was mechanically generated: Do not edit! -- //
+
+import java.nio.*;
+
+public class OrderShort extends Order {
+    private static void ckShortBuffer(ShortBuffer buf, ByteOrder expected) {
+        ck(buf.asReadOnlyBuffer().order(), expected);
+        ck(buf.duplicate().order(), expected);
+        ck(buf.slice().order(), expected);
+    }
+
+    static void ckShortBuffer() {
+        short[] array = new short[LENGTH];
+        ShortBuffer buf = ShortBuffer.wrap(array);
+        ck(buf.order(), nord);
+        ckShortBuffer(buf, nord);
+
+        buf = ShortBuffer.wrap(array, LENGTH/2, LENGTH/2);
+        ck(buf.order(), nord);
+        ckShortBuffer(buf, nord);
+
+        buf = ShortBuffer.allocate(LENGTH);
+        ck(buf.order(), nord);
+        ckShortBuffer(buf, nord);
+
+        ckShortBuffer(ByteBuffer.allocate(LENGTH).asShortBuffer(), be);
+        ckShortBuffer(ByteBuffer.allocateDirect(LENGTH).asShortBuffer(), be);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/nio/Buffer/genOrder.sh	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,39 @@
+#! /bin/sh
+
+#
+# Copyright (c) 2002, 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.
+#
+
+javac -d . ../../../../make/src/classes/build/tools/spp/Spp.java > Spp.java
+
+gen() {
+    java  build.tools.spp.Spp -K$1 -Dtype=$1 -DType=$2 -DFulltype=$3<Order-X.java.template >Order$2.java
+}
+
+gen char Char Character
+gen short Short Short
+gen int Int Integer
+gen long Long Long
+gen float Float Float
+gen double Double Double
+
+rm -rf build
--- a/jdk/test/java/nio/channels/DatagramChannel/ReceiveISA.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/nio/channels/DatagramChannel/ReceiveISA.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2001, 2010, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2001, 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
@@ -23,7 +23,7 @@
 
 /*
  * @test
- * @bug 4503641
+ * @bug 4503641 8130394
  * @summary Check that DatagramChannel.receive returns a new SocketAddress
  *          when it receives a packet from the same source address but
  *          different endpoint.
@@ -63,6 +63,7 @@
         SocketAddress sa[] = new SocketAddress[3];
         for (int i=0; i<3; i++) {
             sa[i] = dc3.receive(rb);
+            System.out.println("received "+ sa[i] );
             rb.clear();
         }
 
--- a/jdk/test/java/nio/channels/DatagramChannel/Sender.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/nio/channels/DatagramChannel/Sender.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2002, 2010, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2002, 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
@@ -22,20 +22,24 @@
  */
 
 /* @test
- * @bug 4669040
+ * @bug 4669040 8130394
  * @summary Test DatagramChannel subsequent receives with no datagram ready
  * @author Mike McCloskey
  */
 
-import java.io.*;
-import java.net.*;
-import java.nio.*;
-import java.nio.channels.*;
-import java.nio.charset.*;
+import java.io.IOException;
+import java.io.PrintStream;
+import java.net.InetAddress;
+import java.net.InetSocketAddress;
+import java.net.SocketAddress;
+import java.nio.ByteBuffer;
+import java.nio.ByteOrder;
+import java.nio.channels.DatagramChannel;
 
 public class Sender {
 
     static PrintStream log = System.err;
+    static volatile SocketAddress clientISA = null;
 
     public static void main(String[] args) throws Exception {
         test();
@@ -81,6 +85,7 @@
                 InetAddress address = InetAddress.getLocalHost();
                 InetSocketAddress isa = new InetSocketAddress(address, port);
                 dc.connect(isa);
+                clientISA = dc.getLocalAddress();
                 dc.write(bb);
             } catch (Exception ex) {
                 e = ex;
@@ -118,13 +123,20 @@
         public void run() {
             SocketAddress sa = null;
 
+
             try {
                 ByteBuffer bb = ByteBuffer.allocateDirect(12);
                 bb.clear();
                 // Get the one valid datagram
                 dc.configureBlocking(false);
-                while (sa == null)
+                while (sa == null) {
                     sa = dc.receive(bb);
+                    if (sa != null && clientISA != null && !clientISA.equals(sa)) {
+                        log.println("Ignore a possible stray diagram from " + sa);
+                        sa = null;
+                    }
+                }
+                showBuffer("Received:", bb);
                 sa = null;
                 for (int i=0; i<100; i++) {
                     bb.clear();
--- a/jdk/test/java/nio/charset/Charset/NIOCharsetAvailabilityTest.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/nio/charset/Charset/NIOCharsetAvailabilityTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -46,9 +46,9 @@
         // two known charset implementation packages
         FileSystem fs = FileSystems.getFileSystem(URI.create("jrt:/"));
         Set<Class> charsets =
-            Stream.concat(Files.walk(fs.getPath("/java.base/sun/nio/cs/")),
-                          Files.walk(fs.getPath("/jdk.charsets/sun/nio/cs/ext/")))
-                 .map( p -> p.subpath(1, p.getNameCount()).toString())
+            Stream.concat(Files.walk(fs.getPath("/modules/java.base/sun/nio/cs/")),
+                          Files.walk(fs.getPath("/modules/jdk.charsets/sun/nio/cs/ext/")))
+                 .map( p -> p.subpath(2, p.getNameCount()).toString())
                  .filter( s ->  s.indexOf("$") == -1 && s.endsWith(".class"))
                  .map( s -> {
                      try {
--- a/jdk/test/java/nio/file/spi/SetDefaultProvider.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/nio/file/spi/SetDefaultProvider.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,6 +25,7 @@
  * @bug 4313887 7006126
  * @summary Unit test for java.nio.file.spi.FileSystemProvider
  * @build TestProvider SetDefaultProvider
+ * @ignore JDK-8129343
  * @run main/othervm -Djava.nio.file.spi.DefaultFileSystemProvider=TestProvider SetDefaultProvider
  */
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/CheckDefaults.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,67 @@
+/*
+ * Copyright (c) 2012, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+import java.security.KeyStore;
+import java.security.Security;
+import static java.lang.System.out;
+
+/**
+ * @test
+ * @bug 8048830
+ * @summary Set up keystore.type secure property and check that
+ * KeyStore.getDefaultType() value is related to property value. Expect a full
+ * match the value 'keystore.type' and the value of the
+ * KeyStore.getDefaultType()
+ * @run  main/othervm CheckDefaults
+ */
+public class CheckDefaults {
+    private static final String DEFAULT_KEY_STORE_TYPE = "pkcs12";
+    private static final String[] KEY_STORE_TYPES = {"jks", "pkcs12", "jceks",
+        "Unregistered_type_of_KS"};
+
+    private void runTest(String[] args) {
+        if (!KeyStore.getDefaultType().
+                equalsIgnoreCase(DEFAULT_KEY_STORE_TYPE)) {
+            throw new RuntimeException(String.format("Default keystore type "
+                    + "Expected '%s' . Actual: '%s' ", DEFAULT_KEY_STORE_TYPE,
+                    KeyStore.getDefaultType()));
+        }
+        for (String ksDefaultType : KEY_STORE_TYPES) {
+            Security.setProperty("keystore.type", ksDefaultType);
+            if (!KeyStore.getDefaultType().equals(ksDefaultType)) {
+                throw new RuntimeException(String.format(
+                        "Keystore default type value: '%s' cannot be set up via"
+                        + " keystore.type "
+                        + "security property, Actual: '%s'",
+                        ksDefaultType, KeyStore.getDefaultType()));
+            }
+        }
+        out.println("Test Passed");
+    }
+
+    public static void main(String[] args) {
+        CheckDefaults checkDefaultsTest = new CheckDefaults();
+        checkDefaultsTest.runTest(args);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/EntryProtectionTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,152 @@
+/*
+ * Copyright (c) 2012, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+import java.io.File;
+import static java.lang.System.err;
+import java.security.*;
+import java.security.cert.Certificate;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Random;
+import javax.crypto.spec.PBEParameterSpec;
+import jdk.testlibrary.RandomFactory;
+import static java.lang.System.out;
+import java.util.Arrays;
+
+/**
+ * @test
+ * @bug 8048830
+ * @summary Test for feature 'support stronger entry protection'. An entry is
+ * stored to keystore with different PasswordProtection objects which are
+ * specified by different PBE algorithms (use -Dseed=X to set PRNG seed)
+ * @library /lib/testlibrary ../
+ * @key randomness
+ */
+public class EntryProtectionTest {
+    private static final char[] PASSWORD = "passwd".toCharArray();
+    private static final String ALIAS = "testkey";
+    private static final byte[] SALT = new byte[8];
+    private static final int ITERATION_COUNT = 1024;
+    private static final List<KeyStore.PasswordProtection> PASSWORD_PROTECTION
+            = new ArrayList<>();
+    private static final String KEYSTORE_PATH = System.getProperty(
+            "test.classes" + File.separator + "ks.pkcs12",
+            "." + File.separator + "ks.pkcs12");
+
+    private void runTest() throws Exception {
+            KeyStore ksIn = Utils.loadKeyStore(KEYSTORE_PATH,
+                    Utils.KeyStoreType.pkcs12, PASSWORD);
+            KeyStore ksTest = KeyStore
+                    .getInstance(Utils.KeyStoreType.pkcs12.name());
+            ksTest.load(null);
+            Certificate cert = ksIn.getCertificate(ALIAS);
+            Key key = ksIn.getKey(ALIAS, PASSWORD);
+            KeyStore.Entry keyStoreEntry = new KeyStore.PrivateKeyEntry(
+                    (PrivateKey) key, new Certificate[]{cert});
+            for (KeyStore.PasswordProtection passwordAlgorithm :
+                    PASSWORD_PROTECTION) {
+                out.println("Try to use: " +
+                        passwordAlgorithm.getProtectionAlgorithm());
+                ksTest.setEntry(ALIAS, keyStoreEntry, passwordAlgorithm);
+                KeyStore.Entry entryRead = ksTest.getEntry(ALIAS,
+                        new KeyStore.PasswordProtection(PASSWORD));
+                if (!isPrivateKeyEntriesEqual((KeyStore.PrivateKeyEntry)
+                        keyStoreEntry, (KeyStore.PrivateKeyEntry)entryRead)) {
+                    err.println("Original entry in KeyStore: " + keyStoreEntry);
+                    err.println("Enc/Dec entry : " + entryRead);
+                    throw new RuntimeException(
+                            String.format(
+                                    "Decrypted & original enities do "
+                                    + "not match. Algo: %s, Actual: %s, "
+                                    + "Expected: %s",
+                                    passwordAlgorithm.getProtectionAlgorithm(),
+                                    entryRead, keyStoreEntry));
+                }
+                ksTest.deleteEntry(ALIAS);
+            }
+            out.println("Test Passed");
+    }
+
+    public static void main(String args[]) throws Exception {
+        EntryProtectionTest entryProtectionTest = new EntryProtectionTest();
+        entryProtectionTest.setUp();
+        entryProtectionTest.runTest();
+    }
+
+    private void setUp() {
+        out.println("Using KEYSTORE_PATH:"+KEYSTORE_PATH);
+        Utils.createKeyStore(Utils.KeyStoreType.pkcs12, KEYSTORE_PATH, ALIAS);
+        Random rand = RandomFactory.getRandom();
+        rand.nextBytes(SALT);
+        out.print("Salt: ");
+        for (byte b : SALT) {
+            out.format("%02X ", b);
+        }
+        out.println("");
+        PASSWORD_PROTECTION
+                .add(new KeyStore.PasswordProtection(PASSWORD,
+                                "PBEWithMD5AndDES", new PBEParameterSpec(SALT,
+                                        ITERATION_COUNT)));
+        PASSWORD_PROTECTION.add(new KeyStore.PasswordProtection(PASSWORD,
+                "PBEWithSHA1AndDESede", null));
+        PASSWORD_PROTECTION.add(new KeyStore.PasswordProtection(PASSWORD,
+                "PBEWithSHA1AndRC2_40", null));
+        PASSWORD_PROTECTION.add(new KeyStore.PasswordProtection(PASSWORD,
+                "PBEWithSHA1AndRC2_128", null));
+        PASSWORD_PROTECTION.add(new KeyStore.PasswordProtection(PASSWORD,
+                "PBEWithSHA1AndRC4_40", null));
+        PASSWORD_PROTECTION.add(new KeyStore.PasswordProtection(PASSWORD,
+                "PBEWithSHA1AndRC4_128", null));
+    }
+
+    /**
+     * Checks whether given two KeyStore.PrivateKeyEntry parameters are equal
+     * The KeyStore.PrivateKeyEntry fields like {privateKey, certificateChain[]}
+     * are checked for equality and another field Set<attributes> is not checked
+     * as default implementation adds few PKCS12 attributes during read
+     * operation
+     * @param  first
+     *         parameter is of type KeyStore.PrivateKeyEntry
+     * @param  second
+     *         parameter is of type KeyStore.PrivateKeyEntry
+     * @return boolean
+     *         true when both the KeyStore.PrivateKeyEntry fields are equal
+    */
+    boolean isPrivateKeyEntriesEqual(KeyStore.PrivateKeyEntry first,
+            KeyStore.PrivateKeyEntry second) {
+        //compare privateKey
+        if (!Arrays.equals(first.getPrivateKey().getEncoded(),
+                second.getPrivateKey().getEncoded())) {
+            err.println("Mismatch found in privateKey!");
+            return false;
+        }
+        //compare certificateChain[]
+        if (!Arrays.equals(first.getCertificateChain(),
+                second.getCertificateChain())) {
+            err.println("Mismatch found in certificate chain!");
+            return false;
+        }
+        return true;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/KeytoolReaderP12Test.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,156 @@
+/*
+ * Copyright (c) 2012, 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.
+ */
+
+import java.io.File;
+import java.io.IOException;
+import java.nio.file.Files;
+import java.nio.file.StandardOpenOption;
+import java.util.Base64;
+import jdk.testlibrary.OutputAnalyzer;
+import static java.lang.System.out;
+import java.nio.file.Paths;
+import java.util.List;
+
+/**
+ * @test
+ * @bug 8048830
+ * @summary Test for PKCS12 keystore list , export commands. Refer README for
+ * keystore files information
+ * @library /lib/testlibrary ../
+ * @run main KeytoolReaderP12Test
+ */
+public class KeytoolReaderP12Test {
+    private static final String WORKING_DIRECTORY = System.getProperty(
+            "test.classes", "."+ File.separator);
+    //private static final String KS_PASSWD = "pass";
+    private static final String KS_PASSWD = "storepass";
+    private static final String CERT_CHAIN_PASSWD = "password";
+    private static final String SOURCE_DIRECTORY =
+            System.getProperty("test.src", "." + File.separator);
+
+    public static void main(String[] args) throws Exception {
+        List<String> expectedValues = null;
+        out.println("Self signed test");
+        expectedValues = Files.readAllLines(Paths.get(SOURCE_DIRECTORY,
+                "api_private_key.p12_expected.data"));
+        readTest("api_private_key.p12.data", KS_PASSWD, expectedValues);
+        out.println("Self signed test Passed");
+
+        out.println("private key with selfsigned cert, key pair not match");
+        expectedValues = Files.readAllLines(Paths.get(SOURCE_DIRECTORY,
+                "api_private_key_not_match.p12_expected.data"));
+        readTest("api_private_key_not_match.p12.data", KS_PASSWD,
+                expectedValues);
+        out.println("private key with selfsigned cert, key pair "
+                + "not match passed");
+
+        out.println("cert chain test");
+        expectedValues = Files.readAllLines(Paths.get(SOURCE_DIRECTORY,
+                "api_cert_chain.p12_expected.data"));
+        readTest("api_cert_chain.p12.data", CERT_CHAIN_PASSWD, expectedValues);
+        out.println("cert chain test passed");
+
+        out.println("IE self test");
+        expectedValues = Files.readAllLines(Paths.get(SOURCE_DIRECTORY,
+                "ie_self.pfx.pem"));
+        exportTest("ie_self.pfx.data", "pkcs12testenduser1",
+                KS_PASSWD, expectedValues);
+        out.println("IE self test passed");
+
+        out.println("IE chain test");
+        expectedValues = Files.readAllLines(Paths.get(SOURCE_DIRECTORY,
+                "ie_chain.pfx.pem"));
+        exportTest("ie_chain.pfx.data", "servercert",
+                CERT_CHAIN_PASSWD, expectedValues);
+        out.println("IE chain test passed");
+
+        out.println("Netscape self");
+        expectedValues = Files.readAllLines(Paths.get(SOURCE_DIRECTORY,
+                "netscape_self.p12.pem"));
+        exportTest("netscape_self.p12.data", "pkcs12testenduser1",
+                KS_PASSWD, expectedValues);
+        out.println("Netscape self passed");
+
+        out.println("Mozilla self test");
+        expectedValues = Files.readAllLines(Paths.get(SOURCE_DIRECTORY,
+                "mozilla_self.p12.pem"));
+        exportTest("mozilla_self.p12.data", "pkcs12testenduser1",
+                KS_PASSWD, expectedValues);
+        out.println("Mozilla self test passed");
+
+        out.println("Openssl test");
+        expectedValues = Files.readAllLines(Paths.get(SOURCE_DIRECTORY,
+                "openssl.p12.pem"));
+        exportTest("openssl.p12.data", "servercert", CERT_CHAIN_PASSWD, expectedValues);
+        out.println("openssl test passed");
+
+        out.println("with different keystore and entrykey password");
+        expectedValues = Files.readAllLines(Paths.get(SOURCE_DIRECTORY,
+                "api_two_pass.p12_expected.data"));
+        readTest("api_two_pass.p12.data", KS_PASSWD,
+                expectedValues);
+        out.println("two pass test passed");
+    }
+
+    private static void readTest(String name, String password,
+            List<String> expectedValues)
+            throws IOException {
+        convertToPFX(name);
+        final String[] command = new String[]{"-debug", "-list", "-v",
+            "-keystore", WORKING_DIRECTORY + File.separator + name,
+            "-storetype", "pkcs12", "-storepass", password};
+        runAndValidate(command, expectedValues);
+    }
+
+    private static void exportTest(String name, String alias,
+            String password, List<String> expectedValues)
+            throws IOException {
+        convertToPFX(name);
+        final String[] command = new String[]{"-debug", "-export", "-alias",
+            alias, "-keystore", WORKING_DIRECTORY + File.separator + name,
+            "-storepass", password, "-storetype", "pkcs12", "-rfc"};
+        runAndValidate(command, expectedValues);
+    }
+
+    private static void runAndValidate(String[] command,
+            List<String> expectedValues) throws IOException {
+        OutputAnalyzer output = Utils.executeKeytoolCommand(command);
+        if (expectedValues != null) {
+            expectedValues.stream().forEach(line -> {
+                output.shouldContain(line);
+            });
+        }
+    }
+
+    /**
+     * Decodes the base64 encoded keystore and writes into new file
+     * @param name base64 encoded keystore name
+     */
+    private static void convertToPFX(String name) throws IOException{
+        File base64File = new File(SOURCE_DIRECTORY, name);
+        File pkcs12File = new File(WORKING_DIRECTORY, name);
+        byte[] input = Files.readAllBytes(base64File.toPath());
+        Files.write(pkcs12File.toPath(), Base64.getMimeDecoder().
+                decode(input), StandardOpenOption.CREATE);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/KeytoolWriteP12Test.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,128 @@
+/*
+ * Copyright (c) 2012, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+import java.io.File;
+import jdk.testlibrary.OutputAnalyzer;
+import static java.lang.System.out;
+
+/**
+ * @test
+ * @bug 8048830
+ * @summary Tests for creating pkcs12 keystore with various algorithms
+ * @library /lib/testlibrary ../
+ * @run main KeytoolWriteP12Test
+ */
+public class KeytoolWriteP12Test {
+    private static final String ALIAS = "pkcs12testCA";
+    private static final Utils.KeyStoreType PKCS12 = Utils.KeyStoreType.pkcs12;
+    private static final int FAILED_EXIT_CODE = 1;
+    private static final String CERT_FILE_NAME = "cert.data";
+    private static final String DNAME = "CN=PKCS12 Test CA, OU=Security SQE, "
+            + "O=JavaSoft, C=US";
+    private static final String WORKING_DIRECTORY = System.
+            getProperty("test.classes", "." + File.separator);
+    private enum Algorithm {
+        DSA, RSA, ECC
+    };
+    private void run() {
+        out.println("Running DSA Test");
+        keytoolListTest("kt_DSA.p12", Algorithm.DSA);
+        out.println("DSA Test passed");
+
+        out.println("Running RSA Test");
+        final String rsaKeyStoreName = "kt_RSA_MD5.p12";
+        keytoolListTest(rsaKeyStoreName, Algorithm.RSA);
+        out.println("RSA Test passed");
+
+        out.println("Running RSA and Signing Algorithm SHA1withRSA Test");
+        keytoolListTest("kt_RSA_SHA1.p12", Algorithm.RSA,
+                "-sigalg", "SHA1withRSA");
+        out.println("RSA and Signing Algorithm SHA1withRSA Test Passed");
+
+        out.println("Running Keysize 256 Test");
+        keytoolListNegativeTest("kt_DSA_256.p12", Algorithm.DSA, "-keysize",
+                "256");
+        out.println("Keysize 256 Test Passed");
+
+        out.println("Running Keysize 1023 Test");
+        keytoolListTest("kt_RSA_MD5_1023.p12", Algorithm.RSA, "-keysize",
+                "1023");
+        out.println("Keysize 1023 Test Passed");
+        out.println("Running Export certificate Test");
+        exportTest(rsaKeyStoreName);
+        out.println("Export certificate Test Passed");
+    }
+
+    private void exportTest(String keyStore) {
+        final String keyStoreName = WORKING_DIRECTORY + File.separator
+                + keyStore;
+        deleteKeyStoreFile(keyStoreName);
+        Utils.createKeyStore(DNAME, PKCS12, keyStore, ALIAS,
+                Algorithm.RSA.name());
+        final String certFilePath = WORKING_DIRECTORY + File.separator
+                + CERT_FILE_NAME;
+        Utils.exportCert(PKCS12, keyStore,
+                ALIAS, certFilePath);
+        final String[] command = new String[]{"-debug", "-printcert", "-v",
+            "-file", certFilePath};
+        Utils.executeKeytoolCommand(command);
+    }
+
+    private void keytoolListTest(String keyStore, Algorithm algorithm,
+            String ...optionalArgs) {
+        final String keyStoreName = WORKING_DIRECTORY + File.separator
+                + keyStore;
+        final String[] command = new String[]{"-debug", "-list", "-v", "-alias",
+            ALIAS, "-keystore", keyStoreName, "-storetype", "pkcs12",
+            "-storepass", Utils.DEFAULT_PASSWD};
+        deleteKeyStoreFile(keyStoreName);
+        Utils.createKeyStore(DNAME, PKCS12, keyStoreName, ALIAS,
+                algorithm.name(), optionalArgs);
+        OutputAnalyzer output = Utils.executeKeytoolCommand(command);
+        output.shouldContain(DNAME);
+    }
+
+    private void keytoolListNegativeTest(String keyStore, Algorithm algorithm,
+            String... optionalArgs) {
+        final String keyStoreName = WORKING_DIRECTORY  + File.separator
+                + keyStore;
+        deleteKeyStoreFile(keyStoreName);
+        Utils.createKeyStore(DNAME, PKCS12, keyStoreName, ALIAS,
+                algorithm.name(), optionalArgs, FAILED_EXIT_CODE);
+    }
+
+    public static void main(String[] args) {
+        KeytoolWriteP12Test test = new KeytoolWriteP12Test();
+        test.run();
+        out.println("Test Passed");
+    }
+
+    private void deleteKeyStoreFile(String fileName) {
+        File file = new File(fileName);
+        if (file.exists()) {
+            file.delete();
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/MetadataEmptyTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,79 @@
+/*
+ * Copyright (c) 2012, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+import java.io.File;
+import java.security.Key;
+import java.security.KeyStore;
+import java.security.KeyStoreException;
+import java.security.NoSuchAlgorithmException;
+import java.security.PrivateKey;
+import java.security.UnrecoverableKeyException;
+import java.security.cert.Certificate;
+import java.io.IOException;
+import java.security.cert.CertificateException;
+import static java.lang.System.out;
+
+/**
+ * @test
+ * @bug 8048830
+ * @summary Entry's attribute set should be empty
+ * @library /lib/testlibrary ../
+ * @run main MetadataEmptyTest
+ */
+public class MetadataEmptyTest {
+    private static final char[] PASSWORD = "passwd".toCharArray();
+    private static final String ALIAS = "testkey";
+    private static final String KEYSTORE_PATH = System.getProperty(
+            "test.classes" + File.separator + "ks.pkcs12",
+            "." + File.separator + "ks.pkcs12");
+
+    private void runTest() throws IOException, KeyStoreException,
+            NoSuchAlgorithmException, CertificateException,
+            UnrecoverableKeyException {
+        KeyStore ks = Utils.loadKeyStore(KEYSTORE_PATH,
+                Utils.KeyStoreType.pkcs12, PASSWORD);
+        Key key = ks.getKey(ALIAS, PASSWORD);
+        Certificate cert = ks
+                .getCertificate(ALIAS);
+        KeyStore.Entry entry = new KeyStore.PrivateKeyEntry(
+                (PrivateKey) key,
+                new Certificate[]{cert});
+        if (!entry.getAttributes().isEmpty()) {
+            throw new RuntimeException("Entry's attributes set "
+                    + "must be empty");
+        }
+        out.println("Test Passed");
+    }
+
+    public static void main(String[] args) throws Exception{
+        MetadataEmptyTest test = new MetadataEmptyTest();
+        test.setUp();
+        test.runTest();
+    }
+
+    private void setUp() {
+        Utils.createKeyStore(Utils.KeyStoreType.pkcs12, KEYSTORE_PATH, ALIAS);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/MetadataStoreLoadTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,148 @@
+/*
+ * Copyright (c) 2012, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+import java.io.File;
+import java.io.IOException;
+import java.security.GeneralSecurityException;
+import java.security.Key;
+import java.security.KeyStore;
+import java.security.KeyStoreException;
+import java.security.NoSuchAlgorithmException;
+import java.security.PKCS12Attribute;
+import java.security.PrivateKey;
+import java.security.UnrecoverableEntryException;
+import java.security.cert.Certificate;
+import java.util.Arrays;
+import java.util.Set;
+import static java.lang.System.out;
+import java.util.HashSet;
+
+/**
+ * @test
+ * @bug 8048830
+ * @summary Test store metadata attributes to PKCS12 keystore.
+ * @library /lib/testlibrary ../
+ * @run main MetadataStoreLoadTest
+ */
+public class MetadataStoreLoadTest {
+    private static final char[] PASSWORD = "passwd".toCharArray();
+    private static final char[] KEY_PASSWORD = "keypasswd".toCharArray();
+    private static final String ALIAS = "testkey_metadata";
+    private static final String KEYSTORE = "ks.pkcs12";
+    private static final String KESTORE_NEW = "ks-attr.pkcs12";
+    private static final int MAX_HUGE_SIZE = 2000000;
+    private static final String WORKING_DIRECTORY = System.getProperty(
+            "test.classes", "." + File.separator);
+    private static final String KEYSTORE_PATH = WORKING_DIRECTORY
+            + File.separator + KEYSTORE;
+    private static KeyStore.Entry.Attribute[] ATTR_SET;
+
+    private void runTest() throws GeneralSecurityException,
+            UnrecoverableEntryException, NoSuchAlgorithmException,
+            KeyStoreException, IOException {
+        storeAttrs();
+        checkAttrs();
+    }
+
+    private void storeAttrs() throws UnrecoverableEntryException,
+            GeneralSecurityException, NoSuchAlgorithmException,
+            KeyStoreException, IOException {
+        KeyStore ksIn = Utils.loadKeyStore(KEYSTORE_PATH,
+                Utils.KeyStoreType.pkcs12, PASSWORD);
+        KeyStore ksAttr = KeyStore
+                .getInstance(Utils.KeyStoreType.pkcs12.name());
+        ksAttr.load(null);
+        Key key = ksIn.getKey(ALIAS, PASSWORD);
+        Certificate cert = ksIn.getCertificate(ALIAS);
+        Set<KeyStore.Entry.Attribute> attrs =
+                new HashSet<>(Arrays.asList(ATTR_SET));
+        KeyStore.Entry e = new KeyStore.PrivateKeyEntry((PrivateKey) key,
+                new Certificate[]{cert}, attrs);
+        ksAttr.setEntry(ALIAS, e, new KeyStore.PasswordProtection(
+                KEY_PASSWORD));
+
+        out.println("Attributes before store:");
+        e.getAttributes().stream().forEach((attr) -> {
+            out.println(attr.getName() + ", '" + attr.getValue() + "'");
+        });
+        Utils.saveKeyStore(ksAttr, WORKING_DIRECTORY + File.separator
+                + KESTORE_NEW, PASSWORD);
+    }
+
+    private void checkAttrs() throws UnrecoverableEntryException,
+            GeneralSecurityException, NoSuchAlgorithmException,
+            KeyStoreException, IOException {
+        KeyStore ks = Utils.loadKeyStore(WORKING_DIRECTORY
+                + File.separator
+                + KESTORE_NEW, Utils.KeyStoreType.pkcs12, PASSWORD);
+        KeyStore.Entry keyStoreEntry = ks.getEntry(ALIAS,
+                new KeyStore.PasswordProtection(KEY_PASSWORD));
+        out.println("Attributes after store:");
+        //print attribute values
+        keyStoreEntry.getAttributes().stream().forEach((attr) -> {
+            out.println(attr.getName() + ", '" + attr.getValue() + "'");
+        });
+        Arrays.stream(ATTR_SET).forEach((attr) -> {
+            if (!keyStoreEntry.getAttributes().contains(attr)) {
+                throw new RuntimeException("Entry doesn't contain attribute: ("
+                        + attr.getName() + ", '" + attr.getValue() + "')");
+            }
+        });
+    }
+
+    public static void main(String[] args) throws Exception {
+        MetadataStoreLoadTest test = new MetadataStoreLoadTest();
+        test.setUp();
+        test.runTest();
+        out.println("Test Passed");
+    }
+
+    private void setUp() {
+        Utils.createKeyStore(Utils.KeyStoreType.pkcs12, KEYSTORE_PATH, ALIAS);
+        final String allCharsString = "`1234567890-=qwertyuiop[]asdfghjkl;'\\zx"
+                + "cvbnm,./!@#$%^&*()_+QWERTYUIOP{}ASDFGHJKL:|>ZXCVBNM<>?\"";
+        StringBuilder sbPrintable = new StringBuilder();
+        while (sbPrintable.length() < MAX_HUGE_SIZE) {
+            sbPrintable.append(allCharsString);
+        }
+        final String hugePrintable = sbPrintable.toString();
+        final String binaryString = "00:11:22:33:44:55:66:77:88:99:AA:BB:DD:"
+                + "EE:FF:";
+        StringBuilder sbBinary = new StringBuilder();
+        sbBinary.append(binaryString);
+        while (sbBinary.length() < MAX_HUGE_SIZE) {
+            sbBinary.append(":").append(binaryString);
+        }
+        sbBinary.insert(0, "[").append("]");
+        final String hugeBinary = sbBinary.toString();
+        ATTR_SET = new PKCS12Attribute[5];
+        ATTR_SET[0] = new PKCS12Attribute("1.2.840.113549.1.9.1",
+                "Test email addres attr <test@oracle.com>");
+        ATTR_SET[1] = new PKCS12Attribute("1.2.110.1", "not registered attr");
+        ATTR_SET[2] = new PKCS12Attribute("1.2.110.2", hugePrintable);
+        ATTR_SET[3] = new PKCS12Attribute("1.2.110.3", hugeBinary);
+        ATTR_SET[4] = new PKCS12Attribute("1.2.110.2", " ");
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/README	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,28 @@
+The test KeytoolReaderP12Test.java depends on keystore data files and validates 
+with output generated by keystore list/export commands
+
+KeyStore File                      storetype  aliasname  keyalg  SignatureAlgorithm
+------                             ------     ------     ------  ---
+api_private_key.p12.data           pkcs12     pkcs12testenduser1    RSA 1024	MD5withRSA
+api_private_key_not_match.p12.data pkcs12     pkcs12testca          RSA 2048	SHA1withRSA
+api_cert_chain.p12.data		   pkcs12     pkcs12testenduser1    RSA 1024	MD5withRSA
+api_two_pass.p12.data              pkcs12     pkcs12testca          RSA 2048	SHA1withRSA
+netscape_self.p12.data		   pkcs12     pkcs12testenduser1    RSA 1023 	MD5withRSA
+mozilla_self.p12.data		   pkcs12     pkcs12testenduser1    RSA 1023 	MD5withRSA
+ie_self.pfx.data		   pkcs12     a3aa3db3-3ec2-4d8b-8cf1-4d3c54afe386  RSA 1023 MD5withRSA
+ie_chain.pfx.data		   pkcs12     4e3053da-ff8e-46d2-b6d1-c38e431dea1f  RSA 1023 MD5withRSA
+
+Following keystore commands were used 	
+1. Generate keystore and along with keypair
+<JAVA-HOME>/bin/keytool -genkey -v -alias pkcs12test -keyalg "RSA" -keysize 2048 
+-sigalg "SHA1withRSA" -dname "cn=PKCS12 Test CA, ou=Security SQE, o=JavaSoft, 
+c=US" -validity 7300 -keypass storepass -keystore ks-pkcs.data -storepass 
+storepass -storetype pkcs12
+
+2. Export certificate 
+<JAVA-HOME>/bin/keytool -export -alias pkcs12test -keystore ks-pkcs.data 
+-storetype pkcs12 -storepass storepass -file pkcs12testCA.cer.data
+
+3. Import certificate
+<JAVA-HOME>/bin/keytool -import -alias pkcs12test -keystore ks-pkcs.data 
+-storepass storepass -file pkcs12testCA.cer.data
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/StoreTrustedCertAPITest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,97 @@
+/*
+ * Copyright (c) 2012, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileNotFoundException;
+import java.io.IOException;
+import java.security.KeyStore;
+import java.security.KeyStoreException;
+import java.security.NoSuchAlgorithmException;
+import java.security.cert.Certificate;
+import java.security.cert.CertificateException;
+import java.security.cert.CertificateFactory;
+import static java.lang.System.err;
+import static java.lang.System.out;
+
+/**
+ * @test
+ * @bug 8048830
+ * @summary Test imports certificate from file to PKCS12 keystore store it as
+ * trusted certificate Check import errors (must be not errors) & check keystore
+ * content after import
+ * @library /lib/testlibrary ../
+ * @run main StoreTrustedCertAPITest
+ */
+public class StoreTrustedCertAPITest {
+    private static final char[] PASSWORD = "passwd".toCharArray();
+    private static final String ALIAS = "testkey_stcapi";
+    private static final String WORKING_DIRECTORY = System.getProperty(
+            "test.classes", "." + File.separator);
+    private static final String CERT_PATH = WORKING_DIRECTORY + File.separator
+            + "cert.data";
+    private static final String KEYSTORE_PATH = WORKING_DIRECTORY
+            + File.separator + "ks.pkcs12";
+
+    /**
+     * Test logic (environment has set up)
+     */
+    private void runTest() throws FileNotFoundException, CertificateException,
+            KeyStoreException, IOException, NoSuchAlgorithmException {
+        Certificate cert;
+        CertificateFactory cf;
+        try (FileInputStream fi = new FileInputStream(CERT_PATH)) {
+            cf = CertificateFactory.getInstance("X.509");
+            cert = cf.generateCertificate(fi);
+            KeyStore ks = KeyStore.getInstance(
+                    Utils.KeyStoreType.pkcs12.name());
+            ks.load(null, null);
+            ks.setCertificateEntry(ALIAS, cert);
+            Utils.saveKeyStore(ks, KEYSTORE_PATH, PASSWORD);
+            ks = Utils.loadKeyStore(KEYSTORE_PATH, Utils.KeyStoreType.pkcs12,
+                    PASSWORD);
+            final Certificate ksCert = ks.getCertificate(ALIAS);
+            if (!ksCert.equals(cert)) {
+                err.println("Orig cert: " + cert.toString());
+                err.println("Cert from keystore: " + ksCert.toString());
+                throw new RuntimeException("Certificates don't match");
+            }
+        }
+    }
+
+    public static void main(String[] args) throws Exception {
+        StoreTrustedCertAPITest test = new StoreTrustedCertAPITest();
+        test.setUp();
+        test.runTest();
+        out.println("Test Passed");
+    }
+
+    private void setUp() {
+        Utils.createKeyStore(Utils.KeyStoreType.pkcs12, KEYSTORE_PATH, ALIAS);
+        Utils.exportCert(Utils.KeyStoreType.pkcs12, KEYSTORE_PATH,
+                ALIAS, CERT_PATH);
+        new File(KEYSTORE_PATH).delete();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/StoreTrustedCertKeytool.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,128 @@
+/*
+ * Copyright (c) 2012, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+import java.io.File;
+import java.io.IOException;
+import java.security.KeyStore;
+import java.security.KeyStoreException;
+import java.security.NoSuchAlgorithmException;
+import java.security.cert.CertificateException;
+import java.security.cert.X509Certificate;
+import jdk.testlibrary.OutputAnalyzer;
+import static java.lang.System.out;
+
+/**
+ * @test
+ * @bug 8048830
+ * @summary Tests keytool command imports certificate , list keystore, print
+ * certificate and import password help.
+ * @library /lib/testlibrary ../
+ * @run main StoreTrustedCertKeytool
+ */
+public class StoreTrustedCertKeytool {
+    private static final String PASSWORD = "passwd";
+    private static final String ALIAS = "testkey_stckey";
+    private static final String FILE_SEPARATOR = File.separator;
+    private static final String WORKING_DIRECTORY = System.getProperty(
+            "test.classes", "." + FILE_SEPARATOR);
+    private static final String CERT_PATH = WORKING_DIRECTORY
+            + FILE_SEPARATOR
+            + "cert.data";
+    private static final String KEYSTORE_PATH = WORKING_DIRECTORY
+            + FILE_SEPARATOR + "ks.pkcs12";
+
+    protected void run() throws IOException, KeyStoreException,
+            NoSuchAlgorithmException, CertificateException {
+        setUp();
+        importCert();
+        out.println("Import Cert test passed");
+        listCerts();
+        out.println("listCerts test passed");
+        printCert();
+        out.println("print cert test passed");
+        helpImportPassword();
+        out.println("help import test passed");
+    }
+
+    private void importCert() {
+        final String[] command = new String[]{"-debug", "-importcert",
+            "-alias", ALIAS, "-file", CERT_PATH, "-noprompt", "-keystore",
+            KEYSTORE_PATH, "-storetype", "pkcs12", "-storepass", PASSWORD};
+        // If the keystore exists delete it.
+        File keystoreFile = new File(KEYSTORE_PATH);
+        if (keystoreFile.exists()) {
+            keystoreFile.delete();
+        }
+        Utils.executeKeytoolCommand(command);
+    }
+
+    private void listCerts() throws IOException, KeyStoreException,
+            NoSuchAlgorithmException, CertificateException {
+        final String[] command = new String[]{"-debug", "-list", "-v",
+            "-alias", ALIAS, "-keystore", KEYSTORE_PATH, "-storetype", "pkcs12",
+            "-storepass", PASSWORD};
+        OutputAnalyzer output = Utils.executeKeytoolCommand(command);
+        if (output == null) {
+            throw new RuntimeException("Keystore print fails");
+        }
+        X509Certificate ksCert = null;
+        final KeyStore ks = Utils.loadKeyStore(KEYSTORE_PATH,
+                Utils.KeyStoreType.pkcs12, PASSWORD.toCharArray());
+        ksCert = (X509Certificate) ks.getCertificate(ALIAS);
+
+        if (ksCert == null) {
+            throw new RuntimeException("Certificate " + ALIAS
+                    + " not found in Keystore " + KEYSTORE_PATH);
+        }
+        String serialNumber = ksCert.getSerialNumber().toString(16);
+        output.shouldContain(serialNumber);
+    }
+
+    private void printCert() {
+        final String[] command = new String[]{"-debug", "-printcert",
+            "-file", CERT_PATH};
+        Utils.executeKeytoolCommand(command);
+
+    }
+
+    private void helpImportPassword() {
+        final String[] command = new String[]{"-debug", "-help",
+            "-importpassword"};
+        Utils.executeKeytoolCommand(command);
+    }
+
+    public static void main(String[] args) throws Exception {
+        final StoreTrustedCertKeytool test = new StoreTrustedCertKeytool();
+        test.run();
+        out.println("Test Passed");
+    }
+
+    private void setUp() {
+        Utils.createKeyStore(Utils.KeyStoreType.pkcs12, KEYSTORE_PATH, ALIAS);
+        Utils.exportCert(Utils.KeyStoreType.pkcs12, KEYSTORE_PATH, ALIAS,
+                CERT_PATH);
+        new File(KEYSTORE_PATH).delete();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/Utils.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,137 @@
+/*
+ * Copyright (c) 2012, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+import java.io.FileInputStream;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.security.KeyStore;
+import java.security.KeyStoreException;
+import java.security.NoSuchAlgorithmException;
+import java.security.cert.CertificateException;
+import java.util.Arrays;
+import java.util.List;
+import jdk.testlibrary.ProcessTools;
+import jdk.testlibrary.OutputAnalyzer;
+import jdk.testlibrary.JDKToolFinder;
+import static java.lang.System.out;
+import java.util.ArrayList;
+
+/**
+ * Helper class for creating keystore and executing keytool commands
+ */
+public class Utils {
+    public enum KeyStoreType {
+        jks, pkcs12;
+    }
+    public static final String DEFAULT_DNAME
+            = "CN=TestKey, T=FuncTestCertKey, O=Oracle, OU=JDKSQE, C=US";
+    public static final String DEFAULT_PASSWD = "passwd";
+    public static final String RSA = "rsa";
+    public static final String JAVA_HOME = System.getProperty("java.home");
+    public static final String KEYTOOL = "keytool";
+    private static final int SUCCESS_EXIT_CODE = 0;
+
+    public static OutputAnalyzer executeKeytoolCommand(String[] command) {
+        return executeKeytoolCommand(command, SUCCESS_EXIT_CODE);
+    }
+
+    public static OutputAnalyzer executeKeytoolCommand(String[] command,
+            int exitCode) {
+        String[] keytoolCmd = new String[command.length + 1];
+        OutputAnalyzer output = null;
+        try {
+            keytoolCmd[0] = JDKToolFinder.getJDKTool(KEYTOOL);
+            System.arraycopy(command, 0, keytoolCmd, 1, command.length);
+            output = ProcessTools.executeCommand(keytoolCmd);
+            output.shouldHaveExitValue(exitCode);
+            out.println("Executed keytool command sucessfully:"
+                    + Arrays.toString(keytoolCmd));
+        } catch (Throwable e) {
+            e.printStackTrace(System.err);
+            throw new RuntimeException("Keytool Command execution failed : "
+                    + Arrays.toString(keytoolCmd), e);
+        }
+        return output;
+    }
+
+    public static void createKeyStore(KeyStoreType type, String name,
+            String alias) {
+        createKeyStore(DEFAULT_DNAME, type, name, alias, RSA);
+    }
+
+    public static void createKeyStore(String dName, KeyStoreType type,
+            String name, String alias, String algorithm,
+            String... optionalArgs) {
+        createKeyStore(dName, type, name, alias, algorithm, optionalArgs,
+                SUCCESS_EXIT_CODE);
+    }
+
+    public static void createKeyStore(String dName, KeyStoreType type,
+            String name, String alias, String algorithm,
+            String[] optionalArgs, int exitCode) {
+        String[] command = new String[]{"-debug", "-genkeypair", "-alias",
+            alias, "-keystore", name, "-dname", dName, "-storepass",
+            DEFAULT_PASSWD, "-keypass", DEFAULT_PASSWD, "-validity", "7300",
+            "-keyalg", algorithm, "-storetype", type.name()};
+        if (optionalArgs != null && optionalArgs.length > 0) {
+            List<String> commandArgs = new ArrayList<>(Arrays.asList(command));
+            List<String> temp = Arrays.asList(optionalArgs);
+            commandArgs.addAll(temp);
+            if (!commandArgs.contains(("-keysize"))) {
+                commandArgs.add("-keysize");
+                commandArgs.add("1024");
+            }
+            command = commandArgs.toArray(new String[commandArgs.size()]);
+        }
+        executeKeytoolCommand(command, exitCode);
+    }
+
+    public static void exportCert(KeyStoreType type, String name,
+            String alias, String cert) {
+        String[] command = {"-debug", "-exportcert", "-keystore", name,
+            "-storetype", type.name(), "-storepass", DEFAULT_PASSWD, "-alias",
+            alias,"-file",cert,"-noprompt"};
+        executeKeytoolCommand(command);
+    }
+
+    public static KeyStore loadKeyStore(String file, KeyStoreType type,
+            char[] passwd)
+            throws IOException, KeyStoreException,
+            NoSuchAlgorithmException, CertificateException {
+        KeyStore ks = KeyStore.getInstance(type.name());
+        try (FileInputStream fin = new FileInputStream(file)) {
+            ks.load(fin, passwd);
+        }
+        return ks;
+    }
+
+    public static void saveKeyStore(KeyStore ks, String file, char[] passwd)
+            throws IOException, KeyStoreException, NoSuchAlgorithmException,
+            CertificateException {
+        try (FileOutputStream fout = new FileOutputStream(file)) {
+            ks.store(fout, passwd);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/api_cert_chain.p12.data	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,76 @@
+MIIQ6AIBAzCCEKIGCSqGSIb3DQEHAaCCEJMEghCPMIIQizCCBXAGCSqGSIb3DQEHAaCCBWEEggVd
+MIIFWTCCBVUGCyqGSIb3DQEMCgECoIIE+jCCBPYwKAYKKoZIhvcNAQwBAzAaBBSKdWqt6IsXyQA9
+6SNtYnk7vaT/CQICBAAEggTIv5XR91OsI7r831ltprYhtOfAhl3TFKj+cqnohJF1xm60K5dQN5BZ
+enfVw4YPbCTR16+zTiGyHJ/MFELwOrOogPdSQBTuy1PtUZOfskD/EKFQaCVSQ1omNlgOWqVh0dhF
+TMjw6KLaTfhwx2Qw3aLIjhy7rvS5SEsUbGZ/IvJ7ym+DHzFuP8oQFfISUkNxh7wOqk4BSsY1Yh9H
+JbK7Y7JtWReDTbAtuACQSPO0Z7RSWKC2y29cG6x3gIiB8iKTNrPKc6m0wb48RKipzF6r35GQRMoS
+rsordIc22RS/KYFfU4W9LAdV+/vJBuZazc+3MgcOXYUWDaMpAG697aim1yDjudcVnPoUdzdWQvAj
+Z7dHqeplZ8h4Ur+dKH3EeWoipXBXhVI0i9hFbOU+36OZ96LUjlRfaAI3NXVMEa9+kATwDHh9cqnQ
+1zkbVPCXBY6Y6+wnq5o0mpES++MCc8zELiFYZOJl6UWBE/D16QAv+6Qd/JHmRaZfNt+vNxKm1ltm
+nvdyWcO4FlF9F5cC66AS3NcdZ94GNkRBW964+yaUCFHCeVGSfwxqox++akNOyfrw9lP8a24usPLj
+ScueTLGCftprwUGLb9g/zRhPWBHrYELbUplER+KQeWnX84OqyAZXNnBUFhrH8CBJAPDIVCpZj7ti
+Z23eQoplPpL+z/CYKqx1BTk+E82+Z3cXXRhgiguXHqJhf8mR+3ZGsNsS0r23AnHQGJVvh09wbb02
+o1fAJpOkw34GGoLwqstakkO1/nKO2ln2g7UTdkzcGp9GCrhbxAmZ0jXjPy5RFG1m4yEhjAJ/lnRm
+3bwCb3z1mBjtrRO9hnb4iQBzwpvctHlVzAUh77JTbUzsu7TxrranUq2+Z1MWjqsymoPjDxct0GK0
+WrWV5iwVTIB73CW7IcKbAKVxsus9kRjbLaLxkfio6HGiYz2e+30CJX8sB5DPLBjfAZQiWMkq0k3T
+SfAKPRSlX7okdrXpfON57naUPw6biIcbDQovH7sMDSP58VLiGI7CNUuj5rhGu9O6Jhc6n5/krhjI
+W7xUkXZmZPq2yww1OSSD3LF4K7Uu6ukZMQU5NfUOVeeAkq+4RMns/nZdQd3JhP0CyuF4vLrEWq8n
+6WD+Sta3ZvCxbLPs9xylnlqevmq0zUhxbY7gzObEMGH1YpZT/nSjHpAbt0bcwFIiFncCC0t9/d07
+REJjWvG7J0GB9cNb4aNbE05fCx0tlipyNu2GASwT8fw0tPXrcdaHxL+1+/fDdLlsnrODN+Hvx2GC
+oixNMf1NSC1M0evf/8tqPDwwUBcKdFumILwEeWHwOP7Tx3/2eRfSPP3e6iGDYv0KrzHzWV2uyoXj
+bTwfRHs4W+71v91dtrKH8Q+IRKxkiSKdT0KnpDkGlnFwK88TAZso6L1agTshdtjvwNAJ/yaIN1S7
+FBBKcM2/rc3SJwNTmjsHrX3C8VvenO6rAxBvn151pzMjCY9eijJwnUKHEB8V3wSP+eSM/INL1swA
+BPIJba5Jg5Zhch4SpV8B5rjxAz+qkiLlGOxbsPeyfv3jzINZhkBqRtBA3gLxJjPgfPlu2s3U+HBa
+iHm0/K6VlSztjs4Ez30tfgym6vbWv/rrRXNfUqWumNqC5LXyDbVy7MarS5iKMUgwIwYJKoZIhvcN
+AQkUMRYeFABzAGUAcgB2AGUAcgBjAGUAcgB0MCEGCSqGSIb3DQEJFTEUBBJUaW1lIDE0MzI2OTE3
+MzM4NTgwggsTBgkqhkiG9w0BBwagggsEMIILAAIBADCCCvkGCSqGSIb3DQEHATAoBgoqhkiG9w0B
+DAEGMBoEFMrHJAy5G2zs/2U91Kv84axmE50HAgIEAICCCsDf0VQQ5aHERkv1me9S5cr3KQ73vg0h
+gawyFpFcMRGhzwMggy460MuwHIJk9aQ9rlvGi7FNWsPdBrwpJzyU6LFHUl5w/L94hjULrHeSaJ3T
+oltDs8jMK+I7Bx3B96kc5GvYzOlaq3OtRbITPs47a4qA7/TTAJxYC5pgTXiulu4lZ/scaHnBQc2N
+wX6ZFSKMz38lzEllA+ndnhgLNrL7yozrVFslFu0XrDcZC8ga4tm59rn/Dzmyz+hPcK+JKv7nq5gt
+MTGOGwtmaWUh/kSKPNETWVasa7UDlYexSwSadNlDSxWCHXEXb3YXOVvLDbnVB8OmWChBlw78vz/9
+UmeTpaCvH3SbgulOzW1TgsV4R7oTkib/Ck2R1XBPOssDg56VSeRrsd1pVy1GKxUsD/T5tih7wK1I
+IiLPrAh488GELpPadKjsv/990OSbv0q72V4kJWXn6m9RsQVGaOV2QiEjQPWSCq0FEglD8ikpg44X
+HpdCf5hL87iY1z0zONG8OP0IMEEJn091wfegCJZu5XsvT9PFaBm4mjMol1Hr1ZT/w6Qzfc/AmKn2
+serI/uAzOoMWGOEtzpof8M+DFD1saMCRG9Lf4A6fkub2968ZMbiSsdIu2YJefcOMWtmcW277l1Pz
+EjNlLXV40bfv/0tnBlbD2dYfGS2iCi4eMsWEWbV2kBq9gie24+NsDSlGXZjd7x9F0D7xUKGlXnR/
+4NzEilOURjEvxJloqd88K4xM1ZUELm/OYZwIkOmDZdqR1/8Wh82TYW5Mq4NKUbfltTOcvLE0fM5N
+VGyio8qGEVzgLWOGnh7V73QMBidu3cTWKf/OYYp13ywF0CxsGRVZmskFa3uH0C2pAoWnx13Plmo8
+lLtDFtxQ+u9ZBn8dZDGDD4gY2YSYj08/5MBWZQ5EWVLwn9A6xNGQMhFUuFhjmKCuulScaJ6v9aW4
+QBg5SfWzfuYD1G922wx7/TtQFBVR4NIKxTOroIjSpI+lYriNDa3c1UYRa+DY8suC90Wz90sbR37T
+QGOenU/QCSavPIiVijQzQbXz4eEMhddIwoCHTtkn4NgUO+pn4zMl9jCrwwMCSG1t2DZ1L6y67q4Q
+UnI0mU/O8cqglykl5Rz9G2TraHMv5SMGyHgi/jKyfGfAZriopPHWsXXNs85okMoM8j3YCFsM7EJ9
+l4We6J4euWK9WM7YboiSgKltJGXUgTU0l2HYN17ihF3sY3PaBiLdrNARM9blkzAhdhx0Q3NNFn3N
+7g0PniTkvW07aZoemdN/yric2grhC5P3rkuaw0j/AwTDC68ReJbOmdn7Gmv+4RSIXN9DIM/JV0Dd
+Xn06zLhnl9mim5hLtB1+f0E4oSz1MOOh1qoajm/lpr4o7zyHjb3v8mKrTMXvYO4PiQZ5HKWgvbB3
+iMCvdn859bv5X5ckz2SVtpnTjYTemICmEPRk7hRb/DZJkMptlhG2uFIq1ZUSDwVMGrrnRkEwlyLT
+f7wU5C2KoNGVgGhF9W6w/RBzYyTFVrsCTxpR9M9Jy875JnCmOBYUQLoDno+4qR00a70R2AdG7c3q
+gCZQBLzKqEp+gu0YUPGZzda1i8RhSF6c0w2A7ToynDf9gTbKSsyV1iblTm1UhjG/lXtU/9rzOMth
+7ZCrvd1EZGbmn2SP+CsQzoGMh9T0j+FygWx1u/yYO0kRXCjcyzOVq+p+XraDwxiI+GNcqNkrVKUW
+kIJO6ajXZg0cNekZyhiR3vLdY5EOBVWahvTnWFrEPpNt6tavVHyQ+AJP5t3VLq16AkBGgICYAdnG
+zKUgim96I0xNd37EKTmIlBccpNc0uVLgGEzuQiONBBcZPUwD6y4EvJnLmEaOdgRYjcaO8aeuIX/U
+VEC4zQEXI99ghQ7TWuNNOwyR+kyKQQsER5GRct9fzv6qMk0Xei914IdbL7DAy2pSfyaYNNlk339H
+/ji5lQPG1y8qQAw6sDtQPt0LcHg3bMX5Q/r1/LmlpML7rOUz1QwVH7QdHrHWjGvC1kjrmGtZjB7j
+XwQMItY3n/J1/vBfeuSk3sgWeHBYxgmnIjhqMVEoTSTUyelfrOte9N+5fomUWqnujl6rmqHl62oO
+695wUiKq6BVpXQtJEhqauQYAQ+DoGn3Klbmd5iHaqG5PU68wtEQPtSvXG6RPtteUi/H2jpnaG/Z+
+6HVQejCGJrZ4h1C/afq7WnCg5ZM8dy9zE02+CtqTq1hEiXF5mF6rhpKgxJZLlWk8wq0zP47ahnI+
+0VyAljgH5CW5BOwGrZdV8LHPbk+gVhqqBYIw/05HACbO4K32rEEUuvK+DSYQ0wxY8ufa1QttqQnv
+YRQ3XU+M4reL3pDJwPg+3LGP7jcIEqUY+trGeWbhASAETsLUURYuIkAydPKkEvb1rFPJGfiuMAVi
+PhSSTvDSrV8FZR9NNTr7zeHAbbJWArKi0hcv67noStYzBQT++SuiD5stp9Ym4DCE6/sAIR7Sa/1Y
+rhViLtpHp06WzkXi5lSVBCpJjaWKznmQp580gyAjjOx3mRqkEwx440yJq0LfqTdF8jiV2IZhjiT3
+MjdanLQOlldjGL64SpIKCQ0FzQcnB+sNbTtkYSRR9x4ImNYFGQpQtXimbAJAlaS5R4bOLbOygO/C
+mUDjpo1NkTIyAe/YzALpbCyJqaEOPm5Yp+1C6EQfb+DUxv2MyUWNuKw0xvFWhy4TuCCsrzIfQLYi
+2UxpILq8zr8ZhPUGv6KnN4j+jTo92A3DvtBbTLdRLf1n6hfAhWAOBmGu7c8N0kmfNcDJuWtvsG08
+1+xqLNni149FrNDzMjLwMg2YwaHJuwdKZsMcRtEfmGi2uAsTthsq6MxMHZPBFqNaNwrcaN7+PEK1
+c21PW/X6+kATvCRpKJxlChyZE5yEanvsIwpFB9IRmyEZIyYnCIcFl08Mbaw9jGdlxg32VdjIdQTY
+LVQ/8NOQGuz8RJepxoBQQ4dveiWJTPeEY879EC+3U8NgA84O3YZKfNxE4uSbjeGKu4tvVp5DoByW
+H7ZZWKAScltteuKFpP4ME6gGwvgF122HNzfrwztjcooIGfsxRvRSNerbAVjyZbBy3jC/3m3pOmqy
+kJfzhbVqEesBRCJKaCXVHZRSoziSqlwtMgbU+tPYGMERJT727cIFFKhqLILybZbc6LKI/SV852TD
+JXQ420HZX76GTSEWURDsu8glvYuGVosvBdg/63lVf8z15vJiaFbJEQDR7dHAquTAsynB2PVUErhJ
+sNz4kuQRbRoD6vS07fM2avNTLouZUX3bpwugyumgl2H0lvxLWXnXelFHnIc7NzdEqx6oS1YZBgq3
+7U21OG5t9hA02eZZT+LrcAWH1NUV2fFWps60WHKdCKcIN7w/vy/D8dDr1jdOppdubN35oR5ZOwob
+HYjk/KepGNTDeH8el2SX9yhjj5a0aTtMTdy/DvpAN7u9Xaq0bRH1lZZyE0n4F1MysND8sWwQPTH8
+uJoD4msqelGrx81lThyhwwk/8+2AWGG0sU9l0sK4xMmeMCPtdGdg9C4g5m08mHoa/etbOj+7spqf
+MG4Gq1hLOygsHwFRRQe3eRi4BSoE7HvgdyP84qVnLnc4g0RDLhFdDgyBLGTYRqpCX8iZA4Nf4uRJ
+pteB+CANzKjx9HqxBO/jGtOwFBg0eSXBU4d4CI6MoAS4NxUjlqhIGEKJBwJ78jPsCq2JMD0wITAJ
+BgUrDgMCGgUABBTxMWXHZ4F5ADtYXqKlpD5cMihu7wQUsiXIcUR/3TChw09nR5rrIaFsN+MCAgQA
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/api_cert_chain.p12_expected.data	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,7 @@
+MD5:  C6:17:CB:93:51:32:DA:C9:CF:0E:24:E3:16:FA:91:6A
+SHA1: 09:F1:08:B1:B3:28:22:23:22:F7:5F:6D:4A:8D:0E:0A:5E:6D:56:FB
+MD5:  C5:97:13:F6:24:E4:DF:9A:6B:4F:E8:73:90:78:24:95
+SHA1: 2B:CE:0C:E1:35:B9:9D:FE:5A:6E:25:88:01:F7:E9:E5:7B:89:17:42
+MD5:  0F:8A:2A:DB:D4:A5:CD:A6:9C:EE:DA:47:A0:9D:10:2B
+SHA1: 7D:48:4D:1C:F8:55:E8:79:6A:B0:19:E1:26:4F:AC:FD:57:6B:38:A0
+Alias name: servercert
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/api_private_key.p12.data	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,31 @@
+MIIGyAIBAzCCBoIGCSqGSIb3DQEHAaCCBnMEggZvMIIGazCCAzgGCSqGSIb3DQEHAaCCAykEggMl
+MIIDITCCAx0GCyqGSIb3DQEMCgECoIICsjCCAq4wKAYKKoZIhvcNAQwBAzAaBBTyKTFVy4z9Rja3
+Gd3aw4Eb49XnKQICBAAEggKAOFjH3xr57gTXK1A1jBzdxnY7ZaHVqeFrjAcouBC3DV+yR6x2bxNJ
+oEythXOYnC6flZu3NTbGkCd8AjGsUPgIy03SeRrQE8eKhhV981FOWuG1uHpa3wN1e3aCpaH7xvcG
+d+5cS2UUWd2ejrM5hc3GeQ+rGCGdguXEGWwznAYITlv8f81Cv0BliTlZCwHN06uJMMVLDhUlUwD7
++aVHHNjpSl/jZqtEFdrsQy4KFPJy9lvDW9oaQ/EGerWM5gTpvhJ2NFj1h/912BdFvsPMsniE7XPU
+z4M5vxiIagqJ1qZ+vxrHOMq7JPUj9r6LrM2/6nPq/LJxbn0PK5TIBHThmFLKyAw5A70rnyJzmwDf
+AIPSNu/OjORD04VVyDLZNKDM1rkSKA9Ot50lDfqv2z2n/8sVsv5kETNV0lEIslDM2ML3IF5LKmUi
+ErAqHZAA/iXcyAA63M62imBhSvnQdHp3XCE+YtgDqbKVCbRQDg7hcvVzWfEw1Q4ogCS/KG/cb5lJ
+/zWdlXXcNjdrOY0qh6rLc3+s1OjEHkvnFBIs7ljHBqGTNkUPdpLFhrzOtt9B/5vDdzAKisZmTmnM
+yN673KkQ/6dvY7SZLOnYOHOtyBuWN1h+28mN1nWYvuGLFHrtnuaxB0dMFD4sK1LsXYatd4q9+XUv
+/Kj4wQLVphz1bHWzpMSFioe/eLNlsCIwgshWuqKO9c+SLC69HnbdWUgG2iZzZpwOBCI9/4eR+WFW
+o3xFHeVUGSWFuMC+7vSNNvRWIeKBY9B+7QI2iKBTI5aXHC+UUTI1UbVBeEgS0Hp8eRZVgy3wCO7v
+Pt3QKH6NYkWXtQvOfX49d+x7pJzxqWqTqkeWjSQ8gTFYMDMGCSqGSIb3DQEJFDEmHiQAcABrAGMA
+cwAxADIAdABlAHMAdABlAG4AZAB1AHMAZQByADEwIQYJKoZIhvcNAQkVMRQEElRpbWUgMTQzMjY5
+OTg3NjU2ODCCAysGCSqGSIb3DQEHBqCCAxwwggMYAgEAMIIDEQYJKoZIhvcNAQcBMCgGCiqGSIb3
+DQEMAQYwGgQUIgsA0/PkplOYdNScW5OpBIVNLUkCAgQAgIIC2KY5LHfrfcdnYEuai+kP1qLfj0yP
+BDfSvwFyrx8aCFClmbVzHebM05tJfNpHWqDYzwTlVk+WtaXOnyrMP/1HWm6jNe3Id7WKHxlk7HIb
+FWbYdjy4/uHnyPeAIgFIltd1RdxXt5VDwTSAY4lwSwaEA+vvkycVfckzhmbUylclfy4HVNf/3d3e
+61VlLUbitSbnKX281Eek89yfKlB5YxQd0jHdXbdBNTB1eUM9s+Anm7p3emDMa1XR0N+lTehKLAyp
+znOe3ynqL1OxAiLH/4uv3EI4Ah3b09rB+JJ0+sAVRo1olMr2Q5lkQdMWxGBwIFHf1LI+JH05QWkx
+6a8niEfvQceybkgz+e9UPkdKNcX3UYV07rYIHnd3kg5lbsEotN1OdcMPgewg5OC3LbHG8wAlxyfR
+L+WAyFoA7QnFpNhBgstOx6jclTbSpMzjGKBCKb1tsKD6N9wNEKbluJetyQDAnQ7JjNsTpspYM8d6
+pUiX0t7PpaoBM8/sN3o1s5wp+c3jxCVUHGzKGymavx8ItKWKNQJCZdwvZPWjsjIytc8A0k3nVvK8
+qPUlXEj6raWGxnbWV5AUpQwu8SzysyfGHt/7dF9Scc+8uSA8FKGpqOczWktiwe6m8nYwGZAg9D/7
+ynXr8xq4N4LgsM3JlnHf8vIntPaoo8bNSIQCZV6FK7x84A1tnD1vQrZuzSdyW5G7L/FqaomRoaj2
+BCyeoxpgvldNp0TIR1rNsNAwLmur5+r/Qk5TslWtV1fEXpBQDKgboB7lzocAugi1+OPywEqyLQL/
+EjinsMKp+IxzKAFLEJTZF+VGaVHNhDo7UqZI0psp/SqX9lQZkuuQKK9zNrbaLnAHfcijHRKa0mH4
+lkvA3Xp3tdmatCzO3eHd/el2U9zGxQk66B4yJHZTuIS7ipMKrPQWfkRqVi9qqOwpgr9YAIvYrVAw
+4Ke6//xG/zeNpMf3iwq0a2MECex7/ZZuMD0wITAJBgUrDgMCGgUABBR+Gn1klUGKLNrlz1zvINy9
+OAbKhQQUbyJhmiLytWdKpRT8ywMAn/VMTkgCAgQA
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/api_private_key.p12_expected.data	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,3 @@
+MD5:  67:10:B1:84:A4:0B:AF:1F:5B:1A:C7:EB:C6:2C:DB:CE
+SHA1: 48:22:E2:C2:47:9F:75:E3:52:56:9C:20:37:DF:03:7F:CD:9F:87:38
+Alias name: pkcs12testenduser1
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/api_private_key_not_match.p12.data	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,21 @@
+MIIEpAIBAzCCBF4GCSqGSIb3DQEHAaCCBE8EggRLMIIERzCCBEMGCSqGSIb3DQEHBqCCBDQwggQw
+AgEAMIIEKQYJKoZIhvcNAQcBMCgGCiqGSIb3DQEMAQYwGgQUgIXKrki/1oMI4cCRpYWa/iQtL0cC
+AgQAgIID8L1nh0C0Gmm9/AbAYbiwBJeb5oCAHa5E6BXJO9DP+m7774lUoQFuAmHJRoqr9hRzJulD
+FfdkmRO9JdCs1tRgmnik66ybBb2wqr9gsAhPHFhDWuYIQTJcYqYlBTS8hbg5stDYWCeyaqK3+Zyp
+bV3nHZtCe0AO+Rd3derZ3qhluPhc2FWX05fIomTZNiJsbi5wp95ejH4tGX5OdQoWXBjDzlrxopUd
+pmdmHfJvRRTEtMr45VPfuHOkAX8Fe2tPFUgkE2tUalUth90AuPXVlMm5Ne+OdKcj+V2EN2s5JxA6
+28H1IL753Hov3R80/+Rzn+NIN/BCwLfHyTFa4Ur7Z2dyOJHvM5qeaz580RR8MwsEjqSpmXiyVhQW
+3LNuziqs21woC7ueDW7TLiLhHp2Mt8BqFyfUYqBoS29lchRTHZbWTN2h66xycXlzbUCGIOHDXPXB
+mqgxQWIltgluel+9Uf//D5yzIkXbtnW9dkMwKkybctAUs9VN8V44UBxv4+noSxepUs0iG+07c5Uu
+dfvzwYtnKqKUrtTT8tA/MBNd4P1paYJR2Angx5tInyNKp8TwOaSrFUfg9stMYMh2fbWHLJFS9RDz
+P7BDkrBgEO7jDu3O/XyyXzgUQRcQBv/Mw7sCFQ8BBMFzwf/dc6q277w+DJmwz2ex23iXQXQi/b6Y
+iHbPwYHVwURWpVAq3P36pCTYjnUpPHMgRKo/9Iy+tL39H46SyGqBFlriM4jDEu7dbi7n1MuMxRYD
+zocSkdsnlsJUBOhHLFFYIUIqx6jOgnOESKPWbG9XIHCTZJYnpasmP/VidrQMljzC7c3piePsI03D
+8NcJq+BqCRrX+7Z5vPAU022hMryQqHesgnx0T0dWXaCyabzjjjOaWvacxRRCiJ4+EFZqAahMNQp/
+XTNlpW1eI0oQ3YBlJl5FWuwhk6YuoNSoi8ya1wp42rFnTwXIG8enfa0wyx/ORAvfypW4wcohsCdP
+oRjc9foQsdcjxv2e1yMn9TlgjTOemY81mFfaSMa+4OIhSgLnIYI96QztrY9n8WHJer1hxVdKrb+8
+Mhf2vcNEToVF9ypst1C7fXSeOKdAYlNDskPAAm3prcuLMf1dzceIADr+4JOYxzdz6lLvjR+tpAHo
+zWO1xh73P+p+Bo82wxnoWCopqOUCEoAYhsy+JBGZNM4AHvPAo4g0Sett3qixZhvbmw9kzKsiFAjf
+wQHYPUfl0O02HvBizHK7dRDqJ94G/djGBhqfe34P0hKrCzW+n0u5nFmkFEdk50LpsTu0z3AaaaNh
+E6485FDeW3R3/67pGXglNJHBWPsl2AYFimUTzxQqOfoCzBiw9St7hNvuCJBv5jA9MCEwCQYFKw4D
+AhoFAAQUczIrgX5A0QTP7tpYDiY3MaSbEM8EFAprSM643ml+k9DGSQKZ7MG0UEhKAgIEAA==
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/api_private_key_not_match.p12_expected.data	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,3 @@
+MD5:  C5:97:13:F6:24:E4:DF:9A:6B:4F:E8:73:90:78:24:95
+SHA1: 2B:CE:0C:E1:35:B9:9D:FE:5A:6E:25:88:01:F7:E9:E5:7B:89:17:42
+Alias name: pkcs12testenduser1
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/api_two_pass.p12.data	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,46 @@
+MIIKGAIBAzCCCdIGCSqGSIb3DQEHAaCCCcMEggm/MIIJuzCCBYAGCSqGSIb3DQEHAaCCBXEEggVt
+MIIFaTCCBWUGCyqGSIb3DQEMCgECoIIE+jCCBPYwKAYKKoZIhvcNAQwBAzAaBBRXawh3kWXVQuH9
+IwNiyygBmKxSAAICBAAEggTINY1+d2I8JZk2edT/FddM9FOQ/jchyf+SE4a0eKQae4Hby2LrL+AG
+/+6MmRyvKOQYVthtxEAqoqUxsEPc35vr0xtiv/em42AUI5abfAnh8tTrgoCY4Zc3Gk/m7iS0XKQJ
+Eg/uiA2C6UbrS0soIjpBkNKxmh45L9hBtkOQkwRC2SqXPQy5g9ezwyPFWm3KsbdyMwnyJs2dMEnE
+p2D2BrdSfJwEZjDFLRFszQDLYvLgJcWzt8Zl3vdgVB6MDVGtT8Zdsa5cyxnplCQU+tWxP1U0uODn
+4uyM3PPujLwgwBl6EvCtR1ddcz8k4YMrIp0h1UbEGUibg7kaBmZ79xeZ94FWU0ulxW7sXX3YBSPH
+Nf4KM1fHshdAbwKZD2cR9yGG1fta/HnZN8y5YuQ9iNsAF+sJZATOysqa4/L8cst0Y1KpuirFkctp
+sVykTqCqiwOhSzQ0plMXG0rABhSX/Poapsl7ghY9jgK4d/zX1XJ34BQv896AjEQSBUs1NbybzNiK
+AzxV11JF/Mxdp29a8Y2tTr5NQVpnIEMlvxTwJgx662MPTlPyNUTxFWJfx/WkhI8VQzz3lqRhvOD4
+IvkKw91+BK5BrdSclrJ0P6R6Rak5zaXFMY3eveCQ1HQyU4Az84+xPw9NP9xO+5DQxRPbMDLZYLm/
+nMkwJAf/fXpto/2JeXkMPahuG6Qgr3dP53uEFwukQOsY6CG7/I/fumhZ5MoR63ez3WiNrAQXhQL8
+73+gkcWHHqmO4BB+3hkEjIfBf3v/o3VXrTIxmaEbMeQTb+FncoiimSmUP2NtFaty5tZaGE7AnznC
+RZT1q2fFckiKSjF3lRrgtnC7NIqfbSVKpa87W0TEkLMjrgZyj68c3aczXzJf0HHBSNJdHCufkv8V
+shDdqMuhmyo3ieJzjGnZ8eTIH7Dtm2LfgmlhDvid4HaCBvDLV3SEvY6w5YjwrA1a3/4I18tH0NJR
+MizgwzDspvvRHEjB1j4T8Vx/4uhmajlhWO6HOdLlkMB/fDZ1nr5D7Hl+S/530+Dq3ZUav+dwkiKg
+DpBYZgr4ETCY5tkeh8okfCboG76yb3nJNnZhO84EjZFnKECtZzdJL0viKclHPJnN358Zq0qP5hua
+CQN4hE3E5wsOaZC8eISWze8v4jTdedyq3Q3H+hE23oZ7vf7nXMzDbLAQzYZN/ISicWCUFufgLGXp
+crbze2dGmEVIYuGa8E/cHyKcNOJp3ISRVhGVxoPwdhniyXmqDqPLZ9C2HcPqHtrcuUchsTuLykx9
+B2LEnVKpWTTHahZ9aiT6g7s3WUMrlF1iHds9Tc5+YujlP1u3RiK1sg88SuTvwcBYw2fmQilk+JL1
+q5tIdTIwEVuX27GwugtDt4QJJnaEs2tjShXiIY2tPTSobYXIPDTKZJzxzZkbp8KUvNXg2zIVxcQC
+ztIdowkkoHpb/wpU9YdlgViDNk48o2fZRZ1HIOtmvilbSrOzj4yENz7i5jIhjspAOWB1/9fnAQzx
+rhgJfDhqtgVTuDoxxyAyagw8PXoNY5EaJlNzbd4tqpI9AS6r1w3GMBCH9sfMXJcNfBYb75XyKQHr
+LTiNysRBQmER5V8wxGVAq1Ktho+Tc/8gLoBHzoLkp04nlI5b+T7KjJDfsM4hMVgwMwYJKoZIhvcN
+AQkUMSYeJABwAGsAYwBzADEAMgB0AGUAcwB0AGUAbgBkAHUAcwBlAHIAMTAhBgkqhkiG9w0BCRUx
+FAQSVGltZSAxNDMyNzA4NzIxMDI1MIIEMwYJKoZIhvcNAQcGoIIEJDCCBCACAQAwggQZBgkqhkiG
+9w0BBwEwKAYKKoZIhvcNAQwBBjAaBBT1VlQaPNujgukJkTei7jHX1tc9BwICBACAggPgOU7D0OxN
+PwhrndRcfMpbu7smH2BiyXS390t8futsdTc0gX4Ekc9Sd2leVcEDnwf6GdqfFLKK8q3a0gFQPIbD
+y6DyD5CWhoouLo9DmfMqeETxeTSF9M3uJGoLdm1MUCCo0zJ39XrNxFQhgjPFWGYOQsZ894plqN3r
+tb0Gy5IOL3xZ6V5Bzv7/JckMYyV5Jd86GyUDKYcjHwUMTELMoKeANN0t3DCdbp/YmPCmKBiPtYRm
+MW/dp8l/5Wi+dBLxIJmd+IrWYgKcPBBsgny1FmiNpdAdRWUyCZvfzKpAITwgBrOwCZI071NMZ2+H
+LbUacBVEbKSRJuKbkd3cFNWe/tBOPCptlqer1biVt8gBx1K1UXA24kcvFex/AgXOE0vgBYv1R/++
+OPgV/Q2YBtANHTne+a9zzxVu6ZNnRFVKdkOUoWagF9I3rc0jNQSEt3CnbdbCbEhtpoDWYE7V4i0f
+JQf+avcyz3Eeb29m1e6foOeCGuiB9lfAHCLHadEhGUcpTJJ0A5JFLA+ua3MFBOtvrkq5mGQSQ2mT
+CH0t+sHoQbx/2+TTHvU2LAPVXhIum+yIWU5rIxDMJXDKSrEy7CKJEDsoJn3IyJNVZSysgYPJrlzT
+3zIdCG2xlQJ4O1hDqjBVgj//e+WDlt3Bz22zAOien/OjjF0UyE6gfyqaDgBozzaPDN+2bgaoglgj
+A9cDzJ/jAXNejXc99jKfpvECpbQev3GTqRRbs3kcEsZv1QW+HZj9beOKMxWIZWn/RqmEcFw8nk+2
+qvCkkXvJRYnvp5prH9V9l3THURR0TURHyeV1FQChOZOikfWmcEpg5xwmmDH7ji07/DsM+gn4d3rZ
+0ioGRovKy/WlQXOtkQJ/+y9huYiRXUDBMFY1pWjHdV1JOM8CzUAcS6143BpWC6wotPTBsyis/RmL
+8z5B44M1d0HkjgcFDQNHm2xR4W9uuCcrxkicU2e5GzO5bUDaBv7rnwBj7Fy/AiVhFCreJO6cVAFR
+kIyeLBrJGzlemscTbymrYsg2BydoxRXWU4wRmgZQQyRgQTxHZeNYtn5mpvV5D7m3HNCGxoYj46L2
+6P+FFoByASwSQpKrn6OnH42xmAs7HT/flOhz4e3cD1UuUcfqqITaOWSrX22Ew88JqzbLDgN/K5Eo
+TIMvtPSwihL4NLJpzG1HbuhnzmOiYtI3/IVhrDQ5dPYTUy+U1hasE1NTLM3xvdTBebksygbj3IMu
+wiW+reRdF5l0Pz9tz63MFu1FbKNrKEkg8Vw4cDEtnvpJRIO2VbVgZpdKhhMC7Z0T3xP9hEa8crv6
+/8qd5uY9mvY3RSKO0IdJSgkwPTAhMAkGBSsOAwIaBQAEFKSVvKysZX3JB3K2WGS6czUVRXZeBBTO
++FjQ0fq7d/D+Ilu6e2EBG1y/ngICBAA=
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/api_two_pass.p12_expected.data	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,3 @@
+MD5:  FE:A8:AA:47:D0:CB:A9:9D:9F:88:DC:4D:55:85:F4:95
+SHA1: 77:90:EC:65:C5:0C:FD:F2:1E:B0:3A:BD:43:21:1A:C6:FD:18:8C:AB
+Alias name: pkcs12testenduser1
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/ie_chain.pfx.data	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,65 @@
+MIIOWAIBAzCCDhIGCSqGSIb3DQEHAaCCDgMEgg3/MIIN+zCCBXAGCSqGSIb3DQEHAaCCBWEEggVd
+MIIFWTCCBVUGCyqGSIb3DQEMCgECoIIE+jCCBPYwKAYKKoZIhvcNAQwBAzAaBBSqiN24DSDipTd5
+Xb2bNDHnBDLKowICBAAEggTIGD+TSQT0ClN8f5xEDke7KNu7RmoMsfl6GpVcs7ohHbS1TRlU22T5
+eD7ftKYEtxS7mrQ40ePrw+eq4xkGarKXfNzLcUJ6mLvOtiyyz6KfzLbcqeicmuqBIZvOndSFYzS7
+c0sLvsymbMw6plSlVXEWbzGhdqTrmj/FPB6DSGPKh8HJCD5g3dW5HCe3I+WomlxVUaFAZg+Tzp1t
+2ZqerKzm9bVeGaBpDbzmazErdPqjeO616NG/yPo0sx3m9wdiYHV7RYdOiNsNFCwirR1zYATB+IAn
+l0d/Ma+ei1mcWKA04WoqFBrYijRAPSZK3yTjTqwIaaLynjQ0GM6h2VId2USKEKGiyvlL3nTyVnb/
+r5XVVzc7SWGS1fv9arnktR5tpJd+U55GPIs9D521wgEJ6PgXpEGpDpA1JB7icWdPJtE5YyjTQNXd
+pjwgZUYvUYLzN5X8fkr1FEnADmBMUOzf59f7lKkzzRdj+BtDlUtj3eNuUTUR6+dloJQenYnUf0jk
+F6LhsdxLFnJC32jBqCdBLWuKRyrKIwIX7S6LP5pEqgVTEeFzCa7xnCNgvgoMMxaIMLVRTCYgSv9x
+XU0bnyahESWXeJEjym3Avsjf+yXFS8HUz/M0AMQpbDWhFmWnK0hc3mP7gqMftVchrq8SkTS5Ri5X
+BsJIh0RaZwXrmeMML/+v7gHbEk8I747V+L8D6JSlszqDVhdNpxDTxUr95K5TjI79rgwSg4xTLyRw
+xVzQevVC8NdWqs3YDAr+N4piwz3wux/c6ozKytbKlNqrB7U/aKnOqFp5cmLI3NPuLEru5k4qTcox
+5yBcdgUGSOPruFX28q6dPbA+O6CDf2VRTqBMNQPyUB3qEr57MpaSH3LzydCvoZnW8R8CFpp9XqZC
+cgxRsYbq8DgJzwBsHpFHIHP7rQt1WNN4WcoQhE2FovMdAfztt+yXVzcu5EZfvHsycLwqLfuEfWVp
+iG/AUrAvRtgWgpoyoolaUWvDaBeUksMxcxuHEP8t3cgawWlbN6ABLkbPBaWRvvOFc9zoxuoirO+5
+XWt67rw5XooPKkpYhWGsOJzklPKENTHjYT/QIzcE42OHZU2nngg1b41kRzDBH3OFCZeF50qDSyUB
+WSUsnMNiO3rkA3ptrvVwpdpapotaE/zuF59ymOmc8U/BeW40o7LyW9qaUCxeiJN84Di1HYpgCE01
+dvUkvb+nI2y32E4Au6xOvJ658+U890rLXfzUwlxjIQON5OTj9XfH30QdVzNW1IVaXBCF8BRiKqH1
+7j5Sq/dh5nN3Y2kgxOE/e4yR8S2UUyOyWxcCVYxpgXbGNWpYq0+3AqejFrlMfPOWEWF0AQ1/VhJQ
+KtX5NgAdAjIkvbHFEnjnkHiJ2H1Bb3XfCXd41dqfNwTLPBug7kKA2HpWTcQc+EztwNRmW2NbMKT7
+X6L5JAmO6LRsWVnaAh+zNTsBLKpv0ELfsJzsTLS16zx54uBTuR1W+AUb8rhd6AnZl7OR2MGFjcAe
+ka6qq9hiN2Xf+6dO72uadQsWgHhYORoVPMhW1jdSv4cpTSS2Nb9ZZdEzRS9WADOq7rlwdnpluLiU
+umt/glhAuJ6y4UpgTydl9DOLgXRr3mbcs5UZN4dRfLTmsr4LJipnDniAH6DhMUgwIwYJKoZIhvcN
+AQkUMRYeFABzAGUAcgB2AGUAcgBjAGUAcgB0MCEGCSqGSIb3DQEJFTEUBBJUaW1lIDE0MzI3ODg4
+MDgwMjEwggiDBgkqhkiG9w0BBwagggh0MIIIcAIBADCCCGkGCSqGSIb3DQEHATAoBgoqhkiG9w0B
+DAEGMBoEFEuhX9gb3C7Sr2akNJMU545Ob/ynAgIEAICCCDCObKQs4Fle6w1joyIqB4TVMV7dnpfc
+nf+A5YhBNjl/tkFAwe620NC384/+yVmHx3vwhKzQNSCPuVFb+dw/0B4hl7ZDqMd8C/vcmiL+W1Tm
+tkU0v/DnpdUK5juX5ssX2guBWw0Ij0dr5dYlwgLhKv5hEQxVAH++ryw6cMimFJGWIl3EQM5+JapH
+W5A5LkPKDpF4FnbNtnZKthDDZwS9DHvf0XFcRc70diD+//xglq1LYvgVh3NMuNGzCwL7KVwRFSQ4
+SWai8/sdzQTFe6aLqslHvZx0XH0v92LG3icDT8At8LD4XYyOty3/qYFrJ45LL+lRwoQEO1P8UVT7
+pjAcijGdbJ5268SvsWC2nFnhensG3E+zmtOxHJGoSkjp4dfw4A8P1H8dfcoUKHiDqSx/jqgXLuAA
+JTGT4pKHyOzZrkunET4REU7OeyyZWHZQWH+Dn/XUYYi9TfmdDZ7NGzigi4tRwi2uabQs1aMITvgR
+9GIpqINHGFPJGJOFEMETaUVrt5Eb1EyFXUO+EKW5prRwy/VgAtb2M799EcviC8siolAL0RpaSRMM
+mpYFvWfvGwT3jlF7LZYlo45Qrs0thgPh0HCnCg+RCNwQericTazO8bUsjrzJZ7R4drQJnh5guU2+
+z5JuoEtReISw4PcGKqr2zlx+cmyumgRn2fWJiJ5ZDYm+ETeKxXvd9uR5Xq+qjAYPci14L6isOPYG
+pP5X6NSNX7jtp4ivGV3jBqzC43JbwPvwh88Xz6Ab8+b7Mu9LQHDAPV2zqQJwC6TDJdd6MOBYkIDe
+PmQizz0DsRtoDRiv+5bbASioOpT+4WpbEsrQ4APNNqOFbFQFQI7uwXFnlq/OjBvSc6YomXPzTi0M
+GEgV+yCcyQFKnDEIM691iUEIxVDTL76Z39fK6LtbKMfpRWVLFfPs3rd+nTF5X3AQCJPkk0YukMzI
+uth3zWWgTzfbAxtQPwQNnBM9j+x1HL0iX65191BCAhRXD4EGrL3aNHRG3gGrOozW7ChygPgvb0wf
+EYtnfK7aG58fdmG3+RQBxfq8/H7mf2lW+Y4XwSYBUdTH1bTwrxHmgnPlv4lc/0revPVUYuMMd19U
+W0/OSQhqnaOysYIvOZl1bUiWL0oZKUmTvNGx/TqMCNr1Zl1bYvB0fDK6CUgsV5mFDrGlM/ELR077
+tzYIwCakjN7wXsdXFSa1Pk0z2tEAtY192mT08hMGXquKCAfE9QAi7vfy/uhkOE4369hV9PTrdRS8
+j5BPBSb0m/F9Nq+CuSO9uEhpMm9neVZz7JQWZ09SqjY4rBBCVuTLSWMgguFvBXi7DMKJhY0i31u9
+qb0uRZEn2vB/m9F5KnCY9oZcnq//pCNxKOb8NMb6bla7KeLQdt+nfztX4Ilq0m677F1cpthWe4b9
+L3Tfh5SBKIOl0JtAdNHIh6UsLBnyTmA/EQO6KepuzKTJdNjrbD+HaFZCaDHc6glGGsI91cXYH+Mq
+LcDZIEUXmxRTH/EnKBaEQ9TIpByio5P5mw5JWT6DOu4+SLDDj6jqEzo1Df94Vtb86Um8vgNiw/ZH
+o5N6ww6onWBFcy0VHYhjYbdIDpmZABRpQmMKlYmQG4HGasRYwZ7r3LWdub9KB0ajM5/uatLUtrcH
+qWoeFtDTPMClW63oce0Vx17Ywc7HhEDizZje6w4bkeKjmuczhVR4qY7mNsjyHRiawgoWnnaWVKkw
+JaO6zdAFyWsxH+CmPEtaA1tgYpBqPjGSE6EsJCWV0SMApB/TR/cUmOZj1TfubMadUKlCSes11kSn
+/7y1WK0x/uxBCMDzs9CKjE1GHkIL4QAQR+FR/MB/OjEqvTdhnoap5pGIwRN57N1x0YTzYESsCiNT
+EfQfaSW6/JMMVV7IHEW2ndOC6GkLHc9Z9NdJ0qmJout5pQH7ULoDbyswNjgd395C+UjuT383/77d
+GpC91icQWTr/2Y/urPXKGH2cSRTxp3qtP54Xzpm7h7ufXJIP1Vc+GQNqbxYXkL4dPsw81Lg9gNoX
+FOYG/TfzwEpLrDnYJK0gml8A1GW6kQkJwM2vgjIjr40snsyLEkO8KHmyteJHF0oZa5rHY+ngwgt2
+Xy3seW9D4Td1Bi0s76qWJsg5IWwgiS/PG1PoxItyv5xUUtzoa7C1jLNFRi4AXP85NHvYvQH0u7cn
+x936ggiMFvcJYO9sSbet1JXXWloG2Lzv8xY07/rLlDrrTkFAXnZKyyZrRPt0+FEIBj/AXWnhq17v
+EfK0p0Us2rurgAi2xuufX1sB5jz4aIraA+Uq2OEZFjpo/tGthH+LPLVSt9r/j2yTBGqoki7w3TdE
+TyMV7xJkRs2mr9AurMsoORgdb+LxUuI5u1QS9xW5q1tNoEwTmrGfG3oergsDFmpty3c8DKJ1LJtL
+chuTi0lRpc9Js5hCuDRjDRaf2JaQwpo+OxvnQRWUWbVyS3UZX1tZj1gjcEEAeZPnItICeUl+igZd
+yvIPDBcwUUIuEG1sTcigsxh1e40AQ2+sl+8s90lbWLVQqpCrx511RukoPl2bWlcxR+GWnqhj1ssQ
+b+RBTQbj48qoke37CHdnwod/7aAwW/OFB6JlAu0h6G+OcCE7qmtav+We4XHsdXjfCL+k9Y3CNies
+36GeZEcTTsmrXplDHWLgBjEp5PVtTFE9NEe4h5YT1B8G6kPqOixPzNucpFZ8EGoenrcGOGSqTc3L
+9vRny/TJYEAjXMZBXo2QzNc9dGWcG0NhTadKQWuYxFew9C5OvxCu5D3kdTh2PWRpG/uynW+bpjUi
+KPgg9lY8mkHjvb+FmPDmOZla63V/TzA9MCEwCQYFKw4DAhoFAAQUQNid2ROQWDvYCz4DPzph7hci
+fAQEFPL7KYm4NrHpQSKpto5+pPs7NgLWAgIEAA==
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/ie_chain.pfx.pem	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,23 @@
+-----BEGIN CERTIFICATE-----
+MIID7DCCAtSgAwIBAgIBBDANBgkqhkiG9w0BAQsFADBXMQswCQYDVQQGEwJJTjEL
+MAkGA1UECAwCS0ExDDAKBgNVBAcMA2JscjEPMA0GA1UECgwGT3JhY2xlMQ0wCwYD
+VQQLDARKYXZhMQ0wCwYDVQQDDARMZWFkMB4XDTE1MDUyODAzNDMwN1oXDTI1MDUy
+NTAzNDMwN1owSzELMAkGA1UEBhMCSU4xCzAJBgNVBAgMAktBMQ8wDQYDVQQKDAZP
+cmFjbGUxDTALBgNVBAsMBEphdmExDzANBgNVBAMMBk1lbWJlcjCCASIwDQYJKoZI
+hvcNAQEBBQADggEPADCCAQoCggEBAMr07JoRV0kR5mNKgLFKLYeUQ2eFEyV8alkC
+3OL2Ew9tP9CT+60kqlbyLfxa8+8XU/SClch6yf7R4majR85PgfJuZKRvyUdWgw5y
+K0wbxWkRVqRAgSo0Zp8hkhV9BDe1R7s4r4XBI/rSVTQmDsMVZdigDtIDYKMS0BtW
+DnW4ueWbZHdNHyxlTEJc6trsvU2KH5pY69VgGZzonNuMa9p17aQpOnVbWNhS6Mcs
+mHonU5d19Xh543T8ovbA8cj0osdYgcOQ42FEBqON4Lih8SyhqZQyi4UvkiHek3Pu
+i5Q0dwwVT1lnorUwH3bXp4boMaUmh7bvKMe/BQ5T18wkXlgYuVECAwEAAaOBzjCB
+yzAJBgNVHRMEAjAAMCwGCWCGSAGG+EIBDQQfFh1PcGVuU1NMIEdlbmVyYXRlZCBD
+ZXJ0aWZpY2F0ZTAdBgNVHQ4EFgQUWDsl+9vHtuuQRhb+Zyd//f6qSXEwcQYDVR0j
+BGowaKFbpFkwVzELMAkGA1UEBhMCSU4xCzAJBgNVBAgMAktBMQwwCgYDVQQHDANi
+bHIxDzANBgNVBAoMBk9yYWNsZTENMAsGA1UECwwESmF2YTENMAsGA1UEAwwETGVh
+ZIIJAIQbGsfQ2qikMA0GCSqGSIb3DQEBCwUAA4IBAQABEg/vV+ckqMwwA6QLdk6i
+Q+oaYcjz2C7wcZmvmrdYGHUrtlf4aWQd4G/TDBtqKZ6MfA2AaciDe7lAI2agdKCM
+MFG6XeqtjElCa77b8KrE3Ha+N07pmYnU42vZrqMpayjj/Eey9bOuSaTgLVTA00BI
+5wiTbLokTrYW3lhMityeFyvGw7bEvfGbXLs/7hyZ6wEXindgaGT9adL9jz2LT2Tt
+YorRvxRSRMbBWCc6o+ICfawU226ZOetGVfdTSYgL3a9AQ+zAMhgdJq+ac077G1vA
+HzKZgygYAHIr1G0DxwEPOAHBQFtbTbAQURpjzKWFYeGiZuCEBwwsKgDIT0kGF76E
+-----END CERTIFICATE-----
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/ie_self.pfx.data	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,31 @@
+MIIGwAIBAzCCBnoGCSqGSIb3DQEHAaCCBmsEggZnMIIGYzCCAzAGCSqGSIb3DQEHAaCCAyEEggMd
+MIIDGTCCAxUGCyqGSIb3DQEMCgECoIICqjCCAqYwKAYKKoZIhvcNAQwBAzAaBBSZNW+Sd+0mytcN
+A/vZXbBxiRZHxgICBAAEggJ4YAYE4bHqC0rxj3w6eUmXqp/tebM75dLfm/YyOQqKTE5bPJNWAT2E
+njhtDTNDigxhLjy4tH1sligytYgABTOcBotniRGM9yZ/52JR7bv6NxGCbv+SU2v10Srug+onIhFM
+639E7bG1yRfNW7IATgKLX1KxIBWFX973MBnsDVK5gZEhy17hzLUdaJRk3AyiCIB17R3d0SthtIW+
+WR/1rYUDOUe4weJYPsVW+WwtYtdOllcDLopS+B/QgXPrv9FOLUfEHtNO9crLMnGU8Kr9uqMyHu99
+ZdIgH1wuuK3Na7noc4KI4Q3JoTsRRfWpl6nEt5FERpRY8Q1spNwzo9mZ9NwtVyMkjGfSnZP8RE7M
+2csqZESd88PGVcnrMzNb/y+5X1qgj+bx56v+6m91QcIcv3RMK645Wiow9WjtmZL5sGl0SNUcwzP1
+zYGjZrWnTICjMmuNDIDznX2yrtHLxoM8AzhUwIvirTROv+RaqO+gopDxTBy9kymPiHS6PLllC3hL
+GYqZ1CFCIkn7nf9DP4tKJmfvOhrURCFnbXSlIbu7d5j8TNI+6CLuD9H1c8vlp6kdvaJejLzAVFt8
+eY8A/zIDUKcyKXCFPS4F25X6vJ6ZdQOKBVzg8ueAUety6o44eJ7NxusLoMyHneLCTQ7jRobSihss
+eXa182Yk1Q+H7Dx+zbPr6FsNp8wNf90CM6zZAbgBqBzM5eGb2Y/Ich1eG2oLAFurrpqgxXlb6nJS
+nJ7e7NgAqf3S4VbKt3uCvVtrZfUUvCdx4BUfeNSNOGmAtgCRlPn93Gc2+IL7eJYNqDScNjGf/hj+
+rHCL7jNPRvoovzBdUSzJ1Y92r0iUWu4xWDAzBgkqhkiG9w0BCRQxJh4kAHAAawBjAHMAMQAyAHQA
+ZQBzAHQAZQBuAGQAdQBzAGUAcgAxMCEGCSqGSIb3DQEJFTEUBBJUaW1lIDE0MzI3MDQxMTIzNzQw
+ggMrBgkqhkiG9w0BBwagggMcMIIDGAIBADCCAxEGCSqGSIb3DQEHATAoBgoqhkiG9w0BDAEGMBoE
+FNSn/NMdKj9fmg+dMmEFE2rlvLY8AgIEAICCAtiFvAUXr/bKf77WWVx2Y9OnqlUNkXkeE7XEI5XB
+qKid6iUlv4eRWY3PyK5gLIDELGJHOIpHKAkjSef6kBU04E/jcQmg+kA+3GScXFZXTw+jjgGmaX9x
+zbAzXAvEURwh/T0HRtxsxXLf+7D3gdiIAQcVyh50xD58HOOox7mo1NFQ9Vi63f82wyJgQH1tYSid
+ExsC2ZJ2H7mncZrD/RtKgShwEmn8CTappx9iILVGkyRTbliWKxfr5EaEY0yXpDN8aj5N4pgGWg8O
+Qh9axIRFuTxhZ4jIDMEI6VUT0ugBn1rfBbaqWfmM3IfQZsQQsidARCISyajzjEDaiB0wRRCSuoyU
+FJdkCttHj8M85VvsRDN9YQa2ilBDfSjaJT8SQsvmMP8fpohnalGZsADBSTCZp1s6m5vgPErSCmY3
+w347fK3UtnDhtpxy6KvtiosJq2YLszC16O2KaiwvDoOteJSTv3aJfMXuZWF0QCBwN2pPhyPCnQZq
+sUe7YlnaihKqzAj+jyaWRI48HJY3y94zeEESXuY4Y1fgrWfsEuO7oHcqTvy0O10otPOnG5etIvNL
+uFBmYYL3Ag9HNKYHwl1d/lqrh7a3dHi8IuREQ1vY74sFbhefzDsZs4Foz0m60oJY2BeNl1BPtFKW
+yVrwIMKAlLovx5+sH/HvVtchabl0RPlNtYJNEUDVnp40OLE4B7fDQaNOY3hQJErCsE+ffhHMqy0k
+bLVM73XKBhS4GypIBx+GSZauuOXmxBKJCz/00ZUXfeRDqjSUe901eip9fILUmFObBlohbE02xt15
+8b0m+tHgj3aNvF5RkTnendRGh3D+O8hBWz9+AHSpIsXxemuWJ+VQgIeMOERwD+62zkEqLgOsn1pB
+3ZmN3pUl8mIWNDrdC7nGLU6YJt4PNVFRYtJIhuo8fN3I/Fk0CMCwZhZMsP8UcEH9GJOBK5/MtCds
+ZBMUE/UJsjlGCzcq/7OVTDA9MCEwCQYFKw4DAhoFAAQUPQnz3GvfsIzh1/29KwCg+E8LeVAEFMmb
+qHeo0noP26ViWalg3FeT8Lk+AgIEAA==
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/ie_self.pfx.pem	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,15 @@
+-----BEGIN CERTIFICATE-----
+MIICRTCCAa6gAwIBAgIEFjfyzjANBgkqhkiG9w0BAQQFADBWMQswCQYDVQQGEwJV
+UzEPMA0GA1UEChMGT3JhY2xlMRUwEwYDVQQLEwxTZWN1cml0eSBTUUUxHzAdBgNV
+BAMTFlBLQ1MxMiBUZXN0IEVuZCBVc2VyIDEwHhcNMTUwNTI3MDUyMTUyWhcNMzUw
+MjExMDUyMTUyWjBWMQswCQYDVQQGEwJVUzEPMA0GA1UEChMGT3JhY2xlMRUwEwYD
+VQQLEwxTZWN1cml0eSBTUUUxHzAdBgNVBAMTFlBLQ1MxMiBUZXN0IEVuZCBVc2Vy
+IDEwgZ4wDQYJKoZIhvcNAQEBBQADgYwAMIGIAoGAUPl3dSLSQd+ocj4oDJI6qdt+
+iIamUd6aDHllX/vNfguuX5G1/NO/aas5XofV9Zfy+XCdqGI/rUE294vod1BkBOiP
+UmsgHl30nWCwEq5FuFWLwLWgm2DkNMGVJnvvCVLDzuYhvkymNbOoppHywIMVAryP
+Xi2082vRKvW677VqcT0CAwEAAaMhMB8wHQYDVR0OBBYEFLpLVS5KZoGIDGmden5r
+AK3/D9+5MA0GCSqGSIb3DQEBBAUAA4GBAEomR40Sj+BvNYiL8Lfr2vMadCF23R3X
+fjPd3TCGuMJtI78N9lSTnrZCnrxn4ep7FuVl59jqEX7mBQcVtUNPqw/xrFI/sv4z
+Nwxa18TG78i85OXapvVsX1fWx0GeeK2XTKetHLMEc8zcW8IHcukSX+5Z6Y/pg+lB
+mqEx9bvLCJTW
+-----END CERTIFICATE-----
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/mozilla_self.p12.data	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,31 @@
+MIIGyAIBAzCCBoIGCSqGSIb3DQEHAaCCBnMEggZvMIIGazCCAzgGCSqGSIb3DQEHAaCCAykEggMl
+MIIDITCCAx0GCyqGSIb3DQEMCgECoIICsjCCAq4wKAYKKoZIhvcNAQwBAzAaBBR6huDKLG6JmXNE
+gLQSS7qhZPzNHQICBAAEggKAeoGHu8bLhxweaBp0O3ax8X/4fLqhEJxCc6mDZN0CNqEvsAf28Ozy
+73Mrm+W1oSd+y3J/A4AZX7Vqbzb01R1UagQSBGPv3emvpMZ0EoWTwe3uK8SZnco3xdgfAlqMou9a
+AqBWk8R/TRmBfN4Dx9P2CZabBtGjRabUWSk9ainDVjONEVnemOwIk1gU6wT5r0IekKC4p201lu3a
+OBnxtPnvHF6mIAJ26qYuq8T+9tUBcb11ZyzQIedgTeVLtHc4Kvq29KRLFB/IeW1FWFn4szYJRS0f
+Th1lh4dtFfUGThiJAIypYc7XH4+Q4LWUIvrjZ1gOdJzrXbF5+iuqyXtEMSGHHPCpPgUhpmW0VmGr
+2MI7kMNyBp8QvwpgB4M07kSVSF5rOjTWPl3QrJ2F+U/VvoLOjcdht8hVAyG7GJmIhpnmuVAaQQjo
+pbsVBRjE89GEP5R3YFTJ8hFPSnavQYXb9/vodAJSD/OhqJFc70pKnDQVKwiQ44JGLoeMgXzrbfpF
+VJLl0YM+/7jPZnTNlZ0TuMAKYJhENq7cxTb8Rt7uOQUoEEU9ceUhdxx+aQOlyYh7vQme80+hj9sE
+Ptv4Isy6HumhSTpg2Ge+9cFKnN4MNhn/mmo/2dSjIB5Nba6SlahKx18y4zQ+pKJWeMDNu4Se4uVx
+avHiy+1fKkeUtx0iNVTKbfDefkabABr/OIaJuC+EkLpXxU905ZrPebity95G8FWWG+XWLjKcmter
+B0KoREIDYWcy6Pc6FZIkR7rLE9FAYZ1EFdYtgP12EjizlZRsXeu4+OLXLM7JtFLJeUAUw0KCC/Pk
+2vYmQzODNmcvW4dCxE4Lv8r9JxzIdc4TcQc8/qvAnTFYMDMGCSqGSIb3DQEJFDEmHiQAcABrAGMA
+cwAxADIAdABlAHMAdABlAG4AZAB1AHMAZQByADEwIQYJKoZIhvcNAQkVMRQEElRpbWUgMTQzMjcw
+NDkyNTkzOTCCAysGCSqGSIb3DQEHBqCCAxwwggMYAgEAMIIDEQYJKoZIhvcNAQcBMCgGCiqGSIb3
+DQEMAQYwGgQUMQ+KLugaQj8beDrrbP7A6n1oGCACAgQAgIIC2JJCJPM5kJb0ngUEIl3npgicSI75
+OT1XXHUtRNB838JjtKf81IO4Ti1PVPQgVcDioK7Fhweb8U7bJi9bPJ2OnfyY/ICWgnsO8ckMXqFP
+QYWfHMbgSfBjojqIKFA3GqnK/NF4AScHedBOkeGaZxgWjbJPMzLE+zOdiFGxBcfgHrSrXX7orubh
+dG2m+rIXffyFwax7rS9FNVkHNcI6xw0TJ+XfXPOdAiSiIHfvFz/ST9AJp/RMOVGcTShSB/XwIS8c
+Skzzra8a7jtUXoBK3exsNAqwwt6qz/9ytg0LygI8M9fb8wej8w9KDUGd8Pf1E+zUWi+NPGV/WegS
+UkQYft8wIxBt3OKZSJLSpiN822ZTFvKgqUByLLglESROkjsV2eJ05hi7fU7V36h6J4Je5xDup4Xu
+tLTPryuH03TNKD8X/G2GkOM8jOTIvYnKlDhUHq8MKZ4qoxb1gOuM8gR3bnBCJTVfhClU7j/IVPWl
+aRyWmCKq+k4PUPAqaV3381S5Yxrx56rC3At/lw8NzIp8kjSeWoM4EYtX0/m6Nw15n7J28uzFAHj3
+LO3rlaZlW/LNtz2T2ROBFesg52jALbqBHOkILL1h/WN/r9CtbotBwxavX5xMZ6vWY4aGMAZjofOi
+tuFgXYmg4z2GugGgURdY3QI9fY+OBAEPySoAHVSVOvsa3h3pTHF59Ge9+8oHMDiDJFf4bo+LybvQ
+4WEvMlYJ6hF3yONLrHqDdqI+0aEja/Zk9UbDYXeRwHLyI+2V0FEH18k5bmxPpY0ca68pI04Tiwjf
+FmlW7dB1pSo7HYzAez0bA0QsyR3uCYRxHLNGPq26XYxVNNqywrclRfzw6jZq45JxAo5QeW3pRelU
+1gyCF+BTib+WznEnovDY9Poj9eoxVJoZNbBrLsJ52qOrT3pIkWY5c+GkOEK6cotoX+YhpL8ucn+i
+yPUpO1zZ55xsamRk6VitvbLZok88N98yMD0wITAJBgUrDgMCGgUABBS4le9ij+FqtmZ7BNgcK5Y/
+HR2zpAQUKYUZweQ2t1bPQ5Ug60MA7JcTgS4CAgQA
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/mozilla_self.p12.pem	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,15 @@
+-----BEGIN CERTIFICATE-----
+MIICRTCCAa6gAwIBAgIEL8ZaXTANBgkqhkiG9w0BAQQFADBWMQswCQYDVQQGEwJV
+UzEPMA0GA1UEChMGT3JhY2xlMRUwEwYDVQQLEwxTZWN1cml0eSBTUUUxHzAdBgNV
+BAMTFlBLQ1MxMiBUZXN0IEVuZCBVc2VyIDEwHhcNMTUwNTI3MDUzNTI1WhcNMzUw
+MjExMDUzNTI1WjBWMQswCQYDVQQGEwJVUzEPMA0GA1UEChMGT3JhY2xlMRUwEwYD
+VQQLEwxTZWN1cml0eSBTUUUxHzAdBgNVBAMTFlBLQ1MxMiBUZXN0IEVuZCBVc2Vy
+IDEwgZ4wDQYJKoZIhvcNAQEBBQADgYwAMIGIAoGARub+B5xAEtoE2Sv9+oRnKYIC
+AZZ5dpTdMUWiExsXBcK6KQ61X5GftMz4a5io7PoxJxsDkPyTPNaHov2dzOBblbn2
+Gd0YgRdI3jcmm6ELDN7CqzsO7FK48L8maLeIj/0hYPBZPxKohjChi2GUNKn97OMf
+Y0LTeDqpO6+oc2E25XECAwEAAaMhMB8wHQYDVR0OBBYEFLC2ChLxDu/yacB3s0ON
+NNDusz2SMA0GCSqGSIb3DQEBBAUAA4GBADhG2wSf4KHMspsKv8bkjWrDA6wTjwnx
+pQES8E2dMmmp/LybH0CerpcShGGw35uh8wnCaWA1hBgMAs1mfghTt9X8tZCG5MmA
+VmkR7VPu1lNbdB1sswXAy3/423ncWbPJKIvbXBLJrzvC3Ri6d/AiH/0Tud0H15IN
+YQ+ThBRF5iQC
+-----END CERTIFICATE-----
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/netscape_self.p12.data	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,31 @@
+MIIGyAIBAzCCBoIGCSqGSIb3DQEHAaCCBnMEggZvMIIGazCCAzgGCSqGSIb3DQEHAaCCAykEggMl
+MIIDITCCAx0GCyqGSIb3DQEMCgECoIICsjCCAq4wKAYKKoZIhvcNAQwBAzAaBBTCAQwl6bGuvgin
+MKu6yDFS0MTbSgICBAAEggKA+opmhScngYOULEBEohIPKypaCmqQ/W/bccSFYV5qBxkD8hUKsIr9
+pkgZzZBPFycpAfIL0lJ7BGQaTnQpFOxXZiDOnFxqFTk3s8QTXYYeEL2Q9PMf/wJ0RTpl4eJQlxF9
+j2IiNHhoFNhlarpvSdQxYP5K9OUIrGzEJ/hlpZIavwV3hnj14A0F+/nBviaRn2bnevsF4icjICW9
+8/jPp8TNg2UF+qQkKd1SpGZYo29a3dbgSuZn2PcPYT+CDQZ/V/W8ch1e+k+Lcdh5wBopnUyavONa
+v7lkd9WO8Tc0Y6pBBMBZukv3Fcny9DEgegh4dWxGIBZ4jMLGgW+MMpIi6P+TG8UrIPO5mBrRSC6e
+3LBS5YMZ5O08/Y7s2e2vDy1wcS6n3n9MvEVEwXGh9nl0noLUxZ8Rhk7gvi/FljeiycvVezJ8bUnD
+PFoVaZLYzK1i69u7ezT2P76yePVW10CgDpr97ijYFvItRcK+/sNQG7b0OHLIdAe38KmTfKE20MT4
+5/FXzlpmNdRXoOgv2BXJyGItiLa0YHpbCWRFhmapXkoIdmIw7yIV1YwHPyrujqpaAZn6QxKENGHe
+mf3fbwj7a+iECEYUufoIYZdKjav6ANhwmnD2CkPo7bCJVRJdj/XtObhjWLMP0yweotq5RjZM4IU7
+ODdm2TIvfRCRefo0x5APum0P7LgdZoFHANY0BAwn9jPnx7paTQFPN/xTDYT25xVX2b5iVqST5dVY
+rRZfi9RJYv9v5juVw3O7mTdxqoygQpubv3yAbdYqWeRrceel6GmU7NeRKs3NrZpB5PM0/ubTjxST
+oVna5JYWMtVE06tSJ+Rg9id0fOXoclRSPsSPKgP4+TFYMDMGCSqGSIb3DQEJFDEmHiQAcABrAGMA
+cwAxADIAdABlAHMAdABlAG4AZAB1AHMAZQByADEwIQYJKoZIhvcNAQkVMRQEElRpbWUgMTQzMjcw
+NDYxMjY5NTCCAysGCSqGSIb3DQEHBqCCAxwwggMYAgEAMIIDEQYJKoZIhvcNAQcBMCgGCiqGSIb3
+DQEMAQYwGgQUpkMQUxHga8S4M8fk95EXXaGgzZ0CAgQAgIIC2K4Jn6KosJncNg7SfDaU4TbNFLHS
+YB2TMCOi/qgw5NAnMUboxDqANbwEd53I2MrrgKYvnsH0SaKwACV5ILgMn6oaFmEalVR1rV1r1L/G
+XHj21Zo0XdxI7aGowYDcbZ0GspQ14qi5+FxxcV20bm6o8XjxtSiGCnsfCUeZxqsNfSDHU+dMA2Ki
+ubY/xmxlmKQPIQFHywheV7a+fIyhgi2IXitXDXjiYfv9haja9nxl6/mCMzVup3DPQ0Um83Wf7fly
+FRpQCh7wxd6pL0XZPllJ1llmEu1bKwz3gYTW19Wx2UPAzvbJvhG2X7SM6TbIlJhhiF+x9rO0jBZM
+89NxdVwNYfFqAJNmJnRZbXjDvg9A623bBzxNCmCR3oswlYTB5lGwQ22FXDUioW3S6BFASFg59TPF
+e3zir4ao3T/bucSQa2sKKW454vDi1Nhs9r7B8nQ4eZxviToHOlw468M+N1LgHqoGb4P20kCucc0K
+zUYbPuTJIEIxuNFzpT0Zc72YcqD3bSdK8xSxIYy9Vi18+JCBWEOX2oMiWWxmJJq5HFEi0DcxjAAc
+d0khIxMTJIjQ+F5pUGSo4V8/GaSQkxNpb4yYBbGSwd08S+DBgiFfL03TZqlqbS19mDrfRwyGyJjv
+CwK2gVdM9XgSPEG9nVapuWj9AZi4pWiDkKo+IkhZpElWjJIu1Zp4RD90BW9GRaXFKsuD517e4x+q
+B3q8ycQiDgjQXAaSpTPoH04HQy9S/gdUbIekAVZl9ORmzH4XUXuV+nC3+wkwQ1UMvKKKjPoDpSa7
+eIHYtrg6bQPD41kIrG1iRi/5r14ARIsLq3XMXx2iG/fhYVub2ZR37fWWuf/rogl3to3gfey1KIb8
+vcl3FbUaHQ8XOyvHnytCwLjmr6ntMQlcE5ehN2IoCxD3eojlSy5lPF+fAUT0S21hl5ZEjL2ujAJm
+5HKH/m2zEGcqKb4S8Nhfnt/L1F0L7Oz2MD0wITAJBgUrDgMCGgUABBTE7Dt3V4d3L/CZttQjo08Y
+KdM5PQQUIa9fu0bxNWT30V5EgPtnjo1pK3cCAgQA
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/netscape_self.p12.pem	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,16 @@
+-----BEGIN CERTIFICATE-----
+MIICRTCCAa6gAwIBAgIECrE+nTANBgkqhkiG9w0BAQQFADBWMQswCQYDVQQGEwJV
+UzEPMA0GA1UEChMGT3JhY2xlMRUwEwYDVQQLEwxTZWN1cml0eSBTUUUxHzAdBgNV
+BAMTFlBLQ1MxMiBUZXN0IEVuZCBVc2VyIDEwHhcNMTUwNTI3MDUzMDEyWhcNMzUw
+MjExMDUzMDEyWjBWMQswCQYDVQQGEwJVUzEPMA0GA1UEChMGT3JhY2xlMRUwEwYD
+VQQLEwxTZWN1cml0eSBTUUUxHzAdBgNVBAMTFlBLQ1MxMiBUZXN0IEVuZCBVc2Vy
+IDEwgZ4wDQYJKoZIhvcNAQEBBQADgYwAMIGIAoGAUJKwuZJOuG+EZ9d8L4BDYOzv
+2sFCyCTrDbw6lH/vaG/kkhJgZdYMV1pwqxmsspUrSYwATx3usPElv+OOjEJlwuLo
+wj+/6Ob9LirwUAHb9LbcF5r9dRxLBcFUaTnDlqzgOuS1gn9dnD9z4CugId9t9IjF
+tLiump5zXNcZw/+/JKMCAwEAAaMhMB8wHQYDVR0OBBYEFOKLf8ckktSBUTDRoYxV
+b56vtgd8MA0GCSqGSIb3DQEBBAUAA4GBACgrbEqfqtgKx0iLiQEgKb4K+O4Gg8Td
+wuSjtXn9WQR5Fux7XNoM8f3xRw95CROg1/JEYhsH7fzeG/Aq6BbFooyHZsQ7yGXJ
+ujJ3O7hl0MuFZRChf9QP7YQjYb4toj1wdE0EvA9lNWomr2Ox9b3+QFTdxPcBElv6
++ImhOPtF6/lt
+-----END CERTIFICATE-----
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/openssl.p12.data	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,76 @@
+MIIQ6AIBAzCCEKIGCSqGSIb3DQEHAaCCEJMEghCPMIIQizCCBXAGCSqGSIb3DQEHAaCCBWEEggVd
+MIIFWTCCBVUGCyqGSIb3DQEMCgECoIIE+jCCBPYwKAYKKoZIhvcNAQwBAzAaBBSKdWqt6IsXyQA9
+6SNtYnk7vaT/CQICBAAEggTIv5XR91OsI7r831ltprYhtOfAhl3TFKj+cqnohJF1xm60K5dQN5BZ
+enfVw4YPbCTR16+zTiGyHJ/MFELwOrOogPdSQBTuy1PtUZOfskD/EKFQaCVSQ1omNlgOWqVh0dhF
+TMjw6KLaTfhwx2Qw3aLIjhy7rvS5SEsUbGZ/IvJ7ym+DHzFuP8oQFfISUkNxh7wOqk4BSsY1Yh9H
+JbK7Y7JtWReDTbAtuACQSPO0Z7RSWKC2y29cG6x3gIiB8iKTNrPKc6m0wb48RKipzF6r35GQRMoS
+rsordIc22RS/KYFfU4W9LAdV+/vJBuZazc+3MgcOXYUWDaMpAG697aim1yDjudcVnPoUdzdWQvAj
+Z7dHqeplZ8h4Ur+dKH3EeWoipXBXhVI0i9hFbOU+36OZ96LUjlRfaAI3NXVMEa9+kATwDHh9cqnQ
+1zkbVPCXBY6Y6+wnq5o0mpES++MCc8zELiFYZOJl6UWBE/D16QAv+6Qd/JHmRaZfNt+vNxKm1ltm
+nvdyWcO4FlF9F5cC66AS3NcdZ94GNkRBW964+yaUCFHCeVGSfwxqox++akNOyfrw9lP8a24usPLj
+ScueTLGCftprwUGLb9g/zRhPWBHrYELbUplER+KQeWnX84OqyAZXNnBUFhrH8CBJAPDIVCpZj7ti
+Z23eQoplPpL+z/CYKqx1BTk+E82+Z3cXXRhgiguXHqJhf8mR+3ZGsNsS0r23AnHQGJVvh09wbb02
+o1fAJpOkw34GGoLwqstakkO1/nKO2ln2g7UTdkzcGp9GCrhbxAmZ0jXjPy5RFG1m4yEhjAJ/lnRm
+3bwCb3z1mBjtrRO9hnb4iQBzwpvctHlVzAUh77JTbUzsu7TxrranUq2+Z1MWjqsymoPjDxct0GK0
+WrWV5iwVTIB73CW7IcKbAKVxsus9kRjbLaLxkfio6HGiYz2e+30CJX8sB5DPLBjfAZQiWMkq0k3T
+SfAKPRSlX7okdrXpfON57naUPw6biIcbDQovH7sMDSP58VLiGI7CNUuj5rhGu9O6Jhc6n5/krhjI
+W7xUkXZmZPq2yww1OSSD3LF4K7Uu6ukZMQU5NfUOVeeAkq+4RMns/nZdQd3JhP0CyuF4vLrEWq8n
+6WD+Sta3ZvCxbLPs9xylnlqevmq0zUhxbY7gzObEMGH1YpZT/nSjHpAbt0bcwFIiFncCC0t9/d07
+REJjWvG7J0GB9cNb4aNbE05fCx0tlipyNu2GASwT8fw0tPXrcdaHxL+1+/fDdLlsnrODN+Hvx2GC
+oixNMf1NSC1M0evf/8tqPDwwUBcKdFumILwEeWHwOP7Tx3/2eRfSPP3e6iGDYv0KrzHzWV2uyoXj
+bTwfRHs4W+71v91dtrKH8Q+IRKxkiSKdT0KnpDkGlnFwK88TAZso6L1agTshdtjvwNAJ/yaIN1S7
+FBBKcM2/rc3SJwNTmjsHrX3C8VvenO6rAxBvn151pzMjCY9eijJwnUKHEB8V3wSP+eSM/INL1swA
+BPIJba5Jg5Zhch4SpV8B5rjxAz+qkiLlGOxbsPeyfv3jzINZhkBqRtBA3gLxJjPgfPlu2s3U+HBa
+iHm0/K6VlSztjs4Ez30tfgym6vbWv/rrRXNfUqWumNqC5LXyDbVy7MarS5iKMUgwIwYJKoZIhvcN
+AQkUMRYeFABzAGUAcgB2AGUAcgBjAGUAcgB0MCEGCSqGSIb3DQEJFTEUBBJUaW1lIDE0MzI2OTE3
+MzM4NTgwggsTBgkqhkiG9w0BBwagggsEMIILAAIBADCCCvkGCSqGSIb3DQEHATAoBgoqhkiG9w0B
+DAEGMBoEFMrHJAy5G2zs/2U91Kv84axmE50HAgIEAICCCsDf0VQQ5aHERkv1me9S5cr3KQ73vg0h
+gawyFpFcMRGhzwMggy460MuwHIJk9aQ9rlvGi7FNWsPdBrwpJzyU6LFHUl5w/L94hjULrHeSaJ3T
+oltDs8jMK+I7Bx3B96kc5GvYzOlaq3OtRbITPs47a4qA7/TTAJxYC5pgTXiulu4lZ/scaHnBQc2N
+wX6ZFSKMz38lzEllA+ndnhgLNrL7yozrVFslFu0XrDcZC8ga4tm59rn/Dzmyz+hPcK+JKv7nq5gt
+MTGOGwtmaWUh/kSKPNETWVasa7UDlYexSwSadNlDSxWCHXEXb3YXOVvLDbnVB8OmWChBlw78vz/9
+UmeTpaCvH3SbgulOzW1TgsV4R7oTkib/Ck2R1XBPOssDg56VSeRrsd1pVy1GKxUsD/T5tih7wK1I
+IiLPrAh488GELpPadKjsv/990OSbv0q72V4kJWXn6m9RsQVGaOV2QiEjQPWSCq0FEglD8ikpg44X
+HpdCf5hL87iY1z0zONG8OP0IMEEJn091wfegCJZu5XsvT9PFaBm4mjMol1Hr1ZT/w6Qzfc/AmKn2
+serI/uAzOoMWGOEtzpof8M+DFD1saMCRG9Lf4A6fkub2968ZMbiSsdIu2YJefcOMWtmcW277l1Pz
+EjNlLXV40bfv/0tnBlbD2dYfGS2iCi4eMsWEWbV2kBq9gie24+NsDSlGXZjd7x9F0D7xUKGlXnR/
+4NzEilOURjEvxJloqd88K4xM1ZUELm/OYZwIkOmDZdqR1/8Wh82TYW5Mq4NKUbfltTOcvLE0fM5N
+VGyio8qGEVzgLWOGnh7V73QMBidu3cTWKf/OYYp13ywF0CxsGRVZmskFa3uH0C2pAoWnx13Plmo8
+lLtDFtxQ+u9ZBn8dZDGDD4gY2YSYj08/5MBWZQ5EWVLwn9A6xNGQMhFUuFhjmKCuulScaJ6v9aW4
+QBg5SfWzfuYD1G922wx7/TtQFBVR4NIKxTOroIjSpI+lYriNDa3c1UYRa+DY8suC90Wz90sbR37T
+QGOenU/QCSavPIiVijQzQbXz4eEMhddIwoCHTtkn4NgUO+pn4zMl9jCrwwMCSG1t2DZ1L6y67q4Q
+UnI0mU/O8cqglykl5Rz9G2TraHMv5SMGyHgi/jKyfGfAZriopPHWsXXNs85okMoM8j3YCFsM7EJ9
+l4We6J4euWK9WM7YboiSgKltJGXUgTU0l2HYN17ihF3sY3PaBiLdrNARM9blkzAhdhx0Q3NNFn3N
+7g0PniTkvW07aZoemdN/yric2grhC5P3rkuaw0j/AwTDC68ReJbOmdn7Gmv+4RSIXN9DIM/JV0Dd
+Xn06zLhnl9mim5hLtB1+f0E4oSz1MOOh1qoajm/lpr4o7zyHjb3v8mKrTMXvYO4PiQZ5HKWgvbB3
+iMCvdn859bv5X5ckz2SVtpnTjYTemICmEPRk7hRb/DZJkMptlhG2uFIq1ZUSDwVMGrrnRkEwlyLT
+f7wU5C2KoNGVgGhF9W6w/RBzYyTFVrsCTxpR9M9Jy875JnCmOBYUQLoDno+4qR00a70R2AdG7c3q
+gCZQBLzKqEp+gu0YUPGZzda1i8RhSF6c0w2A7ToynDf9gTbKSsyV1iblTm1UhjG/lXtU/9rzOMth
+7ZCrvd1EZGbmn2SP+CsQzoGMh9T0j+FygWx1u/yYO0kRXCjcyzOVq+p+XraDwxiI+GNcqNkrVKUW
+kIJO6ajXZg0cNekZyhiR3vLdY5EOBVWahvTnWFrEPpNt6tavVHyQ+AJP5t3VLq16AkBGgICYAdnG
+zKUgim96I0xNd37EKTmIlBccpNc0uVLgGEzuQiONBBcZPUwD6y4EvJnLmEaOdgRYjcaO8aeuIX/U
+VEC4zQEXI99ghQ7TWuNNOwyR+kyKQQsER5GRct9fzv6qMk0Xei914IdbL7DAy2pSfyaYNNlk339H
+/ji5lQPG1y8qQAw6sDtQPt0LcHg3bMX5Q/r1/LmlpML7rOUz1QwVH7QdHrHWjGvC1kjrmGtZjB7j
+XwQMItY3n/J1/vBfeuSk3sgWeHBYxgmnIjhqMVEoTSTUyelfrOte9N+5fomUWqnujl6rmqHl62oO
+695wUiKq6BVpXQtJEhqauQYAQ+DoGn3Klbmd5iHaqG5PU68wtEQPtSvXG6RPtteUi/H2jpnaG/Z+
+6HVQejCGJrZ4h1C/afq7WnCg5ZM8dy9zE02+CtqTq1hEiXF5mF6rhpKgxJZLlWk8wq0zP47ahnI+
+0VyAljgH5CW5BOwGrZdV8LHPbk+gVhqqBYIw/05HACbO4K32rEEUuvK+DSYQ0wxY8ufa1QttqQnv
+YRQ3XU+M4reL3pDJwPg+3LGP7jcIEqUY+trGeWbhASAETsLUURYuIkAydPKkEvb1rFPJGfiuMAVi
+PhSSTvDSrV8FZR9NNTr7zeHAbbJWArKi0hcv67noStYzBQT++SuiD5stp9Ym4DCE6/sAIR7Sa/1Y
+rhViLtpHp06WzkXi5lSVBCpJjaWKznmQp580gyAjjOx3mRqkEwx440yJq0LfqTdF8jiV2IZhjiT3
+MjdanLQOlldjGL64SpIKCQ0FzQcnB+sNbTtkYSRR9x4ImNYFGQpQtXimbAJAlaS5R4bOLbOygO/C
+mUDjpo1NkTIyAe/YzALpbCyJqaEOPm5Yp+1C6EQfb+DUxv2MyUWNuKw0xvFWhy4TuCCsrzIfQLYi
+2UxpILq8zr8ZhPUGv6KnN4j+jTo92A3DvtBbTLdRLf1n6hfAhWAOBmGu7c8N0kmfNcDJuWtvsG08
+1+xqLNni149FrNDzMjLwMg2YwaHJuwdKZsMcRtEfmGi2uAsTthsq6MxMHZPBFqNaNwrcaN7+PEK1
+c21PW/X6+kATvCRpKJxlChyZE5yEanvsIwpFB9IRmyEZIyYnCIcFl08Mbaw9jGdlxg32VdjIdQTY
+LVQ/8NOQGuz8RJepxoBQQ4dveiWJTPeEY879EC+3U8NgA84O3YZKfNxE4uSbjeGKu4tvVp5DoByW
+H7ZZWKAScltteuKFpP4ME6gGwvgF122HNzfrwztjcooIGfsxRvRSNerbAVjyZbBy3jC/3m3pOmqy
+kJfzhbVqEesBRCJKaCXVHZRSoziSqlwtMgbU+tPYGMERJT727cIFFKhqLILybZbc6LKI/SV852TD
+JXQ420HZX76GTSEWURDsu8glvYuGVosvBdg/63lVf8z15vJiaFbJEQDR7dHAquTAsynB2PVUErhJ
+sNz4kuQRbRoD6vS07fM2avNTLouZUX3bpwugyumgl2H0lvxLWXnXelFHnIc7NzdEqx6oS1YZBgq3
+7U21OG5t9hA02eZZT+LrcAWH1NUV2fFWps60WHKdCKcIN7w/vy/D8dDr1jdOppdubN35oR5ZOwob
+HYjk/KepGNTDeH8el2SX9yhjj5a0aTtMTdy/DvpAN7u9Xaq0bRH1lZZyE0n4F1MysND8sWwQPTH8
+uJoD4msqelGrx81lThyhwwk/8+2AWGG0sU9l0sK4xMmeMCPtdGdg9C4g5m08mHoa/etbOj+7spqf
+MG4Gq1hLOygsHwFRRQe3eRi4BSoE7HvgdyP84qVnLnc4g0RDLhFdDgyBLGTYRqpCX8iZA4Nf4uRJ
+pteB+CANzKjx9HqxBO/jGtOwFBg0eSXBU4d4CI6MoAS4NxUjlqhIGEKJBwJ78jPsCq2JMD0wITAJ
+BgUrDgMCGgUABBTxMWXHZ4F5ADtYXqKlpD5cMihu7wQUsiXIcUR/3TChw09nR5rrIaFsN+MCAgQA
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/security/KeyStore/PKCS12/openssl.p12.pem	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,22 @@
+-----BEGIN CERTIFICATE-----
+MIIDjjCCAnagAwIBAgIBAzANBgkqhkiG9w0BAQsFADBMMQswCQYDVQQGEwJJTjEL
+MAkGA1UECAwCS0ExDzANBgNVBAoMBk9yYWNsZTENMAsGA1UECwwESmF2YTEQMA4G
+A1UEAwwHQ2xpZW50MTAeFw0xNTA1MjYyMjE3MThaFw0yNTA1MjMyMjE3MThaMEwx
+CzAJBgNVBAYTAklOMQswCQYDVQQIDAJLQTEPMA0GA1UECgwGT3JhY2xlMQ0wCwYD
+VQQLDARKYXZhMRAwDgYDVQQDDAdDbGllbnQyMIIBIjANBgkqhkiG9w0BAQEFAAOC
+AQ8AMIIBCgKCAQEA2HADVMaKPd7xAYK0BTsCcQzglk8H2qp0Sg5nDYgb7KqB/1cb
+RyMB3g3FG4Isv6L0Lp2GLAeHVn35YljHNrcBUU5fG/+DNJPNiM+srevblMeksOcA
+frPnxmog+GMgiO97O2/3Xtgl0ailsOHidPH9hBXr+WikNu7ITPXkJiYi0d1n8p2N
+e/p4W4cBitxIUlZm2OTSW4d3EDW86saf657kSpTlb2zBT/r9fjWluHlTg+jGnGIz
+UdpYP7sSnye8oym5PxT2IMPU6vRgF9Gzwg+6bPaZnrYNURifGJIuQH+/wDaqA+Ix
+g2Q2Ij8SiDhkNrCoeLf77Aot9d5ZPtledJPSRQIDAQABo3sweTAJBgNVHRMEAjAA
+MCwGCWCGSAGG+EIBDQQfFh1PcGVuU1NMIEdlbmVyYXRlZCBDZXJ0aWZpY2F0ZTAd
+BgNVHQ4EFgQUhxNmvHpNjpjnl/vMVkEnyF5Msk0wHwYDVR0jBBgwFoAUHyFP2xAx
+0GeDCQPTzfxG7M8di7QwDQYJKoZIhvcNAQELBQADggEBAD4rXzKq8PdSK7rzuwfu
+q+RzeYZnNM7OsoBGhMfHQKnnI3LH5bgyttuCoV665X2mgy6+LZcrXqom/ZrLXQ6x
+JVtGxNHr7rqbnC/9tB2/s9HHN3YiRs966shWHGkhCubsUGre7Z25Pq55K6Pyl+nU
+hb+K8aQ54z4oDt+raAdbuILq91fUjw5j1qex3d62fHvf4IO3spcKY4HhnwBPifg2
+YZCiZRZOoVysi2FTdsvW2NfQCYgtUftbkfNrKglkRuIa9rQEduhDy1cwn4fc9S1f
+6WTvuJNoIp3o1nQppFjfO7fzfIDCrlaEkkXU7O54KQ5HTKu62tZp9xKW71oolOnZ
+bZQ=
+-----END CERTIFICATE-----
--- a/jdk/test/java/text/Bidi/BidiConformance.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/text/Bidi/BidiConformance.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2009, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2009, 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
@@ -23,7 +23,7 @@
 
 /*
  * @test
- * @bug 6850113
+ * @bug 6850113 8032446
  * @summary confirm the behavior of new Bidi implementation. (Backward compatibility)
  */
 
@@ -40,6 +40,8 @@
     private static boolean verbose = false;
     private static boolean abort = false;
 
+    private static final byte MAX_EXPLICIT_LEVEL = 125;
+
     public static void main(String[] args) {
         for (int i = 0; i < args.length; i++) {
             String arg = args[i];
@@ -368,15 +370,15 @@
         AttributedString astr = new AttributedString(paragraph);
         astr.addAttribute(TextAttribute.RUN_DIRECTION,
                           TextAttribute.RUN_DIRECTION_RTL);
-        astr.addAttribute(TextAttribute.BIDI_EMBEDDING, new Integer(-61),
+        astr.addAttribute(TextAttribute.BIDI_EMBEDDING, new Integer(-MAX_EXPLICIT_LEVEL),
                           start, limit);
         try {
             bidi = new Bidi(astr.getIterator());
             for (int i = start; i < limit; i++) {
-                if (bidi.getLevelAt(i) != 61) {
+                if (bidi.getLevelAt(i) != MAX_EXPLICIT_LEVEL) {
                     errorHandling("Bidi(AttributedCharacterIterator).getLevelAt(" +
                         i + ") should not be " + bidi.getLevelAt(i) +
-                        " but 60 when BIDI_EMBEDDING is -61.");
+                        " but MAX_EXPLICIT_LEVEL-1 when BIDI_EMBEDDING is -MAX_EXPLICIT_LEVEL.");
                 }
             }
         }
@@ -387,14 +389,14 @@
         astr = new AttributedString(paragraph);
         astr.addAttribute(TextAttribute.RUN_DIRECTION,
                           TextAttribute.RUN_DIRECTION_RTL);
-        astr.addAttribute(TextAttribute.BIDI_EMBEDDING, new Integer(-62),
+        astr.addAttribute(TextAttribute.BIDI_EMBEDDING, new Integer(-(MAX_EXPLICIT_LEVEL+1)),
                           start, limit);
         try {
             bidi = new Bidi(astr.getIterator());
             for (int i = start; i < limit; i++) {
                 if (bidi.getLevelAt(i) != 1) {
                     errorHandling("Bidi(AttributedCharacterIterator).getLevelAt() " +
-                        "should be 1 when BIDI_EMBEDDING is -62.");
+                        "should be 1 when BIDI_EMBEDDING is -(MAX_EXPLICIT_LEVEL+1).");
                 }
             }
         }
@@ -405,14 +407,14 @@
         astr = new AttributedString(paragraph);
         astr.addAttribute(TextAttribute.RUN_DIRECTION,
                           TextAttribute.RUN_DIRECTION_RTL);
-        astr.addAttribute(TextAttribute.BIDI_EMBEDDING, new Integer(60),
+        astr.addAttribute(TextAttribute.BIDI_EMBEDDING, new Integer(MAX_EXPLICIT_LEVEL-1),
                           start, limit);
         try {
             bidi = new Bidi(astr.getIterator());
             for (int i = start; i < limit; i++) {
-                if (bidi.getLevelAt(i) != 61) {
+                if (bidi.getLevelAt(i) != MAX_EXPLICIT_LEVEL) {
                     errorHandling("Bidi(AttributedCharacterIterator).getLevelAt() " +
-                        "should be 61 when BIDI_EMBEDDING is 60.");
+                        "should be MAX_EXPLICIT_LEVEL when BIDI_EMBEDDING is MAX_EXPLICIT_LEVEL-1.");
                 }
             }
         }
@@ -423,15 +425,15 @@
         astr = new AttributedString(paragraph);
         astr.addAttribute(TextAttribute.RUN_DIRECTION,
                           TextAttribute.RUN_DIRECTION_RTL);
-        astr.addAttribute(TextAttribute.BIDI_EMBEDDING, new Integer(61),
+        astr.addAttribute(TextAttribute.BIDI_EMBEDDING, new Integer(MAX_EXPLICIT_LEVEL),
                           start, limit);
         try {
             bidi = new Bidi(astr.getIterator());
             for (int i = start; i < limit; i++) {
-                if (bidi.getLevelAt(i) != 61) {
+                if (bidi.getLevelAt(i) != MAX_EXPLICIT_LEVEL) {
                     errorHandling("Bidi(AttributedCharacterIterator).getLevelAt(" +
                         i + ") should not be " + bidi.getLevelAt(i) +
-                        " but 61 when BIDI_EMBEDDING is 61.");
+                        " but MAX_EXPLICIT_LEVEL when BIDI_EMBEDDING is MAX_EXPLICIT_LEVEL.");
                 }
             }
         }
@@ -442,15 +444,15 @@
         astr = new AttributedString(paragraph);
         astr.addAttribute(TextAttribute.RUN_DIRECTION,
                           TextAttribute.RUN_DIRECTION_RTL);
-        astr.addAttribute(TextAttribute.BIDI_EMBEDDING, new Integer(62),
+        astr.addAttribute(TextAttribute.BIDI_EMBEDDING, new Integer(MAX_EXPLICIT_LEVEL+1),
                           start, limit);
         try {
             bidi = new Bidi(astr.getIterator());
             for (int i = start; i < limit; i++) {
                 if (bidi.getLevelAt(i) != 1) {
-                    errorHandling("Bidi(AttributedCharacterIterator).getLevelAt()" +
-                        " should not be " + bidi.getLevelAt(i) +
-                        " but 1 when BIDI_EMBEDDING is 62.");
+                    errorHandling("Bidi(AttributedCharacterIterator).getLevelAt(" +
+                         i + ") should not be " + bidi.getLevelAt(i) +
+                        " but 1 when BIDI_EMBEDDING is MAX_EXPLICIT_LEVEL+1.");
                 }
             }
         }
@@ -536,8 +538,8 @@
         }
 
         byte[] actualLevels = new byte[text.length];
-        byte[] validEmbeddings1 = {0, -61, -60, -2, -1};
-        byte[] expectedLevels1  = {0,  61,  60,  2,  1};
+        byte[] validEmbeddings1 = {0, -MAX_EXPLICIT_LEVEL, -(MAX_EXPLICIT_LEVEL-1), -2, -1};
+        byte[] expectedLevels1  = {0,  MAX_EXPLICIT_LEVEL,  MAX_EXPLICIT_LEVEL-1,  2,  1};
         try {
             bidi = new Bidi(text, 0, validEmbeddings1, 0, 5,
                             Bidi.DIRECTION_LEFT_TO_RIGHT);
@@ -553,11 +555,11 @@
         }
         catch (Exception e) {
             errorHandling("Bidi(char[], ...) should not throw an exception " +
-                "when embeddings is valid(-61).");
+                "when embeddings is valid(-MAX_EXPLICIT_LEVEL).");
         }
 
-        byte[] validEmbeddings2 = {0,  61,  60,  2,  1};
-        byte[] expectedLevels2  = {0,  62,  60,  2,  2};
+        byte[] validEmbeddings2 = {0,  MAX_EXPLICIT_LEVEL,  MAX_EXPLICIT_LEVEL-1,  2,  1};
+        byte[] expectedLevels2  = {0,  MAX_EXPLICIT_LEVEL+1,  MAX_EXPLICIT_LEVEL-1,  2,  2};
         try {
             bidi = new Bidi(text, 0, validEmbeddings2, 0, 5,
                             Bidi.DIRECTION_LEFT_TO_RIGHT);
@@ -573,35 +575,35 @@
         }
         catch (Exception e) {
             errorHandling("Bidi(char[], ...) should not throw an exception " +
-                "when embeddings is valid(61).");
+                "when embeddings is valid(MAX_EXPLICIT_LEVEL).");
         }
 
-        byte[] invalidEmbeddings1 = {0, -62, 0, 0, 0};
+        byte[] invalidEmbeddings1 = {0, -(MAX_EXPLICIT_LEVEL+1), 0, 0, 0};
         try {
             bidi = new Bidi(text, 0, invalidEmbeddings1, 0, 5,
                             Bidi.DIRECTION_LEFT_TO_RIGHT);
             if (bidi.getLevelAt(1) != 0) {
                 errorHandling("Bidi(char[], ...).getLevelAt(1) should be 0 " +
-                    "when embeddings[1] is -62.");
+                    "when embeddings[1] is -(MAX_EXPLICIT_LEVEL+1).");
             }
         }
         catch (Exception e) {
             errorHandling("Bidi(char[], ...) should not throw an exception " +
-                "even when embeddings includes -62.");
+                "even when embeddings includes -(MAX_EXPLICIT_LEVEL+1).");
         }
 
-        byte[] invalidEmbeddings2 = {0, 62, 0, 0, 0};
+        byte[] invalidEmbeddings2 = {0, MAX_EXPLICIT_LEVEL+1, 0, 0, 0};
         try {
             bidi = new Bidi(text, 0, invalidEmbeddings2, 0, 5,
                             Bidi.DIRECTION_LEFT_TO_RIGHT);
             if (bidi.getLevelAt(1) != 0) {
                 errorHandling("Bidi(char[], ...).getLevelAt(1) should be 0 " +
-                    "when embeddings[1] is 62.");
+                    "when embeddings[1] is MAX_EXPLICIT_LEVEL+1.");
             }
         }
         catch (Exception e) {
             errorHandling("Bidi(char[], ...) should not throw an exception " +
-                "even when embeddings includes 62.");
+                "even when embeddings includes MAX_EXPLICIT_LEVEL+1.");
         }
 
         try {
@@ -1595,6 +1597,10 @@
     private static final char PDF = '\u202C';
     private static final char LRO = '\u202D';
     private static final char RLO = '\u202E';
+    private static final char LRI = '\u2066';
+    private static final char RLI = '\u2067';
+    private static final char FSI = '\u2068';
+    private static final char PDI = '\u2069';
 
     /*
      *  0x05D0-0x05EA:   [R]   Hewbrew letters (Strong)
@@ -2002,8 +2008,8 @@
 
         /* For Text #18 */
         {" ABC (" + ArabicABC + " " + Arabic123 + ") 123.",
-             "0000001111222112220", "0000001111222112220",
-             "0000001111222112220", "1222111111222112221"},
+             "0000001111222002220", "0000001111222002220",
+             "0000001111222002220", "1222111111222112221"},
 
         /* For Text #19 */
         {" " + HebrewABC + " (ABC 123) " + NKo123 + ".",
@@ -2028,6 +2034,90 @@
          PDF,
              "22222221111111111111110", "22222221111111111111110",
              "22222221111111111111110", "44444443333333333333331"},
+
+        /* For Text #23 */
+        {" ABC (" + Arabic123 + " " + ArabicABC + ") 123.",
+             "0000002221111002220", "0000002221111002220",
+             "0000002221111002220", "1222112221111112221"},
+
+        /* For Text #24 */
+        {" 123 (" + ArabicABC + " " + Arabic123 + ") ABC.",
+             "1222111111222112221", "1222111111222112221",
+             "0000001111222000000", "1222111111222112221"},
+
+        /* For Text #25 */
+        {" 123 (" + Arabic123 + " " + ArabicABC + ") ABC.",
+             "1222112221111112221", "1222112221111112221",
+             "0000002221111000000", "1222112221111112221"},
+
+        /* For Text #26 */
+        {" " + ArabicABC + " (ABC 123) "  + Arabic123 + ".",
+             "1111112222222112221", "1111112222222112221",
+             "0111000000000002220", "1111112222222112221"},
+
+        /* For Text #27 */
+        {" " + ArabicABC + " (123 ABC) "  + Arabic123 + ".",
+             "1111112221222112221", "1111112221222112221",
+             "0111002220000002220", "1111112221222112221"},
+
+        /* For Text #28 */
+        {" " + Arabic123 + " (ABC 123) "  + ArabicABC + ".",
+             "0222000000000001110", "0222000000000001110",
+             "0222000000000001110", "1222112222222111111"},
+
+        /* For Text #29 */
+        {" " + Arabic123 + " (123 ABC) "  + ArabicABC + ".",
+             "0222000000000001110", "0222000000000001110",
+             "0222000000000001110", "1222112221222111111"},
+
+        /* For Text #30 */
+        {RLI + "ABC " + ArabicABC + " " + ArabicABC + "." + PDI,
+             "02221111111110", "14443333333331",
+             "02221111111110", "14443333333331"},
+
+        /* For Text #31 */
+        {"ABC abc \"" + RLI + "IJK " + ArabicABC + " " + ArabicABC + PDI +
+         ".\" \"" + RLI + ArabicABC + " " + ArabicABC + PDI + ",\" xyz XYZ.",
+             "0000000000222111111110000001111111000000000000",
+             "0000000000222111111110000001111111000000000000",
+             "0000000000222111111110000001111111000000000000",
+             "2222222222444333333332222223333333222222222221"},
+
+        /* For Text #32 */
+        {ArabicABC + " " + ArabicABC + " '" + LRI + "abc def \"" + RLI +
+         "xyz " + ArabicABC + " " + ArabicABC + PDI + "\"" + PDI + "'?",
+             "111111111122222222224443333333322111",
+             "111111111122222222224443333333322111",
+             "111111100022222222224443333333322000",
+             "111111111122222222224443333333322111"},
+
+        /* For Text #33 */
+        {FSI + Arabic123 + " ABC " + ArabicABC + " " + ArabicABC + "." + PDI,
+             "044422222333333320", "144422222333333321",
+             "044422222333333320", "144422222333333321"},
+
+        /* For Text #34 */
+        {FSI + "123 ABC " + ArabicABC + " " + ArabicABC + "." + PDI,
+             "022222222333333320", "122222222333333321",
+             "022222222333333320", "122222222333333321"},
+
+        /* For Text #35 */
+        {FSI + "123 " + ArabicABC + " ABC " + ArabicABC + "." + PDI,
+             "022211111222111110", "144433333444333331",
+             "022211111222111110", "144433333444333331"},
+
+        /* For Text #36 */
+        {FSI + Arabic123 + " " + ArabicABC + " ABC " + ArabicABC + "." + PDI,
+             "022211111222111110", "144433333444333331",
+             "022211111222111110", "144433333444333331"},
+
+        /* For Text #37 */
+        {FSI + Arabic123 + " 123." + PDI,
+             "0444222220", "1444222221", "0444222220", "1444222221"},
+
+        /* For Text #38 */
+        {FSI + "123 " + Arabic123 + "." + PDI,
+             "0222244420", "1222244421", "0222244420", "1222244421"},
     };
 
     /* Golden data for baseIsLeftToRight() results */
@@ -2060,10 +2150,32 @@
         {true,  true,  true,  false},
         {false, false, true,  false},
 
-        /* For Text #20 - $22  */
+        /* For Text #20 - $24  */
+        {true,  true,  true,  false},
         {true,  true,  true,  false},
         {true,  true,  true,  false},
         {true,  true,  true,  false},
+        {false, false, true,  false},
+
+        /* For Text #25 - $29  */
+        {false, false, true,  false},
+        {false, false, true,  false},
+        {false, false, true,  false},
+        {true,  true,  true,  false},
+        {true,  true,  true,  false},
+
+        /* For Text #30 - $34  */
+        {true,  false, true,  false},
+        {true,  true,  true,  false},
+        {false, false, true,  false},
+        {true,  false, true,  false},
+        {true , false, true,  false},
+
+        /* For Text #35 - $38  */
+        {true,  false, true,  false},
+        {true,  false, true,  false},
+        {true,  false, true,  false},
+        {true,  false, true,  false},
     };
 
     /* Golden data for isLeftToRight() & isRightToLeft() results */
@@ -2097,7 +2209,29 @@
         {{false, false, false, false}, {false, false, false, false}},
         {{false, false, false, false}, {false, false, false, false}},
 
-        /* For Text #20 - $22  */
+        /* For Text #20 - $24  */
+        {{false, false, false, false}, {false, false, false, false}},
+        {{false, false, false, false}, {false, false, false, false}},
+        {{false, false, false, false}, {false, false, false, false}},
+        {{false, false, false, false}, {false, false, false, false}},
+        {{false, false, false, false}, {false, false, false, false}},
+
+        /* For Text #25 - $29  */
+        {{false, false, false, false}, {false, false, false, false}},
+        {{false, false, false, false}, {false, false, false, false}},
+        {{false, false, false, false}, {false, false, false, false}},
+        {{false, false, false, false}, {false, false, false, false}},
+        {{false, false, false, false}, {false, false, false, false}},
+
+        /* For Text #30 - $34  */
+        {{false, false, false, false}, {false, false, false, false}},
+        {{false, false, false, false}, {false, false, false, false}},
+        {{false, false, false, false}, {false, false, false, false}},
+        {{false, false, false, false}, {false, false, false, false}},
+        {{false, false, false, false}, {false, false, false, false}},
+
+        /* For Text #35 - $37  */
+        {{false, false, false, false}, {false, false, false, false}},
         {{false, false, false, false}, {false, false, false, false}},
         {{false, false, false, false}, {false, false, false, false}},
         {{false, false, false, false}, {false, false, false, false}},
@@ -2113,8 +2247,13 @@
         true,  true,  true,  true,  true,
         true,  true,  true,  true,  true,
 
-        /* For Text #20 - $22  */
-        true,  true,  true,
+        /* For Text #20 - $29  */
+        true,  true,  true,  true,  true,
+        true,  true,  true,  true,  true,
+
+        /* For Text #30 - $37  */
+        true,  true,  true,  true,  true,
+        true,  true,  true,  true,
     };
 
     /* --------------------------------------------------------------------- */
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/text/BreakIterator/Bug8032446.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,56 @@
+/*
+ * 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.
+ */
+/*
+ * @test
+ * @bug 8032446
+ * @summary Confirm that BreakIterator works as expected with new characters in Unicode 7.
+ */
+
+import java.text.*;
+import java.util.*;
+
+public class Bug8032446 {
+
+    public static void main(String[] args) {
+        boolean err = false;
+
+        StringBuilder sb = new StringBuilder();
+        for (int i = 0x10860; i <= 0x10876; i++) { // Palmyrene Letters
+            sb.append(Character.toChars(i));
+        }
+        sb.append(" ");
+        for (int i = 0x10879; i <= 0x1087D; i++) { // Palmyrene Numbers
+            sb.append(Character.toChars(i));
+        }
+        String s = sb.toString();
+
+        BreakIterator bi = BreakIterator.getWordInstance(Locale.ROOT);
+        bi.setText(s);
+        bi.first();
+
+        if (bi.next() != s.indexOf(' ')) {
+            throw new RuntimeException("Unexpected word breaking.");
+        }
+    }
+
+}
--- a/jdk/test/java/util/regex/RegExTest.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/util/regex/RegExTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1999, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1999, 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
@@ -32,11 +32,11 @@
  * 6358731 6178785 6284152 6231989 6497148 6486934 6233084 6504326 6635133
  * 6350801 6676425 6878475 6919132 6931676 6948903 6990617 7014645 7039066
  * 7067045 7014640 7189363 8007395 8013252 8013254 8012646 8023647 6559590
- * 8027645 8035076 8039124 8035975 8074678
+ * 8027645 8035076 8039124 8035975 8074678 6854417
  * @library /lib/testlibrary
  * @build jdk.testlibrary.*
  * @run main RegExTest
- * @key intermittent randomness
+ * @key randomness
  */
 
 import java.util.function.Function;
@@ -3554,15 +3554,26 @@
             // Create a short pattern to search for
             int patternLength = generator.nextInt(7) + 4;
             StringBuffer patternBuffer = new StringBuffer(patternLength);
-            for (int x=0; x<patternLength; x++) {
-                int ch = baseCharacter + generator.nextInt(26);
-                if (Character.isSupplementaryCodePoint(ch)) {
-                    patternBuffer.append(Character.toChars(ch));
-                } else {
-                    patternBuffer.append((char)ch);
+            String pattern;
+            retry: for (;;) {
+                for (int x=0; x<patternLength; x++) {
+                    int ch = baseCharacter + generator.nextInt(26);
+                    if (Character.isSupplementaryCodePoint(ch)) {
+                        patternBuffer.append(Character.toChars(ch));
+                    } else {
+                        patternBuffer.append((char)ch);
+                    }
                 }
+                pattern = patternBuffer.toString();
+
+                // Avoid patterns that start and end with the same substring
+                // See JDK-6854417
+                for (int x=1; x <patternLength; x++) {
+                    if (pattern.startsWith(pattern.substring(x)))
+                        continue retry;
+                }
+                break;
             }
-            String pattern =  patternBuffer.toString();
             Pattern p = Pattern.compile(pattern);
 
             // Create a buffer with random ASCII chars that does
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/util/stream/bootlib/java/util/stream/DefaultMethodStreams.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,984 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package java.util.stream;
+
+import java.lang.reflect.Method;
+import java.lang.reflect.Modifier;
+import java.util.Comparator;
+import java.util.DoubleSummaryStatistics;
+import java.util.IntSummaryStatistics;
+import java.util.Iterator;
+import java.util.LongSummaryStatistics;
+import java.util.Optional;
+import java.util.OptionalDouble;
+import java.util.OptionalInt;
+import java.util.OptionalLong;
+import java.util.PrimitiveIterator;
+import java.util.Set;
+import java.util.Spliterator;
+import java.util.function.BiConsumer;
+import java.util.function.BiFunction;
+import java.util.function.BinaryOperator;
+import java.util.function.Consumer;
+import java.util.function.DoubleBinaryOperator;
+import java.util.function.DoubleConsumer;
+import java.util.function.DoubleFunction;
+import java.util.function.DoublePredicate;
+import java.util.function.DoubleToIntFunction;
+import java.util.function.DoubleToLongFunction;
+import java.util.function.DoubleUnaryOperator;
+import java.util.function.Function;
+import java.util.function.IntBinaryOperator;
+import java.util.function.IntConsumer;
+import java.util.function.IntFunction;
+import java.util.function.IntPredicate;
+import java.util.function.IntToDoubleFunction;
+import java.util.function.IntToLongFunction;
+import java.util.function.IntUnaryOperator;
+import java.util.function.LongBinaryOperator;
+import java.util.function.LongConsumer;
+import java.util.function.LongFunction;
+import java.util.function.LongPredicate;
+import java.util.function.LongToDoubleFunction;
+import java.util.function.LongToIntFunction;
+import java.util.function.LongUnaryOperator;
+import java.util.function.ObjDoubleConsumer;
+import java.util.function.ObjIntConsumer;
+import java.util.function.ObjLongConsumer;
+import java.util.function.Predicate;
+import java.util.function.Supplier;
+import java.util.function.ToDoubleFunction;
+
+import java.util.function.ToIntFunction;
+import java.util.function.ToLongFunction;
+
+import static java.util.stream.Collectors.*;
+
+public final class DefaultMethodStreams {
+
+    static {
+        // Verify that default methods are not overridden
+        verify(DefaultMethodRefStream.class);
+        verify(DefaultMethodIntStream.class);
+        verify(DefaultMethodLongStream.class);
+        verify(DefaultMethodDoubleStream.class);
+    }
+
+    static void verify(Class<?> del) {
+        // Find the stream interface
+        Class<?> s = Stream.of(del.getInterfaces())
+                .filter(c -> BaseStream.class.isAssignableFrom(c))
+                .findFirst().get();
+
+        // Get all default methods on the stream class
+        Set<String> dms = Stream.of(s.getMethods())
+                .filter(m -> !Modifier.isStatic(m.getModifiers()))
+                .filter(m -> !m.isBridge())
+                .filter(Method::isDefault)
+                .map(Method::getName)
+                .collect(toSet());
+
+        // Get all methods on the delegating class
+        Set<String> ims = Stream.of(del.getMethods())
+                .filter(m -> !Modifier.isStatic(m.getModifiers()))
+                .filter(m -> m.getDeclaringClass() == del)
+                .map(Method::getName)
+                .collect(toSet());
+
+        if (ims.stream().anyMatch(dms::contains)) {
+            throw new AssertionError(String.format("%s overrides default methods of %s\n", del, s));
+        }
+    }
+
+    /**
+     * Creates a stream that for the next operation either delegates to
+     * a default method on {@link Stream}, if present for that operation,
+     * otherwise delegates to an underlying stream.
+     *
+     * @param s the underlying stream to be delegated to for non-default
+     * methods.
+     * @param <T> the type of the stream elements
+     * @return the delegating stream
+     */
+    public static <T> Stream<T> delegateTo(Stream<T> s) {
+        return new DefaultMethodRefStream<>(s);
+    }
+
+    /**
+     * Creates a stream that for the next operation either delegates to
+     * a default method on {@link IntStream}, if present for that operation,
+     * otherwise delegates to an underlying stream.
+     *
+     * @param s the underlying stream to be delegated to for non-default
+     * methods.
+     * @return the delegating stream
+     */
+    public static IntStream delegateTo(IntStream s) {
+        return new DefaultMethodIntStream(s);
+    }
+
+    /**
+     * Creates a stream that for the next operation either delegates to
+     * a default method on {@link LongStream}, if present for that operation,
+     * otherwise delegates to an underlying stream.
+     *
+     * @param s the underlying stream to be delegated to for non-default
+     * methods.
+     * @return the delegating stream
+     */
+    public static LongStream delegateTo(LongStream s) {
+        return new DefaultMethodLongStream(s);
+    }
+
+    /**
+     * Creates a stream that for the next operation either delegates to
+     * a default method on {@link DoubleStream}, if present for that operation,
+     * otherwise delegates to an underlying stream.
+     *
+     * @param s the underlying stream to be delegated to for non-default
+     * methods.
+     * @return the delegating stream
+     */
+    public static DoubleStream delegateTo(DoubleStream s) {
+        return new DefaultMethodDoubleStream(s);
+    }
+
+    /**
+     * A stream that delegates the next operation to a default method, if
+     * present, or to the same operation of an underlying stream.
+     *
+     * @param <T> the type of the stream elements
+     */
+    static final class DefaultMethodRefStream<T> implements Stream<T> {
+        final Stream<T> s;
+
+        DefaultMethodRefStream(Stream<T> s) {
+            this.s = s;
+        }
+
+
+        // Delegating non-default methods
+
+        @Override
+        public Stream<T> filter(Predicate<? super T> predicate) {
+            return s.filter(predicate);
+        }
+
+        @Override
+        public <R> Stream<R> map(Function<? super T, ? extends R> mapper) {
+            return s.map(mapper);
+        }
+
+        @Override
+        public IntStream mapToInt(ToIntFunction<? super T> mapper) {
+            return s.mapToInt(mapper);
+        }
+
+        @Override
+        public LongStream mapToLong(ToLongFunction<? super T> mapper) {
+            return s.mapToLong(mapper);
+        }
+
+        @Override
+        public DoubleStream mapToDouble(ToDoubleFunction<? super T> mapper) {
+            return s.mapToDouble(mapper);
+        }
+
+        @Override
+        public <R> Stream<R> flatMap(Function<? super T, ? extends Stream<? extends R>> mapper) {
+            return s.flatMap(mapper);
+        }
+
+        @Override
+        public IntStream flatMapToInt(Function<? super T, ? extends IntStream> mapper) {
+            return s.flatMapToInt(mapper);
+        }
+
+        @Override
+        public LongStream flatMapToLong(Function<? super T, ? extends LongStream> mapper) {
+            return s.flatMapToLong(mapper);
+        }
+
+        @Override
+        public DoubleStream flatMapToDouble(Function<? super T, ? extends DoubleStream> mapper) {
+            return s.flatMapToDouble(mapper);
+        }
+
+        @Override
+        public Stream<T> distinct() {
+            return s.distinct();
+        }
+
+        @Override
+        public Stream<T> sorted() {
+            return s.sorted();
+        }
+
+        @Override
+        public Stream<T> sorted(Comparator<? super T> comparator) {
+            return s.sorted(comparator);
+        }
+
+        @Override
+        public Stream<T> peek(Consumer<? super T> action) {
+            return s.peek(action);
+        }
+
+        @Override
+        public Stream<T> limit(long maxSize) {
+            return s.limit(maxSize);
+        }
+
+        @Override
+        public Stream<T> skip(long n) {
+            return s.skip(n);
+        }
+
+        @Override
+        public void forEach(Consumer<? super T> action) {
+            s.forEach(action);
+        }
+
+        @Override
+        public void forEachOrdered(Consumer<? super T> action) {
+            s.forEachOrdered(action);
+        }
+
+        @Override
+        public Object[] toArray() {
+            return s.toArray();
+        }
+
+        @Override
+        public <A> A[] toArray(IntFunction<A[]> generator) {
+            return s.toArray(generator);
+        }
+
+        @Override
+        public T reduce(T identity, BinaryOperator<T> accumulator) {
+            return s.reduce(identity, accumulator);
+        }
+
+        @Override
+        public Optional<T> reduce(BinaryOperator<T> accumulator) {
+            return s.reduce(accumulator);
+        }
+
+        @Override
+        public <U> U reduce(U identity, BiFunction<U, ? super T, U> accumulator, BinaryOperator<U> combiner) {
+            return s.reduce(identity, accumulator, combiner);
+        }
+
+        @Override
+        public <R> R collect(Supplier<R> supplier, BiConsumer<R, ? super T> accumulator, BiConsumer<R, R> combiner) {
+            return s.collect(supplier, accumulator, combiner);
+        }
+
+        @Override
+        public <R, A> R collect(Collector<? super T, A, R> collector) {
+            return s.collect(collector);
+        }
+
+        @Override
+        public Optional<T> min(Comparator<? super T> comparator) {
+            return s.min(comparator);
+        }
+
+        @Override
+        public Optional<T> max(Comparator<? super T> comparator) {
+            return s.max(comparator);
+        }
+
+        @Override
+        public long count() {
+            return s.count();
+        }
+
+        @Override
+        public boolean anyMatch(Predicate<? super T> predicate) {
+            return s.anyMatch(predicate);
+        }
+
+        @Override
+        public boolean allMatch(Predicate<? super T> predicate) {
+            return s.allMatch(predicate);
+        }
+
+        @Override
+        public boolean noneMatch(Predicate<? super T> predicate) {
+            return s.noneMatch(predicate);
+        }
+
+        @Override
+        public Optional<T> findFirst() {
+            return s.findFirst();
+        }
+
+        @Override
+        public Optional<T> findAny() {
+            return s.findAny();
+        }
+
+        @Override
+        public Iterator<T> iterator() {
+            return s.iterator();
+        }
+
+        @Override
+        public Spliterator<T> spliterator() {
+            return s.spliterator();
+        }
+
+        @Override
+        public boolean isParallel() {
+            return s.isParallel();
+        }
+
+        @Override
+        public Stream<T> sequential() {
+            return s.sequential();
+        }
+
+        @Override
+        public Stream<T> parallel() {
+            return s.parallel();
+        }
+
+        @Override
+        public Stream<T> unordered() {
+            return s.unordered();
+        }
+
+        @Override
+        public Stream<T> onClose(Runnable closeHandler) {
+            return s.onClose(closeHandler);
+        }
+
+        @Override
+        public void close() {
+            s.close();
+        }
+    }
+
+    static final class DefaultMethodIntStream implements IntStream {
+        final IntStream s;
+
+        public DefaultMethodIntStream(IntStream s) {
+            this.s = s;
+        }
+
+
+        // Delegating non-default methods
+
+        @Override
+        public IntStream filter(IntPredicate predicate) {
+            return s.filter(predicate);
+        }
+
+        @Override
+        public IntStream map(IntUnaryOperator mapper) {
+            return s.map(mapper);
+        }
+
+        @Override
+        public <U> Stream<U> mapToObj(IntFunction<? extends U> mapper) {
+            return s.mapToObj(mapper);
+        }
+
+        @Override
+        public LongStream mapToLong(IntToLongFunction mapper) {
+            return s.mapToLong(mapper);
+        }
+
+        @Override
+        public DoubleStream mapToDouble(IntToDoubleFunction mapper) {
+            return s.mapToDouble(mapper);
+        }
+
+        @Override
+        public IntStream flatMap(IntFunction<? extends IntStream> mapper) {
+            return s.flatMap(mapper);
+        }
+
+        @Override
+        public IntStream distinct() {
+            return s.distinct();
+        }
+
+        @Override
+        public IntStream sorted() {
+            return s.sorted();
+        }
+
+        @Override
+        public IntStream peek(IntConsumer action) {
+            return s.peek(action);
+        }
+
+        @Override
+        public IntStream limit(long maxSize) {
+            return s.limit(maxSize);
+        }
+
+        @Override
+        public IntStream skip(long n) {
+            return s.skip(n);
+        }
+
+        @Override
+        public void forEach(IntConsumer action) {
+            s.forEach(action);
+        }
+
+        @Override
+        public void forEachOrdered(IntConsumer action) {
+            s.forEachOrdered(action);
+        }
+
+        @Override
+        public int[] toArray() {
+            return s.toArray();
+        }
+
+        @Override
+        public int reduce(int identity, IntBinaryOperator op) {
+            return s.reduce(identity, op);
+        }
+
+        @Override
+        public OptionalInt reduce(IntBinaryOperator op) {
+            return s.reduce(op);
+        }
+
+        @Override
+        public <R> R collect(Supplier<R> supplier, ObjIntConsumer<R> accumulator, BiConsumer<R, R> combiner) {
+            return s.collect(supplier, accumulator, combiner);
+        }
+
+        @Override
+        public int sum() {
+            return s.sum();
+        }
+
+        @Override
+        public OptionalInt min() {
+            return s.min();
+        }
+
+        @Override
+        public OptionalInt max() {
+            return s.max();
+        }
+
+        @Override
+        public long count() {
+            return s.count();
+        }
+
+        @Override
+        public OptionalDouble average() {
+            return s.average();
+        }
+
+        @Override
+        public IntSummaryStatistics summaryStatistics() {
+            return s.summaryStatistics();
+        }
+
+        @Override
+        public boolean anyMatch(IntPredicate predicate) {
+            return s.anyMatch(predicate);
+        }
+
+        @Override
+        public boolean allMatch(IntPredicate predicate) {
+            return s.allMatch(predicate);
+        }
+
+        @Override
+        public boolean noneMatch(IntPredicate predicate) {
+            return s.noneMatch(predicate);
+        }
+
+        @Override
+        public OptionalInt findFirst() {
+            return s.findFirst();
+        }
+
+        @Override
+        public OptionalInt findAny() {
+            return s.findAny();
+        }
+
+        @Override
+        public LongStream asLongStream() {
+            return s.asLongStream();
+        }
+
+        @Override
+        public DoubleStream asDoubleStream() {
+            return s.asDoubleStream();
+        }
+
+        @Override
+        public Stream<Integer> boxed() {
+            return s.boxed();
+        }
+
+        @Override
+        public IntStream sequential() {
+            return s.sequential();
+        }
+
+        @Override
+        public IntStream parallel() {
+            return s.parallel();
+        }
+
+        @Override
+        public PrimitiveIterator.OfInt iterator() {
+            return s.iterator();
+        }
+
+        @Override
+        public Spliterator.OfInt spliterator() {
+            return s.spliterator();
+        }
+
+        @Override
+        public boolean isParallel() {
+            return s.isParallel();
+        }
+
+        @Override
+        public IntStream unordered() {
+            return s.unordered();
+        }
+
+        @Override
+        public IntStream onClose(Runnable closeHandler) {
+            return s.onClose(closeHandler);
+        }
+
+        @Override
+        public void close() {
+            s.close();
+        }
+    }
+
+    static final class DefaultMethodLongStream implements LongStream {
+        final LongStream s;
+
+        public DefaultMethodLongStream(LongStream s) {
+            this.s = s;
+        }
+
+
+        // Delegating non-default methods
+
+        @Override
+        public void forEach(LongConsumer action) {
+            s.forEach(action);
+        }
+
+        @Override
+        public LongStream filter(LongPredicate predicate) {
+            return s.filter(predicate);
+        }
+
+        @Override
+        public LongStream map(LongUnaryOperator mapper) {
+            return s.map(mapper);
+        }
+
+        @Override
+        public <U> Stream<U> mapToObj(LongFunction<? extends U> mapper) {
+            return s.mapToObj(mapper);
+        }
+
+        @Override
+        public IntStream mapToInt(LongToIntFunction mapper) {
+            return s.mapToInt(mapper);
+        }
+
+        @Override
+        public DoubleStream mapToDouble(LongToDoubleFunction mapper) {
+            return s.mapToDouble(mapper);
+        }
+
+        @Override
+        public LongStream flatMap(LongFunction<? extends LongStream> mapper) {
+            return s.flatMap(mapper);
+        }
+
+        @Override
+        public LongStream distinct() {
+            return s.distinct();
+        }
+
+        @Override
+        public LongStream sorted() {
+            return s.sorted();
+        }
+
+        @Override
+        public LongStream peek(LongConsumer action) {
+            return s.peek(action);
+        }
+
+        @Override
+        public LongStream limit(long maxSize) {
+            return s.limit(maxSize);
+        }
+
+        @Override
+        public LongStream skip(long n) {
+            return s.skip(n);
+        }
+
+        @Override
+        public void forEachOrdered(LongConsumer action) {
+            s.forEachOrdered(action);
+        }
+
+        @Override
+        public long[] toArray() {
+            return s.toArray();
+        }
+
+        @Override
+        public long reduce(long identity, LongBinaryOperator op) {
+            return s.reduce(identity, op);
+        }
+
+        @Override
+        public OptionalLong reduce(LongBinaryOperator op) {
+            return s.reduce(op);
+        }
+
+        @Override
+        public <R> R collect(Supplier<R> supplier, ObjLongConsumer<R> accumulator, BiConsumer<R, R> combiner) {
+            return s.collect(supplier, accumulator, combiner);
+        }
+
+        @Override
+        public long sum() {
+            return s.sum();
+        }
+
+        @Override
+        public OptionalLong min() {
+            return s.min();
+        }
+
+        @Override
+        public OptionalLong max() {
+            return s.max();
+        }
+
+        @Override
+        public long count() {
+            return s.count();
+        }
+
+        @Override
+        public OptionalDouble average() {
+            return s.average();
+        }
+
+        @Override
+        public LongSummaryStatistics summaryStatistics() {
+            return s.summaryStatistics();
+        }
+
+        @Override
+        public boolean anyMatch(LongPredicate predicate) {
+            return s.anyMatch(predicate);
+        }
+
+        @Override
+        public boolean allMatch(LongPredicate predicate) {
+            return s.allMatch(predicate);
+        }
+
+        @Override
+        public boolean noneMatch(LongPredicate predicate) {
+            return s.noneMatch(predicate);
+        }
+
+        @Override
+        public OptionalLong findFirst() {
+            return s.findFirst();
+        }
+
+        @Override
+        public OptionalLong findAny() {
+            return s.findAny();
+        }
+
+        @Override
+        public DoubleStream asDoubleStream() {
+            return s.asDoubleStream();
+        }
+
+        @Override
+        public Stream<Long> boxed() {
+            return s.boxed();
+        }
+
+        @Override
+        public LongStream sequential() {
+            return s.sequential();
+        }
+
+        @Override
+        public LongStream parallel() {
+            return s.parallel();
+        }
+
+        @Override
+        public PrimitiveIterator.OfLong iterator() {
+            return s.iterator();
+        }
+
+        @Override
+        public Spliterator.OfLong spliterator() {
+            return s.spliterator();
+        }
+
+        @Override
+        public boolean isParallel() {
+            return s.isParallel();
+        }
+
+        @Override
+        public LongStream unordered() {
+            return s.unordered();
+        }
+
+        @Override
+        public LongStream onClose(Runnable closeHandler) {
+            return s.onClose(closeHandler);
+        }
+
+        @Override
+        public void close() {
+            s.close();
+        }
+    }
+
+    static final class DefaultMethodDoubleStream implements DoubleStream {
+        final DoubleStream s;
+
+        public DefaultMethodDoubleStream(DoubleStream s) {
+            this.s = s;
+        }
+
+        @Override
+        public DoubleStream filter(DoublePredicate predicate) {
+            return s.filter(predicate);
+        }
+
+        @Override
+        public DoubleStream map(DoubleUnaryOperator mapper) {
+            return s.map(mapper);
+        }
+
+        @Override
+        public <U> Stream<U> mapToObj(DoubleFunction<? extends U> mapper) {
+            return s.mapToObj(mapper);
+        }
+
+        @Override
+        public IntStream mapToInt(DoubleToIntFunction mapper) {
+            return s.mapToInt(mapper);
+        }
+
+        @Override
+        public LongStream mapToLong(DoubleToLongFunction mapper) {
+            return s.mapToLong(mapper);
+        }
+
+        @Override
+        public DoubleStream flatMap(DoubleFunction<? extends DoubleStream> mapper) {
+            return s.flatMap(mapper);
+        }
+
+        @Override
+        public DoubleStream distinct() {
+            return s.distinct();
+        }
+
+        @Override
+        public DoubleStream sorted() {
+            return s.sorted();
+        }
+
+        @Override
+        public DoubleStream peek(DoubleConsumer action) {
+            return s.peek(action);
+        }
+
+        @Override
+        public DoubleStream limit(long maxSize) {
+            return s.limit(maxSize);
+        }
+
+        @Override
+        public DoubleStream skip(long n) {
+            return s.skip(n);
+        }
+
+        @Override
+        public void forEach(DoubleConsumer action) {
+            s.forEach(action);
+        }
+
+        @Override
+        public void forEachOrdered(DoubleConsumer action) {
+            s.forEachOrdered(action);
+        }
+
+        @Override
+        public double[] toArray() {
+            return s.toArray();
+        }
+
+        @Override
+        public double reduce(double identity, DoubleBinaryOperator op) {
+            return s.reduce(identity, op);
+        }
+
+        @Override
+        public OptionalDouble reduce(DoubleBinaryOperator op) {
+            return s.reduce(op);
+        }
+
+        @Override
+        public <R> R collect(Supplier<R> supplier, ObjDoubleConsumer<R> accumulator, BiConsumer<R, R> combiner) {
+            return s.collect(supplier, accumulator, combiner);
+        }
+
+        @Override
+        public double sum() {
+            return s.sum();
+        }
+
+        @Override
+        public OptionalDouble min() {
+            return s.min();
+        }
+
+        @Override
+        public OptionalDouble max() {
+            return s.max();
+        }
+
+        @Override
+        public long count() {
+            return s.count();
+        }
+
+        @Override
+        public OptionalDouble average() {
+            return s.average();
+        }
+
+        @Override
+        public DoubleSummaryStatistics summaryStatistics() {
+            return s.summaryStatistics();
+        }
+
+        @Override
+        public boolean anyMatch(DoublePredicate predicate) {
+            return s.anyMatch(predicate);
+        }
+
+        @Override
+        public boolean allMatch(DoublePredicate predicate) {
+            return s.allMatch(predicate);
+        }
+
+        @Override
+        public boolean noneMatch(DoublePredicate predicate) {
+            return s.noneMatch(predicate);
+        }
+
+        @Override
+        public OptionalDouble findFirst() {
+            return s.findFirst();
+        }
+
+        @Override
+        public OptionalDouble findAny() {
+            return s.findAny();
+        }
+
+        @Override
+        public Stream<Double> boxed() {
+            return s.boxed();
+        }
+
+        @Override
+        public DoubleStream sequential() {
+            return s.sequential();
+        }
+
+        @Override
+        public DoubleStream parallel() {
+            return s.parallel();
+        }
+
+        @Override
+        public PrimitiveIterator.OfDouble iterator() {
+            return s.iterator();
+        }
+
+        @Override
+        public Spliterator.OfDouble spliterator() {
+            return s.spliterator();
+        }
+
+        @Override
+        public boolean isParallel() {
+            return s.isParallel();
+        }
+
+        @Override
+        public DoubleStream unordered() {
+            return s.unordered();
+        }
+
+        @Override
+        public DoubleStream onClose(Runnable closeHandler) {
+            return s.onClose(closeHandler);
+        }
+
+        @Override
+        public void close() {
+            s.close();
+        }
+    }
+}
\ No newline at end of file
--- a/jdk/test/java/util/stream/bootlib/java/util/stream/StreamTestDataProvider.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/java/util/stream/bootlib/java/util/stream/StreamTestDataProvider.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012, 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
@@ -119,7 +119,7 @@
 
         // Simple combination of numbers and null values, probably excessive but may catch
         // errors for initialization/termination/sequence
-        // @@@ This is separate from the other data for now until nulls are consitently supported by
+        // @@@ This is separate from the other data for now until nulls are consistently supported by
         // all operations
         {
             List<Object[]> list = new ArrayList<>();
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/util/stream/test/org/openjdk/tests/java/util/stream/WhileOpStatefulTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,304 @@
+/*
+ * 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 org.openjdk.tests.java.util.stream;
+
+import org.testng.annotations.Test;
+
+import java.util.HashMap;
+import java.util.LinkedList;
+import java.util.Map;
+import java.util.concurrent.TimeUnit;
+import java.util.concurrent.atomic.AtomicLong;
+import java.util.function.BooleanSupplier;
+import java.util.function.Consumer;
+import java.util.function.Function;
+import java.util.function.Supplier;
+import java.util.stream.DefaultMethodStreams;
+import java.util.stream.DoubleStream;
+import java.util.stream.IntStream;
+import java.util.stream.LongStream;
+import java.util.stream.OpTestCase;
+import java.util.stream.Stream;
+
+import static java.util.stream.Collectors.toCollection;
+
+/*
+ * @test
+ * @bug 8071597
+ */
+@Test
+public class WhileOpStatefulTest extends OpTestCase {
+    static final long COUNT_PERIOD = 100;
+
+    static final long EXECUTION_TIME_LIMIT = TimeUnit.SECONDS.toMillis(10);
+
+    static final long TAKE_WHILE_COUNT_LIMIT = 100_000;
+
+    static final int DROP_SOURCE_SIZE = 10_000;
+
+    static final long DROP_WHILE_COUNT_LIMIT = 5000;
+
+    @Test
+    public void testTimedTakeWithCount() {
+        testTakeWhileMulti(
+                s -> {
+                    BooleanSupplier isWithinTakePeriod =
+                            within(System.currentTimeMillis(), COUNT_PERIOD);
+                    s.takeWhile(e -> isWithinTakePeriod.getAsBoolean())
+                            .mapToLong(e -> 1).reduce(0, Long::sum);
+                },
+                s -> {
+                    BooleanSupplier isWithinTakePeriod =
+                            within(System.currentTimeMillis(), COUNT_PERIOD);
+                    s.takeWhile(e -> isWithinTakePeriod.getAsBoolean())
+                            .mapToLong(e -> 1).reduce(0, Long::sum);
+                },
+                s -> {
+                    BooleanSupplier isWithinTakePeriod =
+                            within(System.currentTimeMillis(), COUNT_PERIOD);
+                    s.takeWhile(e -> isWithinTakePeriod.getAsBoolean())
+                            .map(e -> 1).reduce(0, Long::sum);
+                },
+                s -> {
+                    BooleanSupplier isWithinTakePeriod =
+                            within(System.currentTimeMillis(), COUNT_PERIOD);
+                    s.takeWhile(e -> isWithinTakePeriod.getAsBoolean())
+                            .mapToLong(e -> 1).reduce(0, Long::sum);
+                });
+    }
+
+    @Test(groups = { "serialization-hostile" })
+    public void testCountTakeWithCount() {
+        testTakeWhileMulti(
+                s -> {
+                    AtomicLong c = new AtomicLong();
+                    long rc = s.takeWhile(e -> c.getAndIncrement() < TAKE_WHILE_COUNT_LIMIT)
+                            .mapToLong(e -> 1).reduce(0, Long::sum);
+                    assertTrue(rc <= c.get());
+                },
+                s -> {
+                    AtomicLong c = new AtomicLong();
+                    long rc = s.takeWhile(e -> c.getAndIncrement() < TAKE_WHILE_COUNT_LIMIT)
+                            .mapToLong(e -> 1).reduce(0, Long::sum);
+                    assertTrue(rc <= c.get());
+                },
+                s -> {
+                    AtomicLong c = new AtomicLong();
+                    long rc = s.takeWhile(e -> c.getAndIncrement() < TAKE_WHILE_COUNT_LIMIT)
+                            .map(e -> 1).reduce(0, Long::sum);
+                    assertTrue(rc <= c.get());
+                },
+                s -> {
+                    AtomicLong c = new AtomicLong();
+                    long rc = s.takeWhile(e -> c.getAndIncrement() < TAKE_WHILE_COUNT_LIMIT)
+                            .mapToLong(e -> 1).reduce(0, Long::sum);
+                    assertTrue(rc <= c.get());
+                });
+    }
+
+    @Test(groups = { "serialization-hostile" })
+    public void testCountTakeWithToArray() {
+        testTakeWhileMulti(
+                s -> {
+                    AtomicLong c = new AtomicLong();
+                    Object[] ra = s.takeWhile(e -> c.getAndIncrement() < TAKE_WHILE_COUNT_LIMIT)
+                            .toArray();
+                    assertTrue(ra.length <= c.get());
+                },
+                s -> {
+                    AtomicLong c = new AtomicLong();
+                    int[] ra = s.takeWhile(e -> c.getAndIncrement() < TAKE_WHILE_COUNT_LIMIT)
+                            .toArray();
+                    assertTrue(ra.length <= c.get());
+                },
+                s -> {
+                    AtomicLong c = new AtomicLong();
+                    long[] ra = s.takeWhile(e -> c.getAndIncrement() < TAKE_WHILE_COUNT_LIMIT)
+                            .toArray();
+                    assertTrue(ra.length <= c.get());
+                },
+                s -> {
+                    AtomicLong c = new AtomicLong();
+                    double[] ra = s.takeWhile(e -> c.getAndIncrement() < TAKE_WHILE_COUNT_LIMIT)
+                            .toArray();
+                    assertTrue(ra.length <= c.get());
+                });
+    }
+
+
+    @Test(groups = { "serialization-hostile" })
+    public void testCountDropWithCount() {
+        testDropWhileMulti(
+                s -> {
+                    AtomicLong c = new AtomicLong();
+                    long rc = s.dropWhile(e -> c.getAndIncrement() < DROP_WHILE_COUNT_LIMIT)
+                            .mapToLong(e -> 1).reduce(0, Long::sum);
+                    assertTrue(c.get() >= DROP_WHILE_COUNT_LIMIT);
+                    assertTrue(rc <= DROP_SOURCE_SIZE);
+                },
+                s -> {
+                    AtomicLong c = new AtomicLong();
+                    long rc = s.dropWhile(e -> c.getAndIncrement() < DROP_WHILE_COUNT_LIMIT)
+                            .mapToLong(e -> 1).reduce(0, Long::sum);
+                    assertTrue(c.get() >= DROP_WHILE_COUNT_LIMIT);
+                    assertTrue(rc <= DROP_SOURCE_SIZE);
+                },
+                s -> {
+                    AtomicLong c = new AtomicLong();
+                    long rc = s.dropWhile(e -> c.getAndIncrement() < DROP_WHILE_COUNT_LIMIT)
+                            .map(e -> 1).reduce(0, Long::sum);
+                    assertTrue(c.get() >= DROP_WHILE_COUNT_LIMIT);
+                    assertTrue(rc <= DROP_SOURCE_SIZE);
+                },
+                s -> {
+                    AtomicLong c = new AtomicLong();
+                    long rc = s.dropWhile(e -> c.getAndIncrement() < DROP_WHILE_COUNT_LIMIT)
+                            .mapToLong(e -> 1).reduce(0, Long::sum);
+                    assertTrue(c.get() >= DROP_WHILE_COUNT_LIMIT);
+                    assertTrue(rc <= DROP_SOURCE_SIZE);
+                });
+    }
+
+    @Test(groups = { "serialization-hostile" })
+    public void testCountDropWithToArray() {
+        testDropWhileMulti(
+                s -> {
+                    AtomicLong c = new AtomicLong();
+                    Object[] ra = s.dropWhile(e -> c.getAndIncrement() < DROP_WHILE_COUNT_LIMIT)
+                            .toArray();
+                    assertTrue(c.get() >= DROP_WHILE_COUNT_LIMIT);
+                    assertTrue(ra.length <= DROP_SOURCE_SIZE);
+                },
+                s -> {
+                    AtomicLong c = new AtomicLong();
+                    int[] ra = s.dropWhile(e -> c.getAndIncrement() < DROP_WHILE_COUNT_LIMIT)
+                            .toArray();
+                    assertTrue(c.get() >= DROP_WHILE_COUNT_LIMIT);
+                    assertTrue(ra.length <= DROP_SOURCE_SIZE);
+                },
+                s -> {
+                    AtomicLong c = new AtomicLong();
+                    long[] ra = s.dropWhile(e -> c.getAndIncrement() < DROP_WHILE_COUNT_LIMIT)
+                            .toArray();
+                    assertTrue(c.get() >= DROP_WHILE_COUNT_LIMIT);
+                    assertTrue(ra.length <= DROP_SOURCE_SIZE);
+                },
+                s -> {
+                    AtomicLong c = new AtomicLong();
+                    double[] ra = s.dropWhile(e -> c.getAndIncrement() < DROP_WHILE_COUNT_LIMIT)
+                            .toArray();
+                    assertTrue(c.get() >= DROP_WHILE_COUNT_LIMIT);
+                    assertTrue(ra.length <= DROP_SOURCE_SIZE);
+                });
+    }
+
+
+    private void testTakeWhileMulti(Consumer<Stream<Integer>> mRef,
+                                    Consumer<IntStream> mInt,
+                                    Consumer<LongStream> mLong,
+                                    Consumer<DoubleStream> mDouble) {
+        Map<String, Supplier<Stream<Integer>>> sources = new HashMap<>();
+        sources.put("Stream.generate()", () -> Stream.generate(() -> 1));
+        sources.put("Stream.iterate()", () -> Stream.iterate(1, x -> 1));
+        sources.put("Stream.iterate().unordered()", () -> Stream.iterate(1, x -> 1));
+        testWhileMulti(sources, mRef, mInt, mLong, mDouble);
+    }
+
+    private void testDropWhileMulti(Consumer<Stream<Integer>> mRef,
+                                    Consumer<IntStream> mInt,
+                                    Consumer<LongStream> mLong,
+                                    Consumer<DoubleStream> mDouble) {
+        Map<String, Supplier<Stream<Integer>>> sources = new HashMap<>();
+        sources.put("IntStream.range().boxed()",
+                    () -> IntStream.range(0, DROP_SOURCE_SIZE).boxed());
+        sources.put("IntStream.range().boxed().unordered()",
+                    () -> IntStream.range(0, DROP_SOURCE_SIZE).boxed().unordered());
+        sources.put("LinkedList.stream()",
+                    () -> IntStream.range(0, DROP_SOURCE_SIZE).boxed()
+                            .collect(toCollection(LinkedList::new))
+                            .stream());
+        sources.put("LinkedList.stream().unordered()",
+                    () -> IntStream.range(0, DROP_SOURCE_SIZE).boxed()
+                            .collect(toCollection(LinkedList::new))
+                            .stream()
+                            .unordered());
+        testWhileMulti(sources, mRef, mInt, mLong, mDouble);
+    }
+
+    private void testWhileMulti(Map<String, Supplier<Stream<Integer>>> sources,
+                                Consumer<Stream<Integer>> mRef,
+                                Consumer<IntStream> mInt,
+                                Consumer<LongStream> mLong,
+                                Consumer<DoubleStream> mDouble) {
+        Map<String, Function<Stream<Integer>, Stream<Integer>>> transforms = new HashMap<>();
+        transforms.put("Stream.sequential()", s -> {
+            BooleanSupplier isWithinExecutionPeriod = within(System.currentTimeMillis(),
+                                                             EXECUTION_TIME_LIMIT);
+            return s.peek(e -> {
+                if (!isWithinExecutionPeriod.getAsBoolean()) {
+                    throw new RuntimeException();
+                }
+            });
+        });
+        transforms.put("Stream.parallel()", s -> {
+            BooleanSupplier isWithinExecutionPeriod = within(System.currentTimeMillis(),
+                                                             EXECUTION_TIME_LIMIT);
+            return s.parallel()
+                    .peek(e -> {
+                        if (!isWithinExecutionPeriod.getAsBoolean()) {
+                            throw new RuntimeException();
+                        }
+                    });
+        });
+
+        Map<String, Consumer<Stream<Integer>>> actions = new HashMap<>();
+        actions.put("Ref", mRef);
+        actions.put("Int", s -> mInt.accept(s.mapToInt(e -> e)));
+        actions.put("Long", s -> mLong.accept(s.mapToLong(e -> e)));
+        actions.put("Double", s -> mDouble.accept(s.mapToDouble(e -> e)));
+        actions.put("Ref using defaults", s -> mRef.accept(DefaultMethodStreams.delegateTo(s)));
+        actions.put("Int using defaults", s -> mInt.accept(DefaultMethodStreams.delegateTo(s.mapToInt(e -> e))));
+        actions.put("Long using defaults", s -> mLong.accept(DefaultMethodStreams.delegateTo(s.mapToLong(e -> e))));
+        actions.put("Double using defaults", s -> mDouble.accept(DefaultMethodStreams.delegateTo(s.mapToDouble(e -> e))));
+
+        for (Map.Entry<String, Supplier<Stream<Integer>>> s : sources.entrySet()) {
+            setContext("source", s.getKey());
+
+            for (Map.Entry<String, Function<Stream<Integer>, Stream<Integer>>> t : transforms.entrySet()) {
+                setContext("transform", t.getKey());
+
+                for (Map.Entry<String, Consumer<Stream<Integer>>> a : actions.entrySet()) {
+                    setContext("shape", a.getKey());
+
+                    Stream<Integer> stream = s.getValue().get();
+                    stream = t.getValue().apply(stream);
+                    a.getValue().accept(stream);
+                }
+            }
+        }
+    }
+
+    static BooleanSupplier within(long start, long durationInMillis) {
+        return () -> (System.currentTimeMillis() - start) < durationInMillis;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/util/stream/test/org/openjdk/tests/java/util/stream/WhileOpTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,364 @@
+/*
+ * 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 org.openjdk.tests.java.util.stream;
+
+import org.testng.annotations.Test;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.LinkedHashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+import java.util.concurrent.atomic.AtomicBoolean;
+import java.util.function.Function;
+import java.util.function.Predicate;
+import java.util.stream.DefaultMethodStreams;
+import java.util.stream.DoubleStream;
+import java.util.stream.IntStream;
+import java.util.stream.LambdaTestHelpers;
+import java.util.stream.LongStream;
+import java.util.stream.OpTestCase;
+import java.util.stream.Stream;
+import java.util.stream.StreamTestDataProvider;
+import java.util.stream.TestData;
+
+/*
+ * @test
+ * @bug 8071597
+ */
+@Test
+public class WhileOpTest extends OpTestCase {
+
+    @Test(dataProvider = "StreamTestData<Integer>", dataProviderClass = StreamTestDataProvider.class,
+          groups = { "serialization-hostile" })
+    public void testTakeWhileOps(String name, TestData.OfRef<Integer> data) {
+        for (int size : sizes(data.size())) {
+            setContext("takeWhile", size);
+
+            testWhileMulti(data,
+                           whileResultAsserter(data, WhileOp.Take, e -> e < size),
+                           s -> s.takeWhile(e -> e < size),
+                           s -> s.takeWhile(e -> e < size),
+                           s -> s.takeWhile(e -> e < size),
+                           s -> s.takeWhile(e -> e < size));
+
+
+            testWhileMulti(data,
+                           whileResultAsserter(data, WhileOp.Take, e -> e < size / 2),
+                           s -> s.takeWhile(e -> e < size).takeWhile(e -> e < size / 2),
+                           s -> s.takeWhile(e -> e < size).takeWhile(e -> e < size / 2),
+                           s -> s.takeWhile(e -> e < size).takeWhile(e -> e < size / 2),
+                           s -> s.takeWhile(e -> e < size).takeWhile(e -> e < size / 2));
+        }
+    }
+
+    @Test(dataProvider = "StreamTestData<Integer>", dataProviderClass = StreamTestDataProvider.class,
+          groups = { "serialization-hostile" })
+    public void testDropWhileOps(String name, TestData.OfRef<Integer> data) {
+        for (int size : sizes(data.size())) {
+            setContext("dropWhile", size);
+
+            testWhileMulti(data,
+                           whileResultAsserter(data, WhileOp.Drop, e -> e < size),
+                           s -> s.dropWhile(e -> e < size),
+                           s -> s.dropWhile(e -> e < size),
+                           s -> s.dropWhile(e -> e < size),
+                           s -> s.dropWhile(e -> e < size));
+
+            testWhileMulti(data,
+                           whileResultAsserter(data, WhileOp.Drop, e -> e < size),
+                           s -> s.dropWhile(e -> e < size / 2).dropWhile(e -> e < size),
+                           s -> s.dropWhile(e -> e < size / 2).dropWhile(e -> e < size),
+                           s -> s.dropWhile(e -> e < size / 2).dropWhile(e -> e < size),
+                           s -> s.dropWhile(e -> e < size / 2).dropWhile(e -> e < size));
+        }
+    }
+
+    @Test(dataProvider = "StreamTestData<Integer>", dataProviderClass = StreamTestDataProvider.class,
+          groups = { "serialization-hostile" })
+    public void testDropTakeWhileOps(String name, TestData.OfRef<Integer> data) {
+        for (int size : sizes(data.size())) {
+            setContext("dropWhile", size);
+
+            testWhileMulti(data,
+                           whileResultAsserter(data, WhileOp.Undefined, null),
+                           s -> s.dropWhile(e -> e < size / 2).takeWhile(e -> e < size),
+                           s -> s.dropWhile(e -> e < size / 2).takeWhile(e -> e < size),
+                           s -> s.dropWhile(e -> e < size / 2).takeWhile(e -> e < size),
+                           s -> s.dropWhile(e -> e < size / 2).takeWhile(e -> e < size));
+        }
+    }
+
+    /**
+     * While operation type to be asserted on
+     */
+    enum WhileOp {
+        /**
+         * The takeWhile operation
+         */
+        Take,
+        /**
+         * The dropWhile operation
+         */
+        Drop,
+        /**
+         * The operation(s) are undefined
+         */
+        Undefined
+    }
+
+    /**
+     * Create a result asserter for takeWhile or dropWhile operations.
+     * <p>
+     * If the stream pipeline consists of the takeWhile operation
+     * ({@link WhileOp#Take}) or the dropWhile operation ({@link WhileOp#Drop})
+     * then specific assertions can be made on the actual result based on the
+     * input elements, {@code inputData}, and whether those elements match the
+     * predicate, {@code p}, of the operation.
+     * <p>
+     * If the input elements have an encounter order then the actual result
+     * is asserted against the result of operating sequentially on input
+     * elements given the predicate and in accordance with the operation
+     * semantics. (The actual result whether produced sequentially or in
+     * parallel should the same.)
+     * <p>
+     * If the input elements have no encounter order then an actual result
+     * is, for practical purposes, considered non-deterministic.
+     * Consider an input list of lists that contains all possible permutations
+     * of the input elements, and a output list of lists that is the result of
+     * applying the pipeline with the operation sequentially to each input
+     * list.
+     * Any list in the output lists is a valid result. It's not practical to
+     * test in such a manner.
+     * For a takeWhile operation the following assertions can be made if
+     * only some of the input elements match the predicate (i.e. taking will
+     * short-circuit the pipeline):
+     * <ol>
+     * <li>The set of output elements is a subset of the set of matching
+     * input elements</li>
+     * <li>The set of output elements and the set of non-matching input
+     * element are disjoint</li>
+     * </ol>
+     * For a dropWhile operation the following assertions can be made:
+     * <ol>
+     * <li>The set of non-matching input elements is a subset of the set of
+     * output elements</li>
+     * <li>The set of matching output elements is a subset of the set of
+     * matching input elements</li>
+     * </ol>
+     *
+     * @param inputData the elements input into the stream pipeline
+     * @param op the operation of the stream pipeline, one of takeWhile,
+     * dropWhile, or an undefined set of operations (possibly including
+     * two or more takeWhile and/or dropWhile operations, or because
+     * the predicate is not stateless).
+     * @param p the stateless predicate applied to the operation, ignored if
+     * the
+     * operation is {@link WhileOp#Undefined}.
+     * @param <T> the type of elements
+     * @return a result asserter
+     */
+    private <T> ResultAsserter<Iterable<T>> whileResultAsserter(Iterable<T> inputData,
+                                                                WhileOp op,
+                                                                Predicate<? super T> p) {
+        return (act, exp, ord, par) -> {
+            if (par & !ord) {
+                List<T> input = new ArrayList<>();
+                inputData.forEach(input::add);
+
+                List<T> output = new ArrayList<>();
+                act.forEach(output::add);
+
+                if (op == WhileOp.Take) {
+                    List<T> matchingInput = new ArrayList<>();
+                    List<T> nonMatchingInput = new ArrayList<>();
+                    input.forEach(t -> {
+                        if (p.test(t))
+                            matchingInput.add(t);
+                        else
+                            nonMatchingInput.add(t);
+                    });
+
+                    // If some, not all, elements are taken
+                    if (matchingInput.size() < input.size()) {
+                        assertTrue(output.size() <= matchingInput.size(),
+                                   "Output is larger than the matching input");
+
+                        // The output must be a subset of the matching input
+                        assertTrue(matchingInput.containsAll(output),
+                                   "Output is not a subset of the matching input");
+
+                        // The output must not contain any non matching elements
+                        for (T nonMatching : nonMatchingInput) {
+                            assertFalse(output.contains(nonMatching),
+                                        "Output and non-matching input are not disjoint");
+                        }
+                    }
+                }
+                else if (op == WhileOp.Drop) {
+                    List<T> matchingInput = new ArrayList<>();
+                    List<T> nonMatchingInput = new ArrayList<>();
+                    input.forEach(t -> {
+                        if (p.test(t))
+                            matchingInput.add(t);
+                        else
+                            nonMatchingInput.add(t);
+                    });
+
+                    // The non matching input must be a subset of output
+                    assertTrue(output.containsAll(nonMatchingInput),
+                               "Non-matching input is not a subset of the output");
+
+                    // The matching output must be a subset of the matching input
+                    List<T> matchingOutput = new ArrayList<>();
+                    output.forEach(i -> {
+                        if (p.test(i))
+                            matchingOutput.add(i);
+                    });
+                    assertTrue(matchingInput.containsAll(matchingOutput),
+                               "Matching output is not a subset of matching input");
+                }
+
+                // Note: if there is a combination of takeWhile and dropWhile then specific
+                // assertions cannot be performed.
+                // All that can be reliably asserted is the output is a subset of the input
+
+                assertTrue(input.containsAll(output));
+            }
+            else {
+                // For specific operations derive expected result from the input
+                if (op == WhileOp.Take) {
+                    List<T> takeInput = new ArrayList<>();
+                    for (T t : inputData) {
+                        if (p.test(t))
+                            takeInput.add(t);
+                        else
+                            break;
+                    }
+
+                    LambdaTestHelpers.assertContents(act, takeInput);
+                }
+                else if (op == WhileOp.Drop) {
+                    List<T> dropInput = new ArrayList<>();
+                    for (T t : inputData) {
+                        if (dropInput.size() > 0 || !p.test(t))
+                            dropInput.add(t);
+                    }
+
+                    LambdaTestHelpers.assertContents(act, dropInput);
+                }
+
+                LambdaTestHelpers.assertContents(act, exp);
+            }
+        };
+    }
+
+    private Collection<Integer> sizes(int s) {
+        Set<Integer> sizes = new LinkedHashSet<>();
+
+        sizes.add(0);
+        sizes.add(1);
+        sizes.add(s / 4);
+        sizes.add(s / 2);
+        sizes.add(3 * s / 4);
+        sizes.add(Math.max(0, s - 1));
+        sizes.add(s);
+        sizes.add(Integer.MAX_VALUE);
+
+        return sizes;
+    }
+
+    private void testWhileMulti(TestData.OfRef<Integer> data,
+                                ResultAsserter<Iterable<Integer>> ra,
+                                Function<Stream<Integer>, Stream<Integer>> mRef,
+                                Function<IntStream, IntStream> mInt,
+                                Function<LongStream, LongStream> mLong,
+                                Function<DoubleStream, DoubleStream> mDouble) {
+        Map<String, Function<Stream<Integer>, Stream<Integer>>> ms = new HashMap<>();
+        ms.put("Ref", mRef);
+        ms.put("Int", s -> mInt.apply(s.mapToInt(e -> e)).mapToObj(e -> e));
+        ms.put("Long", s -> mLong.apply(s.mapToLong(e -> e)).mapToObj(e -> (int) e));
+        ms.put("Double", s -> mDouble.apply(s.mapToDouble(e -> e)).mapToObj(e -> (int) e));
+        ms.put("Ref using defaults", s -> mRef.apply(DefaultMethodStreams.delegateTo(s)));
+        ms.put("Int using defaults", s -> mInt.apply(DefaultMethodStreams.delegateTo(s.mapToInt(e -> e))).mapToObj(e -> e));
+        ms.put("Long using defaults", s -> mLong.apply(DefaultMethodStreams.delegateTo(s.mapToLong(e -> e))).mapToObj(e -> (int) e));
+        ms.put("Double using defaults", s -> mDouble.apply(DefaultMethodStreams.delegateTo(s.mapToDouble(e -> e))).mapToObj(e -> (int) e));
+
+        testWhileMulti(data, ra, ms);
+    }
+
+    private final void testWhileMulti(TestData.OfRef<Integer> data,
+                                      ResultAsserter<Iterable<Integer>> ra,
+                                      Map<String, Function<Stream<Integer>, Stream<Integer>>> ms) {
+        for (Map.Entry<String, Function<Stream<Integer>, Stream<Integer>>> e : ms.entrySet()) {
+            setContext("shape", e.getKey());
+
+            withData(data)
+                    .stream(e.getValue())
+                    .resultAsserter(ra)
+                    .exercise();
+        }
+    }
+
+    @Test(groups = { "serialization-hostile" })
+    public void testRefDefaultClose() {
+        AtomicBoolean isClosed = new AtomicBoolean();
+        Stream<Integer> s = Stream.of(1, 2, 3).onClose(() -> isClosed.set(true));
+        try (Stream<Integer> ds = DefaultMethodStreams.delegateTo(s).takeWhile(e -> e < 3)) {
+            ds.count();
+        }
+        assertTrue(isClosed.get());
+    }
+
+    @Test(groups = { "serialization-hostile" })
+    public void testIntDefaultClose() {
+        AtomicBoolean isClosed = new AtomicBoolean();
+        IntStream s = IntStream.of(1, 2, 3).onClose(() -> isClosed.set(true));
+        try (IntStream ds = DefaultMethodStreams.delegateTo(s).takeWhile(e -> e < 3)) {
+            ds.count();
+        }
+        assertTrue(isClosed.get());
+    }
+
+    @Test(groups = { "serialization-hostile" })
+    public void testLongDefaultClose() {
+        AtomicBoolean isClosed = new AtomicBoolean();
+        LongStream s = LongStream.of(1, 2, 3).onClose(() -> isClosed.set(true));
+        try (LongStream ds = DefaultMethodStreams.delegateTo(s).takeWhile(e -> e < 3)) {
+            ds.count();
+        }
+        assertTrue(isClosed.get());
+    }
+
+    @Test(groups = { "serialization-hostile" })
+    public void testDoubleDefaultClose() {
+        AtomicBoolean isClosed = new AtomicBoolean();
+        DoubleStream s = DoubleStream.of(1, 2, 3).onClose(() -> isClosed.set(true));
+        try (DoubleStream ds = DefaultMethodStreams.delegateTo(s).takeWhile(e -> e < 3)) {
+            ds.count();
+        }
+        assertTrue(isClosed.get());
+    }
+}
--- a/jdk/test/javax/management/monitor/GaugeMonitorDeadlockTest.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/javax/management/monitor/GaugeMonitorDeadlockTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -27,6 +27,7 @@
  * @summary Test that no locks are held when a monitor attribute is sampled
  * or notif delivered.
  * @author Eamonn McManus
+ * @library /lib/testlibrary
  * @modules java.management
  * @run clean GaugeMonitorDeadlockTest
  * @run build GaugeMonitorDeadlockTest
@@ -48,6 +49,8 @@
 import javax.management.monitor.GaugeMonitor;
 import javax.management.monitor.GaugeMonitorMBean;
 
+import jdk.testlibrary.Utils;
+
 public class GaugeMonitorDeadlockTest {
     private static enum When {IN_GET_ATTRIBUTE, IN_NOTIFY};
     private static long checkingTime;
@@ -55,8 +58,7 @@
     public static void main(String[] args) throws Exception {
         if (args.length != 1)
             throw new Exception("Arg should be test number");
-        double factor = Double.parseDouble(System.getProperty("test.timeout.factor", "1.0"));
-        checkingTime = (long)factor*1000;
+        checkingTime = Utils.adjustTimeout(1000); // default 1s timeout
         System.out.println("=== checkingTime = " + checkingTime + "ms");
 
         int testNo = Integer.parseInt(args[0]) - 1;
@@ -102,11 +104,12 @@
             monitorProxy.setGranularityPeriod(10L); // 10 ms
             monitorProxy.setNotifyHigh(true);
             monitorProxy.setNotifyLow(true);
-            monitorProxy.start();
 
             System.out.println("=== Waiting observedProxy.getGetCount() to be "
                     + "changed, presumable deadlock if timeout?");
             final int initGetCount = observedProxy.getGetCount();
+            monitorProxy.start();
+
             long checkedTime = System.currentTimeMillis();
             long nowTime;
             ThreadMXBean threadMXBean = ManagementFactory.getThreadMXBean();
--- a/jdk/test/javax/management/monitor/StringMonitorDeadlockTest.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/javax/management/monitor/StringMonitorDeadlockTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -38,7 +38,6 @@
 
 import java.lang.management.ManagementFactory;
 import java.util.concurrent.atomic.AtomicInteger;
-import javax.management.Attribute;
 import javax.management.JMX;
 import javax.management.MBeanServer;
 import javax.management.Notification;
@@ -96,9 +95,10 @@
             monitorProxy.setStringToCompare("old");
             monitorProxy.setGranularityPeriod(10L); // 10 ms
             monitorProxy.setNotifyDiffer(true);
+
+            final int initGetCount = observedProxy.getGetCount();
             monitorProxy.start();
 
-            final int initGetCount = observedProxy.getGetCount();
             int getCount = initGetCount;
             for (int i = 0; i < 500; i++) { // 500 * 10 = 5 seconds
                 getCount = observedProxy.getGetCount();
--- a/jdk/test/javax/net/ssl/SSLEngine/ConnectionTest.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/javax/net/ssl/SSLEngine/ConnectionTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -81,6 +81,9 @@
         ssle1.setEnabledCipherSuites(new String [] {
             "SSL_RSA_WITH_RC4_128_MD5"});
 
+        ssle2.setEnabledCipherSuites(new String [] {
+            "SSL_RSA_WITH_RC4_128_MD5"});
+
         createBuffers();
     }
 
--- a/jdk/test/javax/net/ssl/SSLEngine/LargeBufs.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/javax/net/ssl/SSLEngine/LargeBufs.java	Wed Jul 05 20:42:36 2017 +0200
@@ -93,6 +93,7 @@
         createSSLEngines();
 
         System.out.println("Using " + cipher);
+        ssle1.setEnabledCipherSuites(new String [] { cipher });
         ssle2.setEnabledCipherSuites(new String [] { cipher });
 
         createBuffers();
--- a/jdk/test/javax/net/ssl/SSLParameters/UseCipherSuitesOrder.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/javax/net/ssl/SSLParameters/UseCipherSuitesOrder.java	Wed Jul 05 20:42:36 2017 +0200
@@ -31,7 +31,7 @@
  * @bug 7188657
  * @summary There should be a way to reorder the JSSE ciphers
  * @run main/othervm UseCipherSuitesOrder
- *     TLS_RSA_WITH_AES_128_CBC_SHA,SSL_RSA_WITH_RC4_128_SHA
+ *     TLS_RSA_WITH_AES_128_CBC_SHA,SSL_RSA_WITH_3DES_EDE_CBC_SHA
  */
 
 import java.io.*;
--- a/jdk/test/javax/net/ssl/TLSCommon/SSLEngineTestCase.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/javax/net/ssl/TLSCommon/SSLEngineTestCase.java	Wed Jul 05 20:42:36 2017 +0200
@@ -749,6 +749,8 @@
      */
     public static SSLContext getContext() {
         try {
+            java.security.Security.setProperty("jdk.tls.disabledAlgorithms", "");
+            java.security.Security.setProperty("jdk.certpath.disabledAlgorithms", "");
             KeyStore ks = KeyStore.getInstance("JKS");
             KeyStore ts = KeyStore.getInstance("JKS");
             char[] passphrase = PASSWD.toCharArray();
--- a/jdk/test/javax/net/ssl/TLSv11/GenericStreamCipher.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/javax/net/ssl/TLSv11/GenericStreamCipher.java	Wed Jul 05 20:42:36 2017 +0200
@@ -93,6 +93,10 @@
         SSLServerSocket sslServerSocket =
             (SSLServerSocket) sslssf.createServerSocket(serverPort);
 
+        // enable a stream cipher
+        sslServerSocket.setEnabledCipherSuites(
+            new String[] {"SSL_RSA_WITH_RC4_128_MD5"});
+
         serverPort = sslServerSocket.getLocalPort();
 
         /*
--- a/jdk/test/javax/net/ssl/sanity/ciphersuites/CipherSuitesInOrder.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/javax/net/ssl/sanity/ciphersuites/CipherSuitesInOrder.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012, 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
@@ -94,13 +94,6 @@
         "SSL_DHE_RSA_WITH_3DES_EDE_CBC_SHA",
         "SSL_DHE_DSS_WITH_3DES_EDE_CBC_SHA",
 
-        "TLS_ECDHE_ECDSA_WITH_RC4_128_SHA",
-        "TLS_ECDHE_RSA_WITH_RC4_128_SHA",
-        "SSL_RSA_WITH_RC4_128_SHA",
-        "TLS_ECDH_ECDSA_WITH_RC4_128_SHA",
-        "TLS_ECDH_RSA_WITH_RC4_128_SHA",
-        "SSL_RSA_WITH_RC4_128_MD5",
-
         "TLS_EMPTY_RENEGOTIATION_INFO_SCSV",
 
         "TLS_DH_anon_WITH_AES_256_GCM_SHA384",
@@ -114,6 +107,13 @@
         "TLS_DH_anon_WITH_AES_128_CBC_SHA",
         "TLS_ECDH_anon_WITH_3DES_EDE_CBC_SHA",
         "SSL_DH_anon_WITH_3DES_EDE_CBC_SHA",
+
+        "TLS_ECDHE_ECDSA_WITH_RC4_128_SHA",
+        "TLS_ECDHE_RSA_WITH_RC4_128_SHA",
+        "SSL_RSA_WITH_RC4_128_SHA",
+        "TLS_ECDH_ECDSA_WITH_RC4_128_SHA",
+        "TLS_ECDH_RSA_WITH_RC4_128_SHA",
+        "SSL_RSA_WITH_RC4_128_MD5",
         "TLS_ECDH_anon_WITH_RC4_128_SHA",
         "SSL_DH_anon_WITH_RC4_128_MD5",
 
--- a/jdk/test/javax/net/ssl/sanity/interop/ClientJSSEServerJSSE.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/javax/net/ssl/sanity/interop/ClientJSSEServerJSSE.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2002, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2002, 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
@@ -33,13 +33,10 @@
 public class ClientJSSEServerJSSE {
 
     public static void main(String[] args) throws Exception {
-        // reset the security property to make sure that the algorithms
+        // reset security properties to make sure that the algorithms
         // and keys used in this test are not disabled.
         Security.setProperty("jdk.tls.disabledAlgorithms", "");
-
-        // MD5 is used in this test case, don't disable MD5 algorithm.
-        Security.setProperty(
-                "jdk.certpath.disabledAlgorithms", "MD2, RSA keySize < 1024");
+        Security.setProperty("jdk.certpath.disabledAlgorithms", "");
 
         CipherTest.main(new JSSEFactory(), args);
     }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/javax/security/sasl/Sasl/ClientServerTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,477 @@
+/*
+ * 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.
+ */
+
+import java.io.Closeable;
+import java.io.IOException;
+import java.io.ObjectInputStream;
+import java.io.ObjectOutputStream;
+import java.io.Serializable;
+import java.net.ServerSocket;
+import java.net.Socket;
+import java.net.UnknownHostException;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.StringJoiner;
+import javax.security.auth.callback.Callback;
+import javax.security.auth.callback.CallbackHandler;
+import javax.security.auth.callback.NameCallback;
+import javax.security.auth.callback.PasswordCallback;
+import javax.security.auth.callback.UnsupportedCallbackException;
+import javax.security.sasl.AuthorizeCallback;
+import javax.security.sasl.RealmCallback;
+import javax.security.sasl.RealmChoiceCallback;
+import javax.security.sasl.Sasl;
+import javax.security.sasl.SaslClient;
+import javax.security.sasl.SaslException;
+import javax.security.sasl.SaslServer;
+
+/*
+ * @test
+ * @bug 8049814
+ * @summary JAVA SASL server and client tests with CRAM-MD5 and
+ *          DIGEST-MD5 mechanisms. The tests try different QOP values on
+ *          client and server side.
+ * @modules java.security.sasl/javax.security.sasl
+ */
+public class ClientServerTest {
+
+    private static final int DELAY = 100;
+    private static final String LOCALHOST = "localhost";
+    private static final String DIGEST_MD5 = "DIGEST-MD5";
+    private static final String CRAM_MD5 = "CRAM-MD5";
+    private static final String PROTOCOL = "saslservice";
+    private static final String USER_ID = "sasltester";
+    private static final String PASSWD = "password";
+    private static final String QOP_AUTH = "auth";
+    private static final String QOP_AUTH_CONF = "auth-conf";
+    private static final String QOP_AUTH_INT = "auth-int";
+    private static final String AUTHID_SASL_TESTER = "sasl_tester";
+    private static final ArrayList<String> SUPPORT_MECHS = new ArrayList<>();
+
+    static {
+        SUPPORT_MECHS.add(DIGEST_MD5);
+        SUPPORT_MECHS.add(CRAM_MD5);
+    }
+
+    public static void main(String[] args) throws Exception {
+        String[] allQops = { QOP_AUTH_CONF, QOP_AUTH_INT, QOP_AUTH };
+        String[] twoQops = { QOP_AUTH_INT, QOP_AUTH };
+        String[] authQop = { QOP_AUTH };
+        String[] authIntQop = { QOP_AUTH_INT };
+        String[] authConfQop = { QOP_AUTH_CONF };
+        String[] emptyQop = {};
+
+        boolean success = true;
+
+        success &= runTest("", CRAM_MD5, new String[] { QOP_AUTH },
+                new String[] { QOP_AUTH }, false);
+        success &= runTest("", DIGEST_MD5, new String[] { QOP_AUTH },
+                new String[] { QOP_AUTH }, false);
+        success &= runTest(AUTHID_SASL_TESTER, DIGEST_MD5,
+                new String[] { QOP_AUTH }, new String[] { QOP_AUTH }, false);
+        success &= runTest("", DIGEST_MD5, allQops, authQop, false);
+        success &= runTest("", DIGEST_MD5, allQops, authIntQop, false);
+        success &= runTest("", DIGEST_MD5, allQops, authConfQop, false);
+        success &= runTest("", DIGEST_MD5, twoQops, authQop, false);
+        success &= runTest("", DIGEST_MD5, twoQops, authIntQop, false);
+        success &= runTest("", DIGEST_MD5, twoQops, authConfQop, true);
+        success &= runTest("", DIGEST_MD5, authIntQop, authQop, true);
+        success &= runTest("", DIGEST_MD5, authConfQop, authQop, true);
+        success &= runTest("", DIGEST_MD5, authConfQop, emptyQop, true);
+        success &= runTest("", DIGEST_MD5, authIntQop, emptyQop, true);
+        success &= runTest("", DIGEST_MD5, authQop, emptyQop, true);
+
+        if (!success) {
+            throw new RuntimeException("At least one test case failed");
+        }
+
+        System.out.println("Test passed");
+    }
+
+    private static boolean runTest(String authId, String mech,
+            String[] clientQops, String[] serverQops, boolean expectException)
+            throws Exception {
+
+        System.out.println("AuthId:" + authId
+                + " mechanism:" + mech
+                + " clientQops: " + Arrays.toString(clientQops)
+                + " serverQops: " + Arrays.toString(serverQops)
+                + " expect exception:" + expectException);
+
+        try (Server server = Server.start(LOCALHOST, authId, serverQops)) {
+            new Client(LOCALHOST, server.getPort(), mech, authId, clientQops)
+                    .run();
+            if (expectException) {
+                System.out.println("Expected exception not thrown");
+                return false;
+            }
+        } catch (SaslException e) {
+            if (!expectException) {
+                System.out.println("Unexpected exception: " + e);
+                return false;
+            }
+            System.out.println("Expected exception: " + e);
+        }
+
+        return true;
+    }
+
+    static enum SaslStatus {
+        SUCCESS, FAILURE, CONTINUE
+    }
+
+    static class Message implements Serializable {
+
+        private final SaslStatus status;
+        private final byte[] data;
+
+        public Message(SaslStatus status, byte[] data) {
+            this.status = status;
+            this.data = data;
+        }
+
+        public SaslStatus getStatus() {
+            return status;
+        }
+
+        public byte[] getData() {
+            return data;
+        }
+    }
+
+    static class SaslPeer {
+
+        final String host;
+        final String mechanism;
+        final String qop;
+        final CallbackHandler callback;
+
+        SaslPeer(String host, String authId, String... qops) {
+            this(host, null, authId, qops);
+        }
+
+        SaslPeer(String host, String mechanism, String authId, String... qops) {
+            this.host = host;
+            this.mechanism = mechanism;
+
+            StringJoiner sj = new StringJoiner(",");
+            for (String q : qops) {
+                sj.add(q);
+            }
+            qop = sj.toString();
+
+            callback = new TestCallbackHandler(USER_ID, PASSWD, host, authId);
+        }
+
+        Message getMessage(Object ob) {
+            if (!(ob instanceof Message)) {
+                throw new RuntimeException("Expected an instance of Message");
+            }
+            return (Message) ob;
+        }
+    }
+
+    static class Server extends SaslPeer implements Runnable, Closeable {
+
+        private volatile boolean ready = false;
+        private volatile ServerSocket ssocket;
+
+        static Server start(String host, String authId, String[] serverQops)
+                throws UnknownHostException {
+            Server server = new Server(host, authId, serverQops);
+            Thread thread = new Thread(server);
+            thread.setDaemon(true);
+            thread.start();
+
+            while (!server.ready) {
+                try {
+                    Thread.sleep(DELAY);
+                } catch (InterruptedException e) {
+                    throw new RuntimeException(e);
+                }
+            }
+
+            return server;
+        }
+
+        Server(String host, String authId, String... qops) {
+            super(host, authId, qops);
+        }
+
+        int getPort() {
+            return ssocket.getLocalPort();
+        }
+
+        private void processConnection(SaslEndpoint endpoint)
+                throws SaslException, IOException, ClassNotFoundException {
+            System.out.println("process connection");
+            endpoint.send(SUPPORT_MECHS);
+            Object o = endpoint.receive();
+            if (!(o instanceof String)) {
+                throw new RuntimeException("Received unexpected object: " + o);
+            }
+            String mech = (String) o;
+            SaslServer saslServer = createSaslServer(mech);
+            Message msg = getMessage(endpoint.receive());
+            while (!saslServer.isComplete()) {
+                byte[] data = processData(msg.getData(), endpoint,
+                        saslServer);
+                if (saslServer.isComplete()) {
+                    System.out.println("server is complete");
+                    endpoint.send(new Message(SaslStatus.SUCCESS, data));
+                } else {
+                    System.out.println("server continues");
+                    endpoint.send(new Message(SaslStatus.CONTINUE, data));
+                    msg = getMessage(endpoint.receive());
+                }
+            }
+        }
+
+        private byte[] processData(byte[] data, SaslEndpoint endpoint,
+                SaslServer server) throws SaslException, IOException {
+            try {
+                return server.evaluateResponse(data);
+            } catch (SaslException e) {
+                endpoint.send(new Message(SaslStatus.FAILURE, null));
+                System.out.println("Error while processing data");
+                throw e;
+            }
+        }
+
+        private SaslServer createSaslServer(String mechanism)
+                throws SaslException {
+            Map<String, String> props = new HashMap<>();
+            props.put(Sasl.QOP, qop);
+            return Sasl.createSaslServer(mechanism, PROTOCOL, host, props,
+                    callback);
+        }
+
+        @Override
+        public void run() {
+            try (ServerSocket ss = new ServerSocket(0)) {
+                ssocket = ss;
+                System.out.println("server started on port " + getPort());
+                ready = true;
+                Socket socket = ss.accept();
+                try (SaslEndpoint endpoint = new SaslEndpoint(socket)) {
+                    System.out.println("server accepted connection");
+                    processConnection(endpoint);
+                }
+            } catch (Exception e) {
+                // ignore it for now, client will throw an exception
+            }
+        }
+
+        @Override
+        public void close() throws IOException {
+            if (!ssocket.isClosed()) {
+                ssocket.close();
+            }
+        }
+    }
+
+    static class Client extends SaslPeer {
+
+        private final int port;
+
+        Client(String host, int port, String mech, String authId,
+                String... qops) {
+            super(host, mech, authId, qops);
+            this.port = port;
+        }
+
+        public void run() throws Exception {
+            System.out.println("Host:" + host + " port: "
+                    + port);
+            try (SaslEndpoint endpoint = SaslEndpoint.create(host, port)) {
+                negotiateMechanism(endpoint);
+                SaslClient client = createSaslClient();
+                byte[] data = new byte[0];
+                if (client.hasInitialResponse()) {
+                    data = client.evaluateChallenge(data);
+                }
+                endpoint.send(new Message(SaslStatus.CONTINUE, data));
+                Message msg = getMessage(endpoint.receive());
+                while (!client.isComplete()
+                        && msg.getStatus() != SaslStatus.FAILURE) {
+                    switch (msg.getStatus()) {
+                        case CONTINUE:
+                            System.out.println("client continues");
+                            data = client.evaluateChallenge(msg.getData());
+                            endpoint.send(new Message(SaslStatus.CONTINUE,
+                                    data));
+                            msg = getMessage(endpoint.receive());
+                            break;
+                        case SUCCESS:
+                            System.out.println("client succeeded");
+                            data = client.evaluateChallenge(msg.getData());
+                            if (data != null) {
+                                throw new SaslException("data should be null");
+                            }
+                            break;
+                        default:
+                            throw new RuntimeException("Wrong status:"
+                                    + msg.getStatus());
+                    }
+                }
+
+                if (msg.getStatus() == SaslStatus.FAILURE) {
+                    throw new RuntimeException("Status is FAILURE");
+                }
+            }
+
+            System.out.println("Done");
+        }
+
+        private SaslClient createSaslClient() throws SaslException {
+            Map<String, String> props = new HashMap<>();
+            props.put(Sasl.QOP, qop);
+            return Sasl.createSaslClient(new String[] {mechanism}, USER_ID,
+                    PROTOCOL, host, props, callback);
+        }
+
+        private void negotiateMechanism(SaslEndpoint endpoint)
+                throws ClassNotFoundException, IOException {
+            Object o = endpoint.receive();
+            if (o instanceof ArrayList) {
+                ArrayList list = (ArrayList) o;
+                if (!list.contains(mechanism)) {
+                    throw new RuntimeException(
+                            "Server does not support specified mechanism:"
+                                    + mechanism);
+                }
+            } else {
+                throw new RuntimeException(
+                        "Expected an instance of ArrayList, but received " + o);
+            }
+
+            endpoint.send(mechanism);
+        }
+
+    }
+
+    static class SaslEndpoint implements AutoCloseable {
+
+        private final Socket socket;
+        private ObjectInputStream input;
+        private ObjectOutputStream output;
+
+        static SaslEndpoint create(String host, int port) throws IOException {
+            return new SaslEndpoint(new Socket(host, port));
+        }
+
+        SaslEndpoint(Socket socket) throws IOException {
+            this.socket = socket;
+        }
+
+        private ObjectInputStream getInput() throws IOException {
+            if (input == null && socket != null) {
+                input = new ObjectInputStream(socket.getInputStream());
+            }
+            return input;
+        }
+
+        private ObjectOutputStream getOutput() throws IOException {
+            if (output == null && socket != null) {
+                output = new ObjectOutputStream(socket.getOutputStream());
+            }
+            return output;
+        }
+
+        public Object receive() throws IOException, ClassNotFoundException {
+            return getInput().readObject();
+        }
+
+        public void send(Object obj) throws IOException {
+            getOutput().writeObject(obj);
+            getOutput().flush();
+        }
+
+        @Override
+        public void close() throws IOException {
+            if (socket != null && !socket.isClosed()) {
+                socket.close();
+            }
+        }
+
+    }
+
+    static class TestCallbackHandler implements CallbackHandler {
+
+        private final String userId;
+        private final char[] passwd;
+        private final String realm;
+        private String authId;
+
+        TestCallbackHandler(String userId, String passwd, String realm,
+                String authId) {
+            this.userId = userId;
+            this.passwd = passwd.toCharArray();
+            this.realm = realm;
+            this.authId = authId;
+        }
+
+        @Override
+        public void handle(Callback[] callbacks) throws IOException,
+                UnsupportedCallbackException {
+            for (Callback callback : callbacks) {
+                if (callback instanceof NameCallback) {
+                    System.out.println("NameCallback");
+                    ((NameCallback) callback).setName(userId);
+                } else if (callback instanceof PasswordCallback) {
+                    System.out.println("PasswordCallback");
+                    ((PasswordCallback) callback).setPassword(passwd);
+                } else if (callback instanceof RealmCallback) {
+                    System.out.println("RealmCallback");
+                    ((RealmCallback) callback).setText(realm);
+                } else if (callback instanceof RealmChoiceCallback) {
+                    System.out.println("RealmChoiceCallback");
+                    RealmChoiceCallback choice = (RealmChoiceCallback) callback;
+                    if (realm == null) {
+                        choice.setSelectedIndex(choice.getDefaultChoice());
+                    } else {
+                        String[] choices = choice.getChoices();
+                        for (int j = 0; j < choices.length; j++) {
+                            if (realm.equals(choices[j])) {
+                                choice.setSelectedIndex(j);
+                                break;
+                            }
+                        }
+                    }
+                } else if (callback instanceof AuthorizeCallback) {
+                    System.out.println("AuthorizeCallback");
+                    ((AuthorizeCallback) callback).setAuthorized(true);
+                    if (authId == null || authId.trim().length() == 0) {
+                        authId = userId;
+                    }
+                    ((AuthorizeCallback) callback).setAuthorizedID(authId);
+                } else {
+                    throw new UnsupportedCallbackException(callback);
+                }
+            }
+        }
+    }
+
+}
--- a/jdk/test/javax/swing/JFileChooser/8080628/bug8080628.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/javax/swing/JFileChooser/8080628/bug8080628.java	Wed Jul 05 20:42:36 2017 +0200
@@ -33,6 +33,7 @@
  * @bug 8080628
  * @summary No mnemonics on Open and Save buttons in JFileChooser.
  * @author Alexey Ivanov
+ * @modules java.desktop/sun.swing
  * @run main bug8080628
  */
 public class bug8080628 {
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/javax/swing/JRadioButton/FocusTraversal/FocusTraversal.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,144 @@
+/*
+ * 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.
+ */
+
+/* @test
+   @bug 8129940
+   @summary JRadioButton does not honor non-standard FocusTraversalKeys
+   @author Semyon Sadetsky
+  */
+
+import javax.swing.*;
+import java.awt.*;
+import java.awt.event.KeyEvent;
+import java.util.HashSet;
+import java.util.Set;
+
+public class FocusTraversal {
+
+    private static JFrame frame;
+    private static JRadioButton a;
+    private static JRadioButton d;
+    private static JTextField next;
+    private static JTextField prev;
+
+    public static void main(String[] args) throws Exception {
+        SwingUtilities.invokeAndWait(new Runnable() {
+            @Override
+            public void run() {
+                frame = new JFrame("FocusTraversalTest");
+                frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
+                frame.setUndecorated(true);
+
+                Set<KeyStroke> keystrokes = new HashSet<KeyStroke>();
+                keystrokes.add(KeyStroke.getKeyStroke("TAB"));
+                keystrokes.add(KeyStroke.getKeyStroke("ENTER"));
+                frame.setFocusTraversalKeys(
+                        KeyboardFocusManager.FORWARD_TRAVERSAL_KEYS,
+                        keystrokes);
+
+                a = new JRadioButton("a");
+                JRadioButton b = new JRadioButton("b");
+                JRadioButton c = new JRadioButton("c");
+                d = new JRadioButton("d");
+
+                ButtonGroup radioButtonGroup = new ButtonGroup();
+                radioButtonGroup.add(a);
+                radioButtonGroup.add(b);
+                radioButtonGroup.add(c);
+                radioButtonGroup.add(d);
+
+                JPanel panel = new JPanel();
+                prev = new JTextField("text");
+                panel.add(prev);
+                panel.add(a);
+                panel.add(b);
+                panel.add(c);
+                panel.add(d);
+                next = new JTextField("text");
+                panel.add(next);
+
+                JPanel root = new JPanel();
+                root.setLayout(new BorderLayout());
+                root.add(panel, BorderLayout.CENTER);
+                root.add(new JButton("OK"), BorderLayout.SOUTH);
+
+                frame.add(root);
+                frame.pack();
+                frame.setVisible(true);
+            }
+        });
+
+        SwingUtilities.invokeAndWait(new Runnable() {
+            @Override
+            public void run() {
+                a.requestFocus();
+            }
+        });
+
+        Robot robot = new Robot();
+        robot.waitForIdle();
+
+        robot.setAutoDelay(200);
+
+        robot.keyPress(KeyEvent.VK_ENTER);
+        robot.keyRelease(KeyEvent.VK_ENTER);
+        robot.waitForIdle();
+
+        SwingUtilities.invokeAndWait(new Runnable() {
+            @Override
+            public void run() {
+                Component focusOwner =
+                        FocusManager.getCurrentManager().getFocusOwner();
+                if (focusOwner != next) {
+                    throw new RuntimeException(
+                            "Focus component is wrong after forward key " + focusOwner);
+                }
+            }
+        });
+
+        robot.keyPress(KeyEvent.VK_SHIFT);
+        robot.keyPress(KeyEvent.VK_TAB);
+        robot.keyRelease(KeyEvent.VK_TAB);
+        robot.keyRelease(KeyEvent.VK_SHIFT);
+        robot.waitForIdle();
+        SwingUtilities.invokeAndWait(new Runnable() {
+            @Override
+            public void run() {
+                Component focusOwner =
+                        FocusManager.getCurrentManager().getFocusOwner();
+                if (focusOwner != d) {
+                    throw new RuntimeException(
+                            "Focus component is wrong after backward key " + focusOwner);
+                }
+            }
+        });
+        SwingUtilities.invokeLater(new Runnable() {
+            @Override
+            public void run() {
+                frame.dispose();
+            }
+        });
+        System.out.println("ok");
+
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/javax/swing/JTree/DnD/LastNodeLowerHalfDrop.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,384 @@
+/*
+ * 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.
+ */
+
+/* @test
+   @bug 8129830
+   @summary JTree drag/drop on lower half of last child of container incorrect
+   @author Semyon Sadetsky
+  */
+
+import java.awt.*;
+import java.awt.datatransfer.DataFlavor;
+import java.awt.datatransfer.Transferable;
+import java.awt.datatransfer.UnsupportedFlavorException;
+import java.awt.event.InputEvent;
+import java.util.ArrayList;
+import java.util.Enumeration;
+import java.util.List;
+import javax.swing.*;
+import javax.swing.tree.DefaultMutableTreeNode;
+import javax.swing.tree.DefaultTreeModel;
+import javax.swing.tree.TreeModel;
+import javax.swing.tree.TreeNode;
+import javax.swing.tree.TreePath;
+import javax.swing.tree.TreeSelectionModel;
+
+public class LastNodeLowerHalfDrop {
+
+    private static DefaultMutableTreeNode b1;
+    private static DefaultMutableTreeNode b2;
+    private static DefaultMutableTreeNode c;
+    private static JTree jTree;
+    private static DefaultMutableTreeNode a;
+    private static DefaultMutableTreeNode b;
+    private static DefaultMutableTreeNode a1;
+    private static Point dragPoint;
+    private static Point dropPoint;
+    private static JFrame f;
+    private static DefaultMutableTreeNode c1;
+    private static DefaultMutableTreeNode root;
+
+
+    public static void main(String[] args) throws Exception {
+        SwingUtilities.invokeAndWait(new Runnable() {
+            @Override
+            public void run() {
+                f = new JFrame();
+                f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
+                f.add(new LastNodeLowerHalfDrop().getContent());
+                f.setSize(400, 400);
+                f.setLocationRelativeTo(null);
+                f.setVisible(true);
+            }
+        });
+        testCase(b2, a1, +0.4f);
+        if (!"b2".equals(jTree.getModel().
+                getChild(a, a.getChildCount() - 1).toString())) {
+            throw new RuntimeException("b1 was not inserted in the last position in a");
+        }
+        testCase(c1, c, -0.4f);
+        if (!"c1".equals(jTree.getModel().getChild(root, 2).toString())) {
+            throw new RuntimeException("c1 was not inserted beetween c and b nodes");
+        }
+
+        SwingUtilities.invokeLater(new Runnable() {
+            @Override
+            public void run() {
+                f.dispose();
+            }
+        });
+        System.out.printf("ok");
+    }
+
+    static void testCase(DefaultMutableTreeNode drag,
+                         DefaultMutableTreeNode drop, float shift) throws Exception {
+        Robot robot = new Robot();
+        robot.waitForIdle();
+        SwingUtilities.invokeAndWait(new Runnable() {
+            @Override
+            public void run() {
+                Rectangle rectDrag =
+                        jTree.getPathBounds(new TreePath(drag.getPath()));
+                dragPoint = new Point((int)rectDrag.getCenterX(),
+                        (int) rectDrag.getCenterY());
+                SwingUtilities.convertPointToScreen(dragPoint, jTree);
+                Rectangle rectDrop =
+                        jTree.getPathBounds(new TreePath(drop.getPath()));
+                dropPoint = new Point(rectDrop.x + 5,
+                        (int) (rectDrop.getCenterY() + shift * rectDrop.height));
+                SwingUtilities.convertPointToScreen(dropPoint, jTree);
+            }
+        });
+
+        robot.mouseMove(dragPoint.x, dragPoint.y);
+        robot.mousePress(InputEvent.BUTTON1_MASK);
+        robot.delay(400);
+        robot.mouseMove(dropPoint.x, dropPoint.y);
+        robot.delay(400);
+        robot.mouseRelease(InputEvent.BUTTON1_MASK);
+
+        robot.waitForIdle();
+    }
+
+    private JScrollPane getContent() {
+        jTree = new JTree(getTreeModel());
+        jTree.setRootVisible(false);
+        jTree.setDragEnabled(true);
+        jTree.setDropMode(DropMode.INSERT);
+        jTree.setTransferHandler(new TreeTransferHandler());
+        jTree.getSelectionModel().setSelectionMode(
+                TreeSelectionModel.SINGLE_TREE_SELECTION);
+        expandTree(jTree);
+        return new JScrollPane(jTree);
+    }
+
+    protected static TreeModel getTreeModel() {
+        root = new DefaultMutableTreeNode("Root");
+
+        a = new DefaultMutableTreeNode("A");
+        root.add(a);
+        a1 = new DefaultMutableTreeNode("a1");
+        a.add(a1);
+
+        b = new DefaultMutableTreeNode("B");
+        root.add(b);
+        b1 = new DefaultMutableTreeNode("b1");
+        b.add(b1);
+        b2 = new DefaultMutableTreeNode("b2");
+        b.add(b2);
+
+        c = new DefaultMutableTreeNode("C");
+        root.add(c);
+        c1 = new DefaultMutableTreeNode("c1");
+        c.add(c1);
+        return new DefaultTreeModel(root);
+    }
+
+    private void expandTree(JTree tree) {
+        DefaultMutableTreeNode root = (DefaultMutableTreeNode) tree.getModel()
+                .getRoot();
+        Enumeration e = root.breadthFirstEnumeration();
+        while (e.hasMoreElements()) {
+            DefaultMutableTreeNode node = (DefaultMutableTreeNode) e.nextElement();
+            if (node.isLeaf()) {
+                continue;
+            }
+            int row = tree.getRowForPath(new TreePath(node.getPath()));
+            tree.expandRow(row);
+        }
+    }
+}
+
+class TreeTransferHandler extends TransferHandler {
+    DataFlavor nodesFlavor;
+    DataFlavor[] flavors = new DataFlavor[1];
+    DefaultMutableTreeNode[] nodesToRemove;
+
+    public TreeTransferHandler() {
+        try {
+            String mimeType = DataFlavor.javaJVMLocalObjectMimeType
+                    + ";class=\""
+                    + javax.swing.tree.DefaultMutableTreeNode[].class.getName()
+                    + "\"";
+            nodesFlavor = new DataFlavor(mimeType);
+            flavors[0] = nodesFlavor;
+        } catch (ClassNotFoundException e) {
+            System.out.println("ClassNotFound: " + e.getMessage());
+        }
+    }
+
+    @Override
+    public boolean canImport(TransferHandler.TransferSupport support) {
+        if (!support.isDrop()) {
+            return false;
+        }
+        support.setShowDropLocation(true);
+        if (!support.isDataFlavorSupported(nodesFlavor)) {
+            return false;
+        }
+        // Do not allow a drop on the drag source selections.
+        JTree.DropLocation dl = (JTree.DropLocation) support.getDropLocation();
+        JTree tree = (JTree) support.getComponent();
+        int dropRow = tree.getRowForPath(dl.getPath());
+        int[] selRows = tree.getSelectionRows();
+        for (int i = 0; i < selRows.length; i++) {
+            if (selRows[i] == dropRow) {
+                return false;
+            }
+        }
+        // Do not allow MOVE-action drops if a non-leaf node is
+        // selected unless all of its children are also selected.
+        int action = support.getDropAction();
+        if (action == MOVE) {
+            return haveCompleteNode(tree);
+        }
+        // Do not allow a non-leaf node to be copied to a level
+        // which is less than its source level.
+        TreePath dest = dl.getPath();
+        DefaultMutableTreeNode target = (DefaultMutableTreeNode)
+                dest.getLastPathComponent();
+        TreePath path = tree.getPathForRow(selRows[0]);
+        DefaultMutableTreeNode firstNode = (DefaultMutableTreeNode)
+                path.getLastPathComponent();
+        if (firstNode.getChildCount() > 0
+                && target.getLevel() < firstNode.getLevel()) {
+            return false;
+        }
+        return true;
+    }
+
+    private boolean haveCompleteNode(JTree tree) {
+        int[] selRows = tree.getSelectionRows();
+        TreePath path = tree.getPathForRow(selRows[0]);
+        DefaultMutableTreeNode first = (DefaultMutableTreeNode)
+                path.getLastPathComponent();
+        int childCount = first.getChildCount();
+        // first has children and no children are selected.
+        if (childCount > 0 && selRows.length == 1) {
+            return false;
+        }
+        // first may have children.
+        for (int i = 1; i < selRows.length; i++) {
+            path = tree.getPathForRow(selRows[i]);
+            DefaultMutableTreeNode next = (DefaultMutableTreeNode)
+                    path.getLastPathComponent();
+            if (first.isNodeChild(next)) {
+                // Found a child of first.
+                if (childCount > selRows.length - 1) {
+                    // Not all children of first are selected.
+                    return false;
+                }
+            }
+        }
+        return true;
+    }
+
+    @Override
+    protected Transferable createTransferable(JComponent c) {
+        JTree tree = (JTree) c;
+        TreePath[] paths = tree.getSelectionPaths();
+        if (paths != null) {
+            // Make up a node array of copies for transfer and
+            // another for/of the nodes that will be removed in
+            // exportDone after a successful drop.
+            List<DefaultMutableTreeNode> copies = new ArrayList<>();
+            List<DefaultMutableTreeNode> toRemove = new ArrayList<>();
+            DefaultMutableTreeNode node = (DefaultMutableTreeNode)
+                    paths[0].getLastPathComponent();
+            DefaultMutableTreeNode copy = copy(node);
+            copies.add(copy);
+            toRemove.add(node);
+            for (int i = 1; i < paths.length; i++) {
+                DefaultMutableTreeNode next = (DefaultMutableTreeNode) paths[i]
+                        .getLastPathComponent();
+                // Do not allow higher level nodes to be added to list.
+                if (next.getLevel() < node.getLevel()) {
+                    break;
+                } else if (next.getLevel() > node.getLevel()) {  // child node
+                    copy.add(copy(next));
+                    // node already contains child
+                } else {                                        // sibling
+                    copies.add(copy(next));
+                    toRemove.add(next);
+                }
+            }
+            DefaultMutableTreeNode[] nodes = copies
+                    .toArray(new DefaultMutableTreeNode[copies.size()]);
+            nodesToRemove = toRemove.toArray(
+                    new DefaultMutableTreeNode[toRemove.size()]);
+            return new NodesTransferable(nodes);
+        }
+        return null;
+    }
+
+    /**
+     * Defensive copy used in createTransferable.
+     */
+    private DefaultMutableTreeNode copy(TreeNode node) {
+        return new DefaultMutableTreeNode(node);
+    }
+
+    @Override
+    protected void exportDone(JComponent source, Transferable data, int action) {
+        if ((action & MOVE) == MOVE) {
+            JTree tree = (JTree) source;
+            DefaultTreeModel model = (DefaultTreeModel) tree.getModel();
+            // Remove nodes saved in nodesToRemove in createTransferable.
+            for (DefaultMutableTreeNode nodesToRemove1 : nodesToRemove) {
+                model.removeNodeFromParent(nodesToRemove1);
+            }
+        }
+    }
+
+    @Override
+    public int getSourceActions(JComponent c) {
+        return COPY_OR_MOVE;
+    }
+
+    @Override
+    public boolean importData(TransferHandler.TransferSupport support) {
+        if (!canImport(support)) {
+            return false;
+        }
+        // Extract transfer data.
+        DefaultMutableTreeNode[] nodes = null;
+        try {
+            Transferable t = support.getTransferable();
+            nodes = (DefaultMutableTreeNode[]) t.getTransferData(nodesFlavor);
+        } catch (UnsupportedFlavorException ufe) {
+            System.out.println("UnsupportedFlavor: " + ufe.getMessage());
+        } catch (java.io.IOException ioe) {
+            System.out.println("I/O error: " + ioe.getMessage());
+        }
+        // Get drop location info.
+        JTree.DropLocation dl = (JTree.DropLocation) support.getDropLocation();
+        int childIndex = dl.getChildIndex();
+        TreePath dest = dl.getPath();
+        DefaultMutableTreeNode parent = (DefaultMutableTreeNode)
+                dest.getLastPathComponent();
+        JTree tree = (JTree) support.getComponent();
+        DefaultTreeModel model = (DefaultTreeModel) tree.getModel();
+        // Configure for drop mode.
+        int index = childIndex;    // DropMode.INSERT
+        if (childIndex == -1) {     // DropMode.ON
+            index = parent.getChildCount();
+        }
+        // Add data to model.
+        for (DefaultMutableTreeNode node : nodes) {
+            model.insertNodeInto(node, parent, index++);
+        }
+        return true;
+    }
+
+    @Override
+    public String toString() {
+        return getClass().getName();
+    }
+
+    public class NodesTransferable implements Transferable {
+        DefaultMutableTreeNode[] nodes;
+
+        public NodesTransferable(DefaultMutableTreeNode[] nodes) {
+            this.nodes = nodes;
+        }
+
+        @Override
+        public Object getTransferData(DataFlavor flavor)
+                throws UnsupportedFlavorException {
+            if (!isDataFlavorSupported(flavor)) {
+                throw new UnsupportedFlavorException(flavor);
+            }
+            return nodes;
+        }
+
+        @Override
+        public DataFlavor[] getTransferDataFlavors() {
+            return flavors;
+        }
+
+        @Override
+        public boolean isDataFlavorSupported(DataFlavor flavor) {
+            return nodesFlavor.equals(flavor);
+        }
+    }
+}
\ No newline at end of file
--- a/jdk/test/javax/swing/RepaintManager/6608456/bug6608456.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/javax/swing/RepaintManager/6608456/bug6608456.java	Wed Jul 05 20:42:36 2017 +0200
@@ -25,6 +25,7 @@
  *
  * @bug 6608456
  * @author Igor Kushnirskiy
+ * @modules java.desktop/com.sun.java.swing
  * @summary tests if delegate RepaintManager gets invoked.
  */
 
--- a/jdk/test/javax/swing/RepaintManager/DisplayListenerLeak/DisplayListenerLeak.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/javax/swing/RepaintManager/DisplayListenerLeak/DisplayListenerLeak.java	Wed Jul 05 20:42:36 2017 +0200
@@ -34,6 +34,7 @@
 /**
  * @test
  * @bug 8041654
+ * @modules java.desktop/sun.java2d
  * @run main/othervm -Xmx80m DisplayListenerLeak
  */
 public final class DisplayListenerLeak {
@@ -79,4 +80,4 @@
             throw new RuntimeException();
         }
     }
-}
\ No newline at end of file
+}
--- a/jdk/test/javax/swing/plaf/basic/6866751/bug6866751.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/javax/swing/plaf/basic/6866751/bug6866751.java	Wed Jul 05 20:42:36 2017 +0200
@@ -27,6 +27,7 @@
    @author Semyon Sadetsky
   */
 import javax.swing.*;
+import java.awt.*;
 
 public class bug6866751 {
     private static JFrame frame;
@@ -54,8 +55,10 @@
                                         caretX + 1);
                     }
                     area.putClientProperty("caretWidth", 10);
+                    frame.pack();
                 }
             });
+            new Robot().waitForIdle();
             SwingUtilities.invokeAndWait(new Runnable() {
                 public void run() {
                     int width = area.getWidth();
--- a/jdk/test/javax/xml/crypto/dsig/GenerationTests.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/javax/xml/crypto/dsig/GenerationTests.java	Wed Jul 05 20:42:36 2017 +0200
@@ -29,22 +29,30 @@
  * @modules java.base/sun.security.util
  *          java.base/sun.security.x509
  *          java.xml.crypto/org.jcp.xml.dsig.internal.dom
+ *          jdk.httpserver/com.sun.net.httpserver
  * @compile -XDignore.symbol.file KeySelectors.java SignatureValidator.java
  *     X509KeySelector.java GenerationTests.java
  * @run main/othervm GenerationTests
  * @author Sean Mullan
  */
 
+import com.sun.net.httpserver.HttpExchange;
+import com.sun.net.httpserver.HttpHandler;
+import com.sun.net.httpserver.HttpServer;
 import java.io.*;
 import java.math.BigInteger;
+import java.net.InetSocketAddress;
 import java.security.Key;
 import java.security.KeyFactory;
+import java.security.KeyPair;
+import java.security.KeyPairGenerator;
 import java.security.KeyStore;
+import java.security.NoSuchAlgorithmException;
 import java.security.PrivateKey;
 import java.security.PublicKey;
+import java.security.SecureRandom;
 import java.security.cert.Certificate;
 import java.security.cert.CertificateFactory;
-import java.security.cert.X509Certificate;
 import java.security.cert.X509CRL;
 import java.security.spec.KeySpec;
 import java.security.spec.DSAPrivateKeySpec;
@@ -59,10 +67,10 @@
 import java.security.spec.RSAPrivateKeySpec;
 import java.security.spec.RSAPublicKeySpec;
 import java.util.*;
+import javax.crypto.KeyGenerator;
 import javax.crypto.SecretKey;
 import javax.xml.XMLConstants;
 import javax.xml.parsers.*;
-import org.w3c.dom.*;
 import javax.xml.crypto.Data;
 import javax.xml.crypto.KeySelector;
 import javax.xml.crypto.OctetStreamData;
@@ -80,6 +88,7 @@
 import javax.xml.transform.*;
 import javax.xml.transform.dom.DOMSource;
 import javax.xml.transform.stream.StreamResult;
+import org.w3c.dom.*;
 
 /**
  * Test that recreates merlin-xmldsig-twenty-three test vectors but with
@@ -123,6 +132,73 @@
     private final static String DSA_SHA256 =
         "http://www.w3.org/2009/xmldsig11#dsa-sha256";
 
+    private static final String BOGUS = "bogus";
+
+    private static final  String xslt = ""
+          + "<xsl:stylesheet xmlns:xsl='http://www.w3.org/1999/XSL/Transform'\n"
+          + "            xmlns='http://www.w3.org/TR/xhtml1/strict' \n"
+          + "            exclude-result-prefixes='foo' \n"
+          + "            version='1.0'>\n"
+          + "  <xsl:output encoding='UTF-8' \n"
+          + "           indent='no' \n"
+          + "           method='xml' />\n"
+          + "  <xsl:template match='/'>\n"
+          + "    <html>\n"
+          + "   <head>\n"
+          + "    <title>Notaries</title>\n"
+          + "   </head>\n"
+          + "   <body>\n"
+          + "    <table>\n"
+          + "      <xsl:for-each select='Notaries/Notary'>\n"
+          + "           <tr>\n"
+          + "           <th>\n"
+          + "            <xsl:value-of select='@name' />\n"
+          + "           </th>\n"
+          + "           </tr>\n"
+          + "      </xsl:for-each>\n"
+          + "    </table>\n"
+          + "   </body>\n"
+          + "    </html>\n"
+          + "  </xsl:template>\n"
+          + "</xsl:stylesheet>\n";
+
+    private static final String[] canonicalizationMethods = new String[] {
+        CanonicalizationMethod.EXCLUSIVE,
+        CanonicalizationMethod.EXCLUSIVE_WITH_COMMENTS,
+        CanonicalizationMethod.INCLUSIVE,
+        CanonicalizationMethod.INCLUSIVE_WITH_COMMENTS
+    };
+
+    private static final String[] xml_transforms = new String[] {
+        Transform.XSLT,
+        Transform.XPATH,
+        Transform.XPATH2,
+        CanonicalizationMethod.EXCLUSIVE,
+        CanonicalizationMethod.EXCLUSIVE_WITH_COMMENTS,
+        CanonicalizationMethod.INCLUSIVE,
+        CanonicalizationMethod.INCLUSIVE_WITH_COMMENTS,
+    };
+
+    private static final String[] non_xml_transforms = new String[] {
+        null, Transform.BASE64
+    };
+
+    private static final String[] signatureMethods = new String[] {
+        SignatureMethod.DSA_SHA1,
+        SignatureMethod.RSA_SHA1,
+        SignatureMethod.HMAC_SHA1
+    };
+
+    private static enum Content {
+        Xml, Text, Base64, NotExisitng
+    }
+
+    private static enum KeyInfoType {
+        KeyValue, x509data, KeyName
+    }
+
+    private static boolean result = true;
+
     public static void main(String args[]) throws Exception {
         setup();
         test_create_signature_enveloped_dsa(1024);
@@ -156,6 +232,97 @@
         test_create_signature_reference_dependency();
         test_create_signature_with_attr_in_no_namespace();
         test_create_signature_with_empty_id();
+
+        // run tests for detached signatures with local http server
+        try (Http server = Http.startServer()) {
+            server.start();
+
+            // tests for XML documents
+            Arrays.stream(canonicalizationMethods).forEach(c ->
+                Arrays.stream(signatureMethods).forEach(s ->
+                    Arrays.stream(xml_transforms).forEach(t ->
+                        Arrays.stream(KeyInfoType.values()).forEach(k -> {
+                            test_create_detached_signature(c, s, t, k,
+                                    Content.Xml, server.getPort(), false, null);
+                        }))));
+
+            // tests for text data with no transform
+            Arrays.stream(canonicalizationMethods).forEach(c ->
+                Arrays.stream(signatureMethods).forEach(s ->
+                    Arrays.stream(KeyInfoType.values()).forEach(k -> {
+                        test_create_detached_signature(c, s, null, k,
+                                Content.Text, server.getPort(), false, null);
+                    })));
+
+            // tests for base64 data
+            Arrays.stream(canonicalizationMethods).forEach(c ->
+                Arrays.stream(signatureMethods).forEach(s ->
+                    Arrays.stream(non_xml_transforms).forEach(t ->
+                        Arrays.stream(KeyInfoType.values()).forEach(k -> {
+                            test_create_detached_signature(c, s, t, k,
+                                    Content.Base64, server.getPort(),
+                                    false, null);
+                        }))));
+
+            // negative tests
+
+            // unknown CanonicalizationMethod
+            test_create_detached_signature(
+                    CanonicalizationMethod.EXCLUSIVE + BOGUS,
+                    SignatureMethod.DSA_SHA1,
+                    CanonicalizationMethod.INCLUSIVE,
+                    KeyInfoType.KeyName,
+                    Content.Xml,
+                    server.getPort(),
+                    true,
+                    NoSuchAlgorithmException.class);
+
+            // unknown SignatureMethod
+            test_create_detached_signature(
+                    CanonicalizationMethod.EXCLUSIVE,
+                    SignatureMethod.DSA_SHA1 + BOGUS,
+                    CanonicalizationMethod.INCLUSIVE,
+                    KeyInfoType.KeyName, Content.Xml,
+                    server.getPort(),
+                    true,
+                    NoSuchAlgorithmException.class);
+
+            // unknown Transform
+            test_create_detached_signature(
+                    CanonicalizationMethod.EXCLUSIVE,
+                    SignatureMethod.DSA_SHA1,
+                    CanonicalizationMethod.INCLUSIVE + BOGUS,
+                    KeyInfoType.KeyName, Content.Xml,
+                    server.getPort(),
+                    true,
+                    NoSuchAlgorithmException.class);
+
+            // no source document
+            test_create_detached_signature(
+                    CanonicalizationMethod.EXCLUSIVE,
+                    SignatureMethod.DSA_SHA1,
+                    CanonicalizationMethod.INCLUSIVE,
+                    KeyInfoType.KeyName,
+                    Content.NotExisitng,
+                    server.getPort(),
+                    true,
+                    XMLSignatureException.class);
+
+            // wrong transform for text data
+            test_create_detached_signature(
+                    CanonicalizationMethod.EXCLUSIVE,
+                    SignatureMethod.DSA_SHA1,
+                    CanonicalizationMethod.INCLUSIVE,
+                    KeyInfoType.KeyName,
+                    Content.Text,
+                    server.getPort(),
+                    true,
+                    XMLSignatureException.class);
+        }
+
+        if (!result) {
+            throw new RuntimeException("At least one test case failed");
+        }
     }
 
     private static void setup() throws Exception {
@@ -761,33 +928,6 @@
 
         // Manifest Reference 3
         List<Transform> manTrans = new ArrayList<>();
-        String xslt = ""
-          + "<xsl:stylesheet xmlns:xsl='http://www.w3.org/1999/XSL/Transform'\n"
-          + "            xmlns='http://www.w3.org/TR/xhtml1/strict' \n"
-          + "            exclude-result-prefixes='foo' \n"
-          + "            version='1.0'>\n"
-          + "  <xsl:output encoding='UTF-8' \n"
-          + "           indent='no' \n"
-          + "           method='xml' />\n"
-          + "  <xsl:template match='/'>\n"
-          + "    <html>\n"
-          + "   <head>\n"
-          + "    <title>Notaries</title>\n"
-          + "   </head>\n"
-          + "   <body>\n"
-          + "    <table>\n"
-          + "      <xsl:for-each select='Notaries/Notary'>\n"
-          + "           <tr>\n"
-          + "           <th>\n"
-          + "            <xsl:value-of select='@name' />\n"
-          + "           </th>\n"
-          + "           </tr>\n"
-          + "      </xsl:for-each>\n"
-          + "    </table>\n"
-          + "   </body>\n"
-          + "    </html>\n"
-          + "  </xsl:template>\n"
-          + "</xsl:stylesheet>\n";
         Document docxslt = db.parse(new ByteArrayInputStream(xslt.getBytes()));
         Node xslElem = docxslt.getDocumentElement();
 
@@ -1166,6 +1306,200 @@
         System.out.println();
     }
 
+    static void test_create_detached_signature(String canonicalizationMethod,
+            String signatureMethod, String transform, KeyInfoType keyInfo,
+            Content contentType, int port, boolean expectedFailure,
+            Class expectedException) {
+
+        final String digestMethod = DigestMethod.SHA1;
+        System.out.println("Test detached signature:");
+        System.out.println("    Canonicalization method: "
+                + canonicalizationMethod);
+        System.out.println("    Signature method: " + signatureMethod);
+        System.out.println("    Transform: " + transform);
+        System.out.println("    Digest method: " + digestMethod);
+        System.out.println("    KeyInfoType: " + keyInfo);
+        System.out.println("    Content type: " + contentType);
+        System.out.println("    Expected failure: "
+                + (expectedFailure ? "yes" : "no"));
+        System.out.println("    Expected exception: "
+                + (expectedException == null ?
+                        "no" : expectedException.getName()));
+
+        try {
+            boolean success = test_create_detached_signature(
+                    canonicalizationMethod,
+                    signatureMethod,
+                    digestMethod,
+                    transform,
+                    keyInfo,
+                    contentType,
+                    port);
+
+            if (success && expectedFailure) {
+                System.out.println("Signature validation unexpectedly passed");
+                result = false;
+            } else if (!success && !expectedFailure) {
+                System.out.println("Signature validation unexpectedly failed");
+                result = false;
+            } else if (expectedException != null) {
+                System.out.println("Expected " + expectedException
+                        + " not thrown");
+                result = false;
+            }
+        } catch (Exception e) {
+            if (expectedException == null
+                    || !e.getClass().isAssignableFrom(expectedException)) {
+                System.out.println("Unexpected exception: " + e);
+                e.printStackTrace(System.out);
+                result = false;
+            } else {
+                System.out.println("Expected exception: " + e);
+            }
+        }
+
+        System.out.println("Test case passed");
+    }
+
+    static boolean test_create_detached_signature(String canonicalizationMethod,
+            String signatureMethod, String digestMethod, String transform,
+            KeyInfoType keyInfo, Content contentType, int port)
+            throws Exception {
+
+        System.out.print("Sign ...");
+
+        DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
+        dbf.setNamespaceAware(true);
+        dbf.setValidating(false);
+
+        // Create SignedInfo
+        DigestMethod dm = fac.newDigestMethod(digestMethod, null);
+
+        List transformList = null;
+        if (transform != null) {
+            TransformParameterSpec params = null;
+            switch (transform) {
+                case Transform.XPATH:
+                    params = new XPathFilterParameterSpec("//.");
+                    break;
+                case Transform.XPATH2:
+                    params = new XPathFilter2ParameterSpec(
+                            Collections.singletonList(new XPathType("//.",
+                                    XPathType.Filter.INTERSECT)));
+                    break;
+                case Transform.XSLT:
+                    Element element = dbf.newDocumentBuilder()
+                            .parse(new ByteArrayInputStream(xslt.getBytes()))
+                            .getDocumentElement();
+                    DOMStructure stylesheet = new DOMStructure(element);
+                    params = new XSLTTransformParameterSpec(stylesheet);
+                    break;
+            }
+            transformList = Collections.singletonList(fac.newTransform(
+                    transform, params));
+        }
+
+        String url = String.format("http://localhost:%d/%s", port, contentType);
+        List refs = Collections.singletonList(fac.newReference(url, dm,
+                transformList, null, null));
+
+        CanonicalizationMethod cm = fac.newCanonicalizationMethod(
+                canonicalizationMethod, (C14NMethodParameterSpec) null);
+
+        SignatureMethod sm = fac.newSignatureMethod(signatureMethod, null);
+
+        Key signingKey;
+        Key validationKey;
+        switch (signatureMethod) {
+            case SignatureMethod.DSA_SHA1:
+            case SignatureMethod.RSA_SHA1:
+                KeyPair kp = generateKeyPair(sm);
+                validationKey = kp.getPublic();
+                signingKey = kp.getPrivate();
+                break;
+            case SignatureMethod.HMAC_SHA1:
+                KeyGenerator kg = KeyGenerator.getInstance("HmacSHA1");
+                signingKey = kg.generateKey();
+                validationKey = signingKey;
+                break;
+            default:
+                throw new RuntimeException("Unsupported signature algorithm");
+        }
+
+        SignedInfo si = fac.newSignedInfo(cm, sm, refs, null);
+
+        // Create KeyInfo
+        KeyInfoFactory kif = fac.getKeyInfoFactory();
+        List list = null;
+        if (keyInfo == KeyInfoType.KeyValue) {
+            if (validationKey instanceof PublicKey) {
+                KeyValue kv = kif.newKeyValue((PublicKey) validationKey);
+                list = Collections.singletonList(kv);
+            }
+        } else if (keyInfo == KeyInfoType.x509data) {
+            list = Collections.singletonList(
+                    kif.newX509Data(Collections.singletonList("cn=Test")));
+        } else if (keyInfo == KeyInfoType.KeyName) {
+            list = Collections.singletonList(kif.newKeyName("Test"));
+        } else {
+            throw new RuntimeException("Unexpected KeyInfo: " + keyInfo);
+        }
+        KeyInfo ki = list != null ? kif.newKeyInfo(list) : null;
+
+        // Create an empty doc for detached signature
+        Document doc = dbf.newDocumentBuilder().newDocument();
+        DOMSignContext xsc = new DOMSignContext(signingKey, doc);
+
+        // Generate signature
+        XMLSignature signature = fac.newXMLSignature(si, ki);
+        signature.sign(xsc);
+
+        // Save signature
+        String signatureString;
+        try (StringWriter writer = new StringWriter()) {
+            TransformerFactory tf = TransformerFactory.newInstance();
+            Transformer trans = tf.newTransformer();
+            Node parent = xsc.getParent();
+            trans.transform(new DOMSource(parent), new StreamResult(writer));
+            signatureString = writer.toString();
+        }
+
+        System.out.print("Validate ... ");
+        try (ByteArrayInputStream bis = new ByteArrayInputStream(
+                signatureString.getBytes())) {
+            doc = dbf.newDocumentBuilder().parse(bis);
+        }
+
+        NodeList nodeLst = doc.getElementsByTagName("Signature");
+        Node node = nodeLst.item(0);
+        if (node == null) {
+            throw new RuntimeException("Couldn't find Signature element");
+        }
+        if (!(node instanceof Element)) {
+            throw new RuntimeException("Unexpected node type");
+        }
+        Element sig = (Element) node;
+
+        // Validate signature
+        DOMValidateContext vc = new DOMValidateContext(validationKey, sig);
+        vc.setProperty("org.jcp.xml.dsig.secureValidation", Boolean.FALSE);
+        signature = fac.unmarshalXMLSignature(vc);
+
+        boolean success = signature.validate(vc);
+        if (!success) {
+            System.out.println("Core signature validation failed");
+            return false;
+        }
+
+        success = signature.getSignatureValue().validate(vc);
+        if (!success) {
+            System.out.println("Cryptographic validation of signature failed");
+            return false;
+        }
+
+        return true;
+    }
+
     private static final String DSA_Y =
         "070662842167565771936588335128634396171789331656318483584455493822" +
         "400811200853331373030669235424928346190274044631949560438023934623" +
@@ -1390,6 +1724,25 @@
         };
     }
 
+    static KeyPair generateKeyPair(SignatureMethod sm)
+            throws NoSuchAlgorithmException {
+        KeyPairGenerator keygen;
+        switch (sm.getAlgorithm()) {
+            case SignatureMethod.DSA_SHA1:
+                keygen = KeyPairGenerator.getInstance("DSA");
+                break;
+            case SignatureMethod.RSA_SHA1:
+                keygen = KeyPairGenerator.getInstance("RSA");
+                break;
+            default:
+                throw new RuntimeException("Unsupported signature algorithm");
+        }
+
+        SecureRandom random = new SecureRandom();
+        keygen.initialize(1024, random);
+        return keygen.generateKeyPair();
+    }
+
     /**
      * This URIDereferencer returns locally cached copies of http content to
      * avoid test failures due to network glitches, etc.
@@ -1416,4 +1769,82 @@
             return defaultUd.dereference(ref, ctx);
         }
     }
+
+    // local http server
+    static class Http implements HttpHandler, AutoCloseable {
+
+        private final HttpServer server;
+
+        private Http(HttpServer server) {
+            this.server = server;
+        }
+
+        static Http startServer() throws IOException {
+            HttpServer server = HttpServer.create(new InetSocketAddress(0), 0);
+            return new Http(server);
+        }
+
+        void start() {
+            server.createContext("/", this);
+            server.start();
+        }
+
+        void stop() {
+            server.stop(0);
+        }
+
+        int getPort() {
+            return server.getAddress().getPort();
+        }
+
+        @Override
+        public void handle(HttpExchange t) throws IOException {
+            try {
+                String type;
+                String path = t.getRequestURI().getPath();
+                if (path.startsWith("/")) {
+                    type = path.substring(1);
+                } else {
+                    type = path;
+                }
+
+                String contentTypeHeader = "";
+                byte[] output = new byte[] {};
+                int code = 200;
+                Content testContentType = Content.valueOf(type);
+                switch (testContentType) {
+                    case Base64:
+                        contentTypeHeader = "application/octet-stream";
+                        output = "VGVzdA==".getBytes();
+                        break;
+                    case Text:
+                        contentTypeHeader = "text/plain";
+                        output = "Text".getBytes();
+                        break;
+                    case Xml:
+                        contentTypeHeader = "application/xml";
+                        output = "<tag>test</tag>".getBytes();
+                        break;
+                    case NotExisitng:
+                        code = 404;
+                        break;
+                    default:
+                        throw new IOException("Unknown test content type");
+                }
+
+                t.getResponseHeaders().set("Content-Type", contentTypeHeader);
+                t.sendResponseHeaders(code, output.length);
+                t.getResponseBody().write(output);
+            } catch (IOException e) {
+                System.out.println("Exception: " + e);
+                t.sendResponseHeaders(500, 0);
+            }
+            t.close();
+        }
+
+        @Override
+        public void close() {
+            stop();
+        }
+    }
 }
--- a/jdk/test/jdk/internal/jimage/VerifyJimage.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/jdk/internal/jimage/VerifyJimage.java	Wed Jul 05 20:42:36 2017 +0200
@@ -217,7 +217,12 @@
         }
 
         int entries() {
-            return getHeader().getLocationCount();
+            try {
+                return getHeader().getTableLength();
+            } catch (IOException ex) {
+                failed.add(imageName() + ": can't access header");
+                return 0;
+            }
         }
 
         void compare(String entry, Path p) {
--- a/jdk/test/jdk/internal/jrtfs/Basic.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/jdk/internal/jrtfs/Basic.java	Wed Jul 05 20:42:36 2017 +0200
@@ -98,8 +98,8 @@
     @DataProvider(name = "knownClassFiles")
     private Object[][] knownClassFiles() {
         return new Object[][] {
-            { "/java.base/java/lang/Object.class" },
-            { "java.base/java/lang/Object.class" },
+            { "/modules/java.base/java/lang/Object.class" },
+            { "modules/java.base/java/lang/Object.class" },
         };
     }
 
@@ -126,14 +126,14 @@
             { "./"                    },
             { "/."                    },
             { "/./"                   },
-            { "/java.base/.."         },
-            { "/java.base/../"        },
-            { "/java.base/../."       },
-            { "/java.base"            },
-            { "/java.base/java/lang"  },
-            { "java.base/java/lang"   },
-            { "/java.base/java/lang/" },
-            { "java.base/java/lang/"  }
+            { "/modules/java.base/.."         },
+            { "/modules/java.base/../"        },
+            { "/modules/java.base/../."       },
+            { "/modules/java.base"            },
+            { "/modules/java.base/java/lang"  },
+            { "modules/java.base/java/lang"   },
+            { "/modules/java.base/java/lang/" },
+            { "modules/java.base/java/lang/"  }
         };
     }
 
@@ -208,23 +208,24 @@
     private Object[][] pathPrefixes() {
         return new Object[][] {
             { "/"                       },
-            { "java.base/java/lang"     },
-            { "./java.base/java/lang"   },
-            { "/java.base/java/lang"    },
-            { "/./java.base/java/lang"  },
-            { "java.base/java/lang/"    },
-            { "./java.base/java/lang/"  },
-            { "/./java.base/java/lang/" },
+            { "modules/java.base/java/lang"     },
+            { "./modules/java.base/java/lang"   },
+            { "/modules/java.base/java/lang"    },
+            { "/./modules/java.base/java/lang"  },
+            { "modules/java.base/java/lang/"    },
+            { "./modules/java.base/java/lang/"  },
+            { "/./modules/java.base/java/lang/" },
         };
     }
 
-    @Test(dataProvider = "pathPrefixes")
+    // @Test(dataProvider = "pathPrefixes")
     public void testParentInDirList(String dir) throws Exception {
         FileSystem fs = FileSystems.getFileSystem(URI.create("jrt:/"));
         Path base = fs.getPath(dir);
         try (DirectoryStream<Path> stream = Files.newDirectoryStream(base)) {
             for (Path entry: stream) {
-                assertTrue( entry.getParent().equals(base) );
+                assertTrue( entry.getParent().equals(base),
+                    base.toString() + "-> " + entry.toString() );
             }
         }
     }
@@ -232,10 +233,10 @@
     @DataProvider(name = "dirStreamStringFilterData")
     private Object[][] dirStreamStringFilterData() {
         return new Object[][] {
-            { "/java.base/java/lang", "/reflect"      },
-            { "/java.base/java/lang", "/Object.class" },
-            { "/java.base/java/util", "/stream"       },
-            { "/java.base/java/util", "/List.class"   },
+            { "/modules/java.base/java/lang", "/reflect"      },
+            { "/modules/java.base/java/lang", "/Object.class" },
+            { "/modules/java.base/java/util", "/stream"       },
+            { "/modules/java.base/java/util", "/List.class"   },
         };
     }
 
@@ -274,7 +275,7 @@
               "isDirectory"
             },
             {
-              "/java.base/java/lang",
+              "/modules/java.base/java/lang",
               (DirectoryStream.Filter<Path>)(Files::isRegularFile),
               "isFile"
             }
@@ -322,7 +323,7 @@
         FileSystem fs = FileSystems.getFileSystem(URI.create("jrt:/"));
         // This test assumes at least there are two elements in "java/lang"
         // package with any filter passed. don't change to different path here!
-        Path dir = fs.getPath("/java.base/java/lang");
+        Path dir = fs.getPath("/modules/java.base/java/lang");
         try (DirectoryStream<Path> stream = Files.newDirectoryStream(dir, filter)) {
             Iterator<Path> itr = stream.iterator();
             itr.hasNext();
@@ -379,9 +380,9 @@
             { "/META-INF" },
             { "/META-INF/services" },
             { "/META-INF/services/java.nio.file.spi.FileSystemProvider" },
-            { "/java.base/packages.offsets" },
-            { "/java.instrument/packages.offsets" },
-            { "/jdk.zipfs/packages.offsets" },
+            { "/modules/java.base/packages.offsets" },
+            { "/modules/java.instrument/packages.offsets" },
+            { "/modules/jdk.zipfs/packages.offsets" },
             { "/java/lang" },
             { "/java/util" },
         };
@@ -396,20 +397,20 @@
     @DataProvider(name = "pathGlobPatterns")
     private Object[][] pathGlobPatterns() {
         return new Object[][] {
-            { "/*", "/java.base", true },
-            { "/*", "/java.base/java", false },
-            { "/j*", "/java.base", true },
-            { "/J*", "/java.base", false },
-            { "**.class", "/java.base/java/lang/Object.class", true },
-            { "**.java", "/java.base/java/lang/Object.class", false },
-            { "**java/*", "/java.base/java/lang", true },
-            { "**java/lang/ref*", "/java.base/java/lang/reflect", true },
-            { "**java/lang/ref*", "/java.base/java/lang/ref", true },
-            { "**java/lang/ref?", "/java.base/java/lang/ref", false },
-            { "**java/lang/{ref,refl*}", "/java.base/java/lang/ref", true },
-            { "**java/lang/{ref,refl*}", "/java.base/java/lang/reflect", true },
-            { "**java/[a-u]?*/*.class", "/java.base/java/util/Map.class", true },
-            { "**java/util/[a-z]*.class", "/java.base/java/util/TreeMap.class", false },
+            { "/modules/*", "/modules/java.base", true },
+            { "/modules/*", "/modules/java.base/java", false },
+            { "/modules/j*", "/modules/java.base", true },
+            { "/modules/J*", "/modules/java.base", false },
+            { "**.class", "/modules/java.base/java/lang/Object.class", true },
+            { "**.java", "/modules/java.base/java/lang/Object.class", false },
+            { "**java/*", "/modules/java.base/java/lang", true },
+            { "**java/lang/ref*", "/modules/java.base/java/lang/reflect", true },
+            { "**java/lang/ref*", "/modules/java.base/java/lang/ref", true },
+            { "**java/lang/ref?", "/modules/java.base/java/lang/ref", false },
+            { "**java/lang/{ref,refl*}", "/modules/java.base/java/lang/ref", true },
+            { "**java/lang/{ref,refl*}", "/modules/java.base/java/lang/reflect", true },
+            { "**java/[a-u]?*/*.class", "/modules/java.base/java/util/Map.class", true },
+            { "**java/util/[a-z]*.class", "/modules/java.base/java/util/TreeMap.class", false },
         };
     }
 
@@ -428,20 +429,20 @@
     @DataProvider(name = "pathRegexPatterns")
     private Object[][] pathRegexPatterns() {
         return new Object[][] {
-            { "/.*", "/java.base", true },
-            { "/[^/]*", "/java.base/java", false },
-            { "/j.*", "/java.base", true },
-            { "/J.*", "/java.base", false },
-            { ".*\\.class", "/java.base/java/lang/Object.class", true },
-            { ".*\\.java", "/java.base/java/lang/Object.class", false },
-            { ".*java/.*", "/java.base/java/lang", true },
-            { ".*java/lang/ref.*", "/java.base/java/lang/reflect", true },
-            { ".*java/lang/ref.*", "/java.base/java/lang/ref", true },
-            { ".*/java/lang/ref.+", "/java.base/java/lang/ref", false },
-            { ".*/java/lang/(ref|refl.*)", "/java.base/java/lang/ref", true },
-            { ".*/java/lang/(ref|refl.*)", "/java.base/java/lang/reflect", true },
-            { ".*/java/[a-u]?.*/.*\\.class", "/java.base/java/util/Map.class", true },
-            { ".*/java/util/[a-z]*\\.class", "/java.base/java/util/TreeMap.class", false },
+            { "/modules/.*", "/modules/java.base", true },
+            { "/modules/[^/]*", "/modules/java.base/java", false },
+            { "/modules/j.*", "/modules/java.base", true },
+            { "/modules/J.*", "/modules/java.base", false },
+            { ".*\\.class", "/modules/java.base/java/lang/Object.class", true },
+            { ".*\\.java", "/modules/java.base/java/lang/Object.class", false },
+            { ".*java/.*", "/modules/java.base/java/lang", true },
+            { ".*java/lang/ref.*", "/modules/java.base/java/lang/reflect", true },
+            { ".*java/lang/ref.*", "/modules/java.base/java/lang/ref", true },
+            { ".*/java/lang/ref.+", "/modules/java.base/java/lang/ref", false },
+            { ".*/java/lang/(ref|refl.*)", "/modules/java.base/java/lang/ref", true },
+            { ".*/java/lang/(ref|refl.*)", "/modules/java.base/java/lang/reflect", true },
+            { ".*/java/[a-u]?.*/.*\\.class", "/modules/java.base/java/util/Map.class", true },
+            { ".*/java/util/[a-z]*\\.class", "/modules/java.base/java/util/TreeMap.class", false },
         };
     }
 
@@ -456,4 +457,159 @@
             p + (expectMatch? " should match " : " should not match ") +
             pattern);
     }
+
+    @Test
+    public void testPackagesAndModules() throws Exception {
+        FileSystem fs = FileSystems.getFileSystem(URI.create("jrt:/"));
+        assertTrue(Files.isDirectory(fs.getPath("/packages")));
+        assertTrue(Files.isDirectory(fs.getPath("/modules")));
+    }
+
+    @DataProvider(name = "packagesSubDirs")
+    private Object[][] packagesSubDirs() {
+        return new Object[][] {
+            { "java.lang" },
+            { "java.util" },
+            { "java.nio"  },
+            { "jdk.nashorn.api.scripting" }
+        };
+    }
+
+    @Test(dataProvider = "packagesSubDirs")
+    public void testPackagesSubDirs(String pkg) throws Exception {
+        FileSystem fs = FileSystems.getFileSystem(URI.create("jrt:/"));
+        assertTrue(Files.isDirectory(fs.getPath("/packages/" + pkg)),
+            pkg + " missing");
+    }
+
+    @DataProvider(name = "packagesLinks")
+    private Object[][] packagesLinks() {
+        return new Object[][] {
+            { "/packages/java.lang/java.base" },
+            { "/packages/java.lang/java.instrument" },
+            { "/packages/java/java.base" },
+            { "/packages/java/java.instrument" },
+            { "/packages/java/java.rmi"  },
+            { "/packages/java/java.sql"  },
+            { "/packages/javax/java.base"  },
+            { "/packages/javax/java.sql"  },
+            { "/packages/javax/java.xml"  },
+            { "/packages/javax/java.management"  },
+            { "/packages/java.util/java.base" },
+            { "/packages/jdk.nashorn.api.scripting/jdk.scripting.nashorn" },
+        };
+    }
+
+    @Test(dataProvider = "packagesLinks")
+    public void testPackagesLinks(String link) throws Exception {
+        FileSystem fs = FileSystems.getFileSystem(URI.create("jrt:/"));
+        Path path = fs.getPath(link);
+        assertTrue(Files.exists(path), link + " missing");
+        assertTrue(Files.isSymbolicLink(path), path + " is not a link");
+        path = Files.readSymbolicLink(path);
+        assertEquals(path.toString(), "/modules" + link.substring(link.lastIndexOf("/")));
+    }
+
+    @DataProvider(name = "modulesSubDirs")
+    private Object[][] modulesSubDirs() {
+        return new Object[][] {
+            { "java.base" },
+            { "java.sql" },
+            { "jdk.scripting.nashorn" },
+        };
+    }
+
+    @Test(dataProvider = "modulesSubDirs")
+    public void testModulesSubDirs(String module) throws Exception {
+        FileSystem fs = FileSystems.getFileSystem(URI.create("jrt:/"));
+        Path path = fs.getPath("/modules/" + module);
+        assertTrue(Files.isDirectory(path), module + " missing");
+        assertTrue(!Files.isSymbolicLink(path), path + " is a link");
+    }
+
+    @DataProvider(name="linkChases")
+    private Object[][] linkChases() {
+        return new Object[][] {
+            { "/modules/java.base/java/lang" },
+            { "/modules/java.base/java/util/Vector.class" },
+            { "/modules/jdk.scripting.nashorn/jdk/nashorn" },
+            { "/packages/java.lang/java.base/java/lang" },
+            { "/packages/java.util/java.base/java/util/Vector.class" },
+        };
+    }
+
+    @Test(dataProvider = "linkChases")
+    public void testLinkChases(String link) throws Exception {
+        FileSystem fs = FileSystems.getFileSystem(URI.create("jrt:/"));
+        Path path = fs.getPath(link);
+        assertTrue(Files.exists(path), link);
+    }
+
+    @Test
+    public void testSymlinkDirList() throws Exception {
+        FileSystem fs = FileSystems.getFileSystem(URI.create("jrt:/"));
+        Path path = fs.getPath("/packages/java.lang/java.base");
+        assertTrue(Files.isSymbolicLink(path));
+        assertTrue(Files.isDirectory(path));
+
+        boolean javaSeen = false, javaxSeen = false;
+        try (DirectoryStream<Path> stream = Files.newDirectoryStream(path)) {
+            for (Path p : stream) {
+                String str = p.toString();
+                if (str.endsWith("/java")) {
+                    javaSeen = true;
+                } else if (str.endsWith("javax")) {
+                    javaxSeen = true;
+                }
+            }
+        }
+        assertTrue(javaSeen);
+        assertTrue(javaxSeen);
+    }
+
+    @Test
+    public void testPackagesSubDirList() throws Exception {
+        FileSystem fs = FileSystems.getFileSystem(URI.create("jrt:/"));
+        String pathName = "/packages/javax.annotation";
+        Path path = fs.getPath(pathName);
+        boolean seenJavaCompiler = false, seenAnnotationsCommon = false;
+        try (DirectoryStream<Path> stream = Files.newDirectoryStream(path)) {
+            for (Path p : stream) {
+               String str = p.toString();
+               if (str.equals(pathName + "/java.compiler")) {
+                   seenJavaCompiler = true;
+               } else if (str.equals(pathName + "/java.annotations.common")) {
+                   seenAnnotationsCommon = true;
+               }
+            }
+        }
+        assertTrue(seenJavaCompiler);
+        assertTrue(seenAnnotationsCommon);
+    }
+
+    @Test
+    public void testRootDirList() throws Exception {
+        FileSystem fs = FileSystems.getFileSystem(URI.create("jrt:/"));
+        Path path = fs.getPath("/");
+        // check /packages and /modules are not repeated
+        // and seen once.
+        boolean packages = false, modules = false;
+        try (DirectoryStream<Path> stream = Files.newDirectoryStream(path)) {
+            for (Path p : stream) {
+                String str = p.toString();
+                switch (str) {
+                    case "/packages":
+                        assertFalse(packages, "/packages repeated");
+                        packages = true;
+                        break;
+                    case "/modules":
+                        assertFalse(modules, "/modules repeated");
+                        modules = true;
+                        break;
+                }
+            }
+        }
+        assertTrue(packages, "/packages missing in / list!");
+        assertTrue(modules, "/modules missing in / list!");
+    }
 }
--- a/jdk/test/jdk/internal/jrtfs/WithSecurityManager.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/jdk/internal/jrtfs/WithSecurityManager.java	Wed Jul 05 20:42:36 2017 +0200
@@ -55,7 +55,8 @@
             FileSystems.getFileSystem(URI.create("jrt:/"));
             if (!allow) throw new RuntimeException("access not expected");
         } catch (SecurityException se) {
-            if (allow) throw new RuntimeException("access expected");
+            if (allow)
+                throw se;
         }
 
         // check FileSystems.newFileSystem
@@ -63,7 +64,8 @@
             FileSystems.newFileSystem(URI.create("jrt:/"), null);
             if (!allow) throw new RuntimeException("access not expected");
         } catch (SecurityException se) {
-            if (allow) throw new RuntimeException("access expected");
+            if (allow)
+                throw se;
         }
 
         // check Paths.get
@@ -71,7 +73,8 @@
             Paths.get(URI.create("jrt:/java.base/java/lang/Object.class"));
             if (!allow) throw new RuntimeException("access not expected");
         } catch (SecurityException se) {
-            if (allow) throw new RuntimeException("access expected");
+            if (allow)
+                throw se;
         }
     }
 }
--- a/jdk/test/sun/java2d/SunGraphicsEnvironment/TestSGEuseAlternateFontforJALocales.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/sun/java2d/SunGraphicsEnvironment/TestSGEuseAlternateFontforJALocales.java	Wed Jul 05 20:42:36 2017 +0200
@@ -28,6 +28,7 @@
  * @summary verify the existence of the  method
  *           SunGraphicsEnvironment.useAlternateFontforJALocales
  *
+ * @modules java.desktop/sun.java2d
  * @run main/othervm TestSGEuseAlternateFontforJALocales
  * @run main/othervm -Dfile.encoding=windows-31j -Duser.language=ja -Duser.country=JA TestSGEuseAlternateFontforJALocales
  *
--- a/jdk/test/sun/management/jmxremote/bootstrap/RmiBootstrapTest.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/sun/management/jmxremote/bootstrap/RmiBootstrapTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 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
@@ -42,6 +42,8 @@
 
 import sun.management.AgentConfigurationError;
 
+import java.security.Security;
+
 /**
  * <p>This class implements unit test for RMI Bootstrap.
  * When called with no arguments main() looks in the directory indicated
@@ -123,6 +125,8 @@
             "com.sun.management.jmxremote.ssl.enabled.protocols";
         public static final String SSL_NEED_CLIENT_AUTH =
             "com.sun.management.jmxremote.ssl.need.client.auth";
+        public static final String SSL_CLIENT_ENABLED_CIPHER_SUITES =
+            "javax.rmi.ssl.client.enabledCipherSuites";
     }
 
     /**
@@ -424,7 +428,7 @@
     }
 
 
-    private void setSslProperties() {
+    private void setSslProperties(String clientEnabledCipherSuites) {
         final String defaultKeyStore =
             getDefaultStoreName(DefaultValues.KEYSTORE);
         final String defaultTrustStore =
@@ -455,6 +459,13 @@
         System.setProperty(PropertyNames.TRUSTSTORE_PASSWD,trustword);
         log.trace("setSslProperties",
                   PropertyNames.TRUSTSTORE_PASSWD+"="+trustword);
+
+        if (clientEnabledCipherSuites != null) {
+            System.setProperty("javax.rmi.ssl.client.enabledCipherSuites",
+                    clientEnabledCipherSuites);
+        } else {
+            System.clearProperty("javax.rmi.ssl.client.enabledCipherSuites");
+        }
     }
 
     private void checkSslConfiguration() {
@@ -507,7 +518,10 @@
                       PropertyNames.SSL_ENABLED_PROTOCOLS + "=" +
                       sslProtocols);
 
-            if (useSsl) setSslProperties();
+            if (useSsl) {
+                setSslProperties(props.getProperty(
+                        PropertyNames.SSL_CLIENT_ENABLED_CIPHER_SUITES));
+            }
         } catch (Exception x) {
             System.out.println("Failed to setup SSL configuration: " + x);
             log.debug("checkSslConfiguration",x);
@@ -839,6 +853,8 @@
      * exit(1) if the test fails.
      **/
     public static void main(String args[]) throws Exception {
+        Security.setProperty("jdk.tls.disabledAlgorithms", "");
+
         try {
             MAX_GET_FREE_PORT_TRIES = Integer.parseInt(System.getProperty("test.getfreeport.max.tries", "10"));
         } catch (NumberFormatException ex) {
--- a/jdk/test/sun/management/jmxremote/bootstrap/RmiSslBootstrapTest.sh	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/sun/management/jmxremote/bootstrap/RmiSslBootstrapTest.sh	Wed Jul 05 20:42:36 2017 +0200
@@ -29,7 +29,6 @@
 # @library /lib/testlibrary
 # @modules java.management/sun.management
 #          java.management/sun.management.jmxremote
-# @ignore 8077924
 # @build jdk.testlibrary.* TestLogger Utils RmiBootstrapTest
 # @run shell/timeout=300  RmiSslBootstrapTest.sh
 
--- a/jdk/test/sun/management/jmxremote/bootstrap/management_ssltest07_ok.properties.in	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/sun/management/jmxremote/bootstrap/management_ssltest07_ok.properties.in	Wed Jul 05 20:42:36 2017 +0200
@@ -2,3 +2,4 @@
 com.sun.management.jmxremote.ssl.enabled.protocols=SSLv2Hello,SSLv3,TLSv1
 com.sun.management.jmxremote.ssl.need.client.auth=true
 com.sun.management.jmxremote.authenticate=false
+javax.rmi.ssl.client.enabledCipherSuites=SSL_RSA_WITH_RC4_128_SHA,SSL_RSA_WITH_RC4_128_MD5
--- a/jdk/test/sun/management/jmxremote/bootstrap/management_ssltest11_ok.properties.in	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/sun/management/jmxremote/bootstrap/management_ssltest11_ok.properties.in	Wed Jul 05 20:42:36 2017 +0200
@@ -3,3 +3,4 @@
 com.sun.management.jmxremote.ssl.need.client.auth=true
 com.sun.management.jmxremote.ssl.config.file=@TEST-SRC@/jmxremote_ssltest11_ok.ssl
 com.sun.management.jmxremote.authenticate=false
+javax.rmi.ssl.client.enabledCipherSuites=SSL_RSA_WITH_RC4_128_SHA,SSL_RSA_WITH_RC4_128_MD5
--- a/jdk/test/sun/net/idn/NFS4StringPrep.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/sun/net/idn/NFS4StringPrep.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 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
@@ -32,7 +32,6 @@
 import java.io.UnsupportedEncodingException;
 import java.text.ParseException;
 
-import sun.text.normalizer.ICUData;
 import sun.net.idn.StringPrep;
 import sun.text.normalizer.UCharacterIterator;
 
--- a/jdk/test/sun/rmi/rmic/RMIGenerator/RmicDefault.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/sun/rmi/rmic/RMIGenerator/RmicDefault.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1999, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1999, 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
@@ -22,7 +22,7 @@
  */
 
 /* @test
- * @bug 4236543
+ * @bug 4236543 8129833
  * @summary rmic w/o -d should put class files in package directory
  * @author Dana Burns
  * @library ../../../../java/rmi/testlibrary
@@ -40,38 +40,47 @@
  */
 
 import java.io.File;
-import java.io.IOException;
 
 public class RmicDefault {
+    private static final String PKG_DIR = "packagedir";
+    private static final String[] remoteClasses = new String[] {
+        "RmicMeImpl", "AppletServer"
+    };
+
     public static void main(String args[]) throws Exception {
         String javahome = System.getProperty("java.home");
         String testclasses = System.getProperty("test.classes");
         String userDir = System.getProperty("user.dir");
+        String cmd = javahome + File.separator + "bin" + File.separator +
+            "javac -d " + testclasses + " " + System.getProperty("test.src") +
+            File.separator + PKG_DIR + File.separator;
 
-        Process javacProcess = Runtime.getRuntime().exec(
-            javahome + File.separator + "bin" + File.separator +
-            "javac -d " + testclasses + " " +
-            System.getProperty("test.src") + File.separator + "packagedir" +
-            File.separator + "RmicMeImpl.java");
+        for (String clz : remoteClasses) {
+            System.out.println("Working on class " + clz);
+            Process javacProcess = Runtime.getRuntime().exec(cmd + clz + ".java");
 
-        StreamPipe.plugTogether(javacProcess.getInputStream(), System.out);
-        StreamPipe.plugTogether(javacProcess.getErrorStream(), System.out);
+            StreamPipe.plugTogether(javacProcess.getInputStream(), System.out);
+            StreamPipe.plugTogether(javacProcess.getErrorStream(), System.out);
 
-        javacProcess.waitFor();
+            javacProcess.waitFor();
 
-        Process rmicProcess = Runtime.getRuntime().exec(
-            javahome + File.separator + "bin" + File.separator +
-            "rmic -classpath " + testclasses + " packagedir.RmicMeImpl");
+            Process rmicProcess = Runtime.getRuntime().exec(
+                javahome + File.separator + "bin" + File.separator +
+                "rmic -classpath " + testclasses + " " + PKG_DIR + "." + clz);
 
-        StreamPipe.plugTogether(rmicProcess.getInputStream(), System.out);
-        StreamPipe.plugTogether(rmicProcess.getErrorStream(), System.err);
+            StreamPipe.plugTogether(rmicProcess.getInputStream(), System.out);
+            StreamPipe.plugTogether(rmicProcess.getErrorStream(), System.err);
 
-        rmicProcess.waitFor();
+            rmicProcess.waitFor();
+            int exitCode = rmicProcess.exitValue();
+            if (rmicProcess.exitValue() != 0) {
+                throw new RuntimeException("Rmic failed. The exit code is " + exitCode);
+            }
 
-        File stub = new File(userDir + File.separator + "packagedir" +
-                             File.separator + "RmicMeImpl_Stub.class");
-        if (!stub.exists()) {
-            throw new RuntimeException("TEST FAILED: could not find stub");
+            File stub = new File(userDir + File.separator + PKG_DIR + File.separator + clz + "_Stub.class");
+            if (!stub.exists()) {
+                throw new RuntimeException("TEST FAILED: could not find stub");
+            }
         }
 
         System.err.println("TEST PASSED");
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/sun/rmi/rmic/RMIGenerator/packagedir/AppletServer.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,31 @@
+/*
+ * 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 packagedir;
+
+import java.awt.Panel;
+
+public class AppletServer extends java.applet.Applet implements java.rmi.Remote {
+    private static final long serialVersionUID = -5097805572269179958L;
+    Panel panel = null;
+}
--- a/jdk/test/sun/security/ec/TestEC.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/sun/security/ec/TestEC.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2009, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2009, 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
@@ -60,13 +60,10 @@
 public class TestEC {
 
     public static void main(String[] args) throws Exception {
-        // reset the security property to make sure that the algorithms
+        // reset security properties to make sure that the algorithms
         // and keys used in this test are not disabled.
         Security.setProperty("jdk.tls.disabledAlgorithms", "");
-
-        // MD5 is used in this test case, don't disable MD5 algorithm.
-        Security.setProperty(
-                "jdk.certpath.disabledAlgorithms", "MD2, RSA keySize < 1024");
+        Security.setProperty("jdk.certpath.disabledAlgorithms", "");
 
         ProvidersSnapshot snapshot = ProvidersSnapshot.create();
         try {
--- a/jdk/test/sun/security/krb5/auto/KDC.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/sun/security/krb5/auto/KDC.java	Wed Jul 05 20:42:36 2017 +0200
@@ -811,7 +811,7 @@
                     new TransitedEncoding(1, new byte[0]),  // TODO
                     new KerberosTime(new Date()),
                     body.from,
-                    till, body.rtime,
+                    till, etp.renewTill,
                     body.addresses != null ? body.addresses
                             : etp.caddr,
                     null);
@@ -834,7 +834,7 @@
                     tFlags,
                     new KerberosTime(new Date()),
                     body.from,
-                    till, body.rtime,
+                    till, etp.renewTill,
                     service,
                     body.addresses
                     );
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/sun/security/krb5/auto/Renew.java	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,106 @@
+/*
+ * 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.
+ */
+
+/*
+ * @test
+ * @bug 8058290
+ * @summary JAAS Krb5LoginModule has suspect ticket-renewal logic,
+ *          relies on clockskew grace
+ * @modules java.base/sun.net.spi.nameservice
+ *          java.base/sun.security.util
+ *          java.security.jgss/sun.security.krb5
+ *          java.security.jgss/sun.security.krb5.internal
+ *          java.security.jgss/sun.security.krb5.internal.ccache
+ *          java.security.jgss/sun.security.krb5.internal.crypto
+ *          java.security.jgss/sun.security.krb5.internal.ktab
+ * @compile -XDignore.symbol.file Renew.java
+ * @run main/othervm Renew 1
+ * @run main/othervm Renew 2
+ * @run main/othervm Renew 3
+ */
+
+import sun.security.krb5.Config;
+
+import java.nio.file.Files;
+import java.nio.file.Paths;
+import java.util.Arrays;
+import java.util.Date;
+import javax.security.auth.kerberos.KerberosTicket;
+
+public class Renew {
+
+    public static void main(String[] args) throws Exception {
+
+        // Three test cases:
+        // 1. renewTGT=false
+        // 2. renewTGT=true with a short life time, renew will happen
+        // 3. renewTGT=true with a long life time, renew won't happen
+        int test = Integer.parseInt(args[0]);
+
+        OneKDC k = new OneKDC(null);
+        KDC.saveConfig(OneKDC.KRB5_CONF, k,
+                "renew_lifetime = 1d",
+                "ticket_lifetime = " + (test == 2? "10s": "8h"));
+        Config.refresh();
+        k.writeJAASConf();
+
+        // KDC would save ccache in a file
+        System.setProperty("test.kdc.save.ccache", "cache.here");
+
+        Files.write(Paths.get(OneKDC.JAAS_CONF), Arrays.asList(
+                "first {",
+                "   com.sun.security.auth.module.Krb5LoginModule required;",
+                "};",
+                "second {",
+                "   com.sun.security.auth.module.Krb5LoginModule required",
+                "   doNotPrompt=true",
+                "   renewTGT=" + (test != 1),
+                "   useTicketCache=true",
+                "   ticketCache=cache.here;",
+                "};"
+        ));
+
+        Context c;
+
+        // The first login uses username and password
+        c = Context.fromUserPass(OneKDC.USER, OneKDC.PASS, false);
+        Date d1 = c.s().getPrivateCredentials(KerberosTicket.class).iterator().next().getAuthTime();
+
+        // 6s is longer than half of 10s
+        Thread.sleep(6000);
+
+        // The second login uses the cache
+        c = Context.fromJAAS("second");
+        Date d2 = c.s().getPrivateCredentials(KerberosTicket.class).iterator().next().getAuthTime();
+
+        if (test == 2) {
+            if (d1.equals(d2)) {
+                throw new Exception("Ticket not renewed");
+            }
+        } else {
+            if (!d1.equals(d2)) {
+                throw new Exception("Ticket renewed");
+            }
+        }
+    }
+}
--- a/jdk/test/sun/security/pkcs11/sslecc/ClientJSSEServerJSSE.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/sun/security/pkcs11/sslecc/ClientJSSEServerJSSE.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2002, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2002, 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
@@ -43,18 +43,15 @@
     private static String[] cmdArgs;
 
     public static void main(String[] args) throws Exception {
-        // reset the security property to make sure that the algorithms
-        // and keys used in this test are not disabled.
-        Security.setProperty("jdk.tls.disabledAlgorithms", "");
-
         cmdArgs = args;
         main(new ClientJSSEServerJSSE());
     }
 
     public void main(Provider p) throws Exception {
-        // MD5 is used in this test case, don't disable MD5 algorithm.
-        Security.setProperty(
-                "jdk.certpath.disabledAlgorithms", "MD2, RSA keySize < 1024");
+        // reset security properties to make sure that the algorithms
+        // and keys used in this test are not disabled.
+        Security.setProperty("jdk.tls.disabledAlgorithms", "");
+        Security.setProperty("jdk.certpath.disabledAlgorithms", "");
 
         if (p.getService("KeyFactory", "EC") == null) {
             System.out.println("Provider does not support EC, skipping");
--- a/jdk/test/sun/security/pkcs12/StoreSecretKeyTest.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/sun/security/pkcs12/StoreSecretKeyTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -23,8 +23,9 @@
 
 /*
  * @test
- * @bug 8005408 8079129
+ * @bug 8005408 8079129 8048830
  * @summary KeyStore API enhancements
+ * @run main StoreSecretKeyTest
  */
 
 import java.io.*;
@@ -44,9 +45,20 @@
     private static final String CERT = DIR + "/trusted.pem";
     private static final String ALIAS = "my trusted cert";
     private static final String ALIAS2 = "my secret key";
-
+    private enum ALGORITHM {
+        DES(56),
+        DESede(168),
+        AES(128);
+        final int len;
+        ALGORITHM(int l) {
+            len = l;
+        }
+        final int getLength() {
+            return len;
+        }
+    }
     public static void main(String[] args) throws Exception {
-
+        boolean isSecretkeyAlgSupported = false;
         // Skip test if AES is unavailable
         try {
             SecretKeyFactory.getInstance("AES");
@@ -55,57 +67,69 @@
             return;
         }
 
-        new File(KEYSTORE).delete();
+        for (ALGORITHM alg : ALGORITHM.values()) {
+            isSecretkeyAlgSupported |= testSecretKeyAlgorithm(alg);
+        }
+        if (!isSecretkeyAlgSupported) {
+            throw new Exception("None of the SecretKey algorithms is "
+                    + "supported");
+        }
+    }
 
-        KeyStore keystore = KeyStore.getInstance("PKCS12");
-        keystore.load(null, null);
+    private static boolean testSecretKeyAlgorithm(ALGORITHM algorithm) throws
+            Exception {
 
-        // Set trusted certificate entry
-        Certificate cert = loadCertificate(CERT);
-        keystore.setEntry(ALIAS,
+        System.out.println("Testing algorithm : " + algorithm.name());
+        new File(KEYSTORE).delete();
+        try {
+            KeyStore keystore = KeyStore.getInstance("PKCS12");
+            keystore.load(null, null);
+
+            // Set trusted certificate entry
+            Certificate cert = loadCertificate(CERT);
+            keystore.setEntry(ALIAS,
             new KeyStore.TrustedCertificateEntry(cert), null);
-
-        // Set secret key entry
-        keystore.setEntry(ALIAS2,
-            new KeyStore.SecretKeyEntry(generateSecretKey("AES", 128)),
+            // Set secret key entry
+            SecretKey secretKey = generateSecretKey(algorithm.name(),
+                    algorithm.len);
+            if(secretKey == null) {
+                return false;
+            }
+            keystore.setEntry(ALIAS2,
+                new KeyStore.SecretKeyEntry(secretKey),
                 new KeyStore.PasswordProtection(PASSWORD));
 
-        try (FileOutputStream outStream = new FileOutputStream(KEYSTORE)) {
-            System.out.println("Storing keystore to: " + KEYSTORE);
-            keystore.store(outStream, PASSWORD);
-        }
+            try (FileOutputStream outStream = new FileOutputStream(KEYSTORE)) {
+                System.out.println("Storing keystore to: " + KEYSTORE);
+                keystore.store(outStream, PASSWORD);
+            }
+
+            try (FileInputStream inStream = new FileInputStream(KEYSTORE)) {
+                System.out.println("Loading keystore from: " + KEYSTORE);
+                keystore.load(inStream, PASSWORD);
+                System.out.println("Loaded keystore with " + keystore.size() +
+                    " entries");
+            }
 
-        try (FileInputStream inStream = new FileInputStream(KEYSTORE)) {
-            System.out.println("Loading keystore from: " + KEYSTORE);
-            keystore.load(inStream, PASSWORD);
-            System.out.println("Loaded keystore with " + keystore.size() +
-                " entries");
+            KeyStore.Entry entry = keystore.getEntry(ALIAS2,
+                new KeyStore.PasswordProtection(PASSWORD));
+            System.out.println("Retrieved entry: " + entry);
+
+            if (entry instanceof KeyStore.SecretKeyEntry) {
+                System.out.println("Retrieved secret key entry: " + entry);
+            } else {
+                throw new Exception("Not a secret key entry");
+            }
+        } catch (KeyStoreException | UnrecoverableKeyException ex) {
+            System.out.println("Unable to check SecretKey algorithm due to "
+                    + "exception: " + ex.getMessage());
+            return false;
         }
-
-        KeyStore.Entry entry = keystore.getEntry(ALIAS2,
-            new KeyStore.PasswordProtection(PASSWORD));
-        System.out.println("Retrieved entry: " + entry);
-
-        if (entry instanceof KeyStore.SecretKeyEntry) {
-            System.out.println("Retrieved secret key entry: " + entry);
-        } else {
-            throw new Exception("Not a secret key entry");
-        }
+        return true;
     }
 
     private static SecretKey generateSecretKey(String algorithm, int size)
         throws NoSuchAlgorithmException {
-
-        // Failover to DES if the requested secret key factory is unavailable
-        SecretKeyFactory keyFactory;
-        try {
-            keyFactory = SecretKeyFactory.getInstance(algorithm);
-        } catch (NoSuchAlgorithmException nsae) {
-            keyFactory = SecretKeyFactory.getInstance("DES");
-            algorithm = "DES";
-            size = 56;
-        }
-
         KeyGenerator generator = KeyGenerator.getInstance(algorithm);
         generator.init(size);
         return generator.generateKey();
--- a/jdk/test/sun/security/ssl/DHKeyExchange/DHEKeySizing.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/sun/security/ssl/DHKeyExchange/DHEKeySizing.java	Wed Jul 05 20:42:36 2017 +0200
@@ -377,9 +377,10 @@
     }
 
     public static void main(String args[]) throws Exception {
-        // reset the security property to make sure that the algorithms
+        // reset security properties to make sure that the algorithms
         // and keys used in this test are not disabled.
         Security.setProperty("jdk.tls.disabledAlgorithms", "");
+        Security.setProperty("jdk.certpath.disabledAlgorithms", "");
 
         if (args.length != 4) {
             System.out.println(
--- a/jdk/test/sun/security/ssl/ServerHandshaker/AnonCipherWithWantClientAuth.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/sun/security/ssl/ServerHandshaker/AnonCipherWithWantClientAuth.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2001, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2001, 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
@@ -21,19 +21,22 @@
  * questions.
  */
 
+//
+// SunJSSE does not support dynamic system properties, no way to re-use
+// system properties in samevm/agentvm mode.
+//
+
 /*
  * @test
  * @bug 4392475
  * @summary Calling setWantClientAuth(true) disables anonymous suites
  * @run main/othervm/timeout=180 AnonCipherWithWantClientAuth
- *
- *     SunJSSE does not support dynamic system properties, no way to re-use
- *     system properties in samevm/agentvm mode.
  */
 
 import java.io.*;
 import java.net.*;
 import javax.net.ssl.*;
+import java.security.Security;
 
 public class AnonCipherWithWantClientAuth {
 
@@ -156,6 +159,11 @@
     volatile Exception clientException = null;
 
     public static void main(String[] args) throws Exception {
+        // reset security properties to make sure that the algorithms
+        // and keys used in this test are not disabled.
+        Security.setProperty("jdk.tls.disabledAlgorithms", "");
+        Security.setProperty("jdk.certpath.disabledAlgorithms", "");
+
         String keyFilename =
             System.getProperty("test.src", "./") + "/" + pathToStores +
                 "/" + keyStoreFile;
--- a/jdk/test/sun/security/tools/jarsigner/TsacertOptionTest.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/sun/security/tools/jarsigner/TsacertOptionTest.java	Wed Jul 05 20:42:36 2017 +0200
@@ -120,6 +120,9 @@
             // specify -tsadigestalg option because
             // TSA server uses SHA-1 digest algorithm
              OutputAnalyzer analyzer = ProcessTools.executeCommand(JARSIGNER,
+                    "-J-Dhttp.proxyHost=",
+                    "-J-Dhttp.proxyPort=",
+                    "-J-Djava.net.useSystemProxies=",
                     "-verbose",
                     "-keystore", KEYSTORE,
                     "-storepass", PASSWORD,
--- a/jdk/test/tools/pack200/PackTestZip64.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/jdk/test/tools/pack200/PackTestZip64.java	Wed Jul 05 20:42:36 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -37,6 +37,7 @@
  * @compile -XDignore.symbol.file Utils.java PackTestZip64.java
  * @run main PackTestZip64
  * @author kizune
+ * @key intermittent
  */
 
 public class PackTestZip64 {
--- a/make/Javadoc.gmk	Thu Jul 16 19:31:01 2015 -0700
+++ b/make/Javadoc.gmk	Wed Jul 05 20:42:36 2017 +0200
@@ -410,7 +410,8 @@
 	$(prep-target)
 	@($(call COMMON_JAVADOCFLAGS) ; \
           $(call COMMON_JAVADOCTAGS) ; \
-          $(call OptionOnly,-Xdoclint:none) ; \
+          $(call OptionOnly,-Xdoclint:reference) ; \
+          $(call OptionOnly,-Xdoclint/package:-org.omg.*) ; \
 	  $(call OptionPair,-sourcepath,$(RELEASEDOCS_SOURCEPATH)) ; \
 	  $(call OptionPair,-encoding,ISO-8859-1) ; \
 	  $(call OptionOnly,-splitIndex) ; \
--- a/make/jprt.properties	Thu Jul 16 19:31:01 2015 -0700
+++ b/make/jprt.properties	Wed Jul 05 20:42:36 2017 +0200
@@ -61,7 +61,7 @@
 
 # Use these configure args to define debug level
 jprt.debug.build.configure.args=--with-debug-level=slowdebug
-jprt.fastdebug.build.configure.args=--with-debug-level=fastdebug
+jprt.fastdebug.build.configure.args=--with-debug-level=fastdebug --disable-precompiled-headers
 jprt.product.build.configure.args=--with-debug-level=release
 jprt.optimized.build.configure.args=--with-debug-level=optimized
 jprt.debugOpen.build.configure.args=${jprt.debug.build.configure.args} --enable-openjdk-only
@@ -121,9 +121,7 @@
     ${jprt.fastdebugOpen.build.configure.args}
 jprt.i586.productOpen.build.configure.args=				\
     ${my.i586.default.build.configure.args}				\
-    ${jprt.productOpen.build.configure.args}
-
-jprt.windows_i586.build.configure.args= \
+    ${jprt.productOpen.build.configure.args}jprt.windows_i586.build.configure.args= \
     --with-devkit=$VS2013_HOME \
     ${jprt.i586.build.configure.args}
 jprt.windows_x64.build.configure.args= \
@@ -281,12 +279,7 @@
     solaris_sparcv9_5.11-{product|fastdebug}-c2-GCBasher_SerialGC,	\
     solaris_sparcv9_5.11-{product|fastdebug}-c2-GCBasher_ParallelGC,	\
     solaris_sparcv9_5.11-{product|fastdebug}-c2-GCBasher_CMS,		\
-    solaris_sparcv9_5.11-{product|fastdebug}-c2-GCBasher_G1,		\
-    solaris_sparcv9_5.11-{product|fastdebug}-c2-jbb_default_nontiered,	\
-    solaris_sparcv9_5.11-{product|fastdebug}-c2-jbb_SerialGC,		\
-    solaris_sparcv9_5.11-{product|fastdebug}-c2-jbb_ParallelGC,		\
-    solaris_sparcv9_5.11-{product|fastdebug}-c2-jbb_CMS,		\
-    solaris_sparcv9_5.11-{product|fastdebug}-c2-jbb_G1
+    solaris_sparcv9_5.11-{product|fastdebug}-c2-GCBasher_G1
 
 my.test.targets.hotspot.solaris.x64=					\
     solaris_x64_5.11-{product|fastdebug}-c2-jvm98,			\
@@ -298,10 +291,7 @@
     solaris_x64_5.11-{product|fastdebug}-c2-GCBasher_SerialGC,		\
     solaris_x64_5.11-{product|fastdebug}-c2-GCBasher_ParallelGC,	\
     solaris_x64_5.11-{product|fastdebug}-c2-GCBasher_CMS,		\
-    solaris_x64_5.11-{product|fastdebug}-c2-GCBasher_G1,		\
-    solaris_x64_5.11-{product|fastdebug}-c2-jbb_default_nontiered,	\
-    solaris_x64_5.11-{product|fastdebug}-c2-jbb_SerialGC,		\
-    solaris_x64_5.11-{product|fastdebug}-c2-jbb_ParallelGC,
+    solaris_x64_5.11-{product|fastdebug}-c2-GCBasher_G1
 
 my.test.targets.hotspot.linux.i586=					\
     linux_i586_2.6-{product|fastdebug}-{c1|c2}-jvm98,			\
@@ -315,12 +305,7 @@
     linux_i586_2.6-{product|fastdebug}-{c1|c2}-GCBasher_SerialGC,	\
     linux_i586_2.6-{product|fastdebug}-{c1|c2}-GCBasher_ParallelGC,	\
     linux_i586_2.6-{product|fastdebug}-{c1|c2}-GCBasher_CMS,		\
-    linux_i586_2.6-{product|fastdebug}-{c1|c2}-GCBasher_G1,		\
-    linux_i586_2.6-{product|fastdebug}-c1-jbb_SerialGC,			\
-    linux_i586_2.6-{product|fastdebug}-c2-jbb_default_nontiered,	\
-    linux_i586_2.6-{product|fastdebug}-c1-jbb_ParallelGC,		\
-    linux_i586_2.6-{product|fastdebug}-c1-jbb_CMS,			\
-    linux_i586_2.6-{product|fastdebug}-c1-jbb_G1
+    linux_i586_2.6-{product|fastdebug}-{c1|c2}-GCBasher_G1
 
 my.test.targets.hotspot.linux.x64=					\
     linux_x64_2.6-{product|fastdebug}-c2-jvm98,				\
@@ -329,10 +314,7 @@
     linux_x64_2.6-{product|fastdebug}-c2-GCBasher_SerialGC,		\
     linux_x64_2.6-{product|fastdebug}-c2-GCBasher_ParallelGC,		\
     linux_x64_2.6-{product|fastdebug}-c2-GCBasher_CMS,			\
-    linux_x64_2.6-{product|fastdebug}-c2-GCBasher_G1,			\
-    linux_x64_2.6-{product|fastdebug}-c2-jbb_default_nontiered,		\
-    linux_x64_2.6-{product|fastdebug}-c2-jbb_ParallelGC,		\
-    linux_x64_2.6-{product|fastdebug}-c2-jbb_G1
+    linux_x64_2.6-{product|fastdebug}-c2-GCBasher_G1
 
 my.test.targets.hotspot.macosx.x64=					\
     macosx_x64_10.9-{product|fastdebug}-c2-jvm98,			\
@@ -341,10 +323,7 @@
     macosx_x64_10.9-{product|fastdebug}-c2-GCBasher_SerialGC,		\
     macosx_x64_10.9-{product|fastdebug}-c2-GCBasher_ParallelGC,		\
     macosx_x64_10.9-{product|fastdebug}-c2-GCBasher_CMS,		\
-    macosx_x64_10.9-{product|fastdebug}-c2-GCBasher_G1,			\
-    macosx_x64_10.9-{product|fastdebug}-c2-jbb_default_nontiered,	\
-    macosx_x64_10.9-{product|fastdebug}-c2-jbb_ParallelGC,		\
-    macosx_x64_10.9-{product|fastdebug}-c2-jbb_G1
+    macosx_x64_10.9-{product|fastdebug}-c2-GCBasher_G1
 
 my.test.targets.hotspot.windows.i586=					\
     windows_i586_6.2-{product|fastdebug}-{c1|c2}-jvm98,			\
@@ -357,12 +336,7 @@
     windows_i586_6.2-{product|fastdebug}-{c1|c2}-GCBasher_SerialGC,	\
     windows_i586_6.2-{product|fastdebug}-{c1|c2}-GCBasher_ParallelGC,	\
     windows_i586_6.2-{product|fastdebug}-{c1|c2}-GCBasher_CMS,		\
-    windows_i586_6.2-{product|fastdebug}-{c1|c2}-GCBasher_G1,		\
-    windows_i586_6.2-{product|fastdebug}-{c1|c2}-jbb_default,		\
-    windows_i586_6.2-{product|fastdebug}-c2-jbb_default_nontiered,	\
-    windows_i586_6.2-product-{c1|c2}-jbb_ParallelGC,			\
-    windows_i586_6.2-product-{c1|c2}-jbb_CMS,				\
-    windows_i586_6.2-product-{c1|c2}-jbb_G1
+    windows_i586_6.2-{product|fastdebug}-{c1|c2}-GCBasher_G1
 
 my.test.targets.hotspot.windows.x64=					\
     windows_x64_6.2-{product|fastdebug}-c2-jvm98,			\
@@ -374,12 +348,7 @@
     windows_x64_6.2-{product|fastdebug}-c2-GCBasher_SerialGC,		\
     windows_x64_6.2-{product|fastdebug}-c2-GCBasher_ParallelGC,		\
     windows_x64_6.2-{product|fastdebug}-c2-GCBasher_CMS,		\
-    windows_x64_6.2-{product|fastdebug}-c2-GCBasher_G1,			\
-    windows_x64_6.2-{product|fastdebug}-c2-jbb_default,			\
-    windows_x64_6.2-{product|fastdebug}-c2-jbb_default_nontiered,	\
-    windows_x64_6.2-product-c2-jbb_CMS,					\
-    windows_x64_6.2-product-c2-jbb_ParallelGC,				\
-    windows_x64_6.2-product-c2-jbb_G1
+    windows_x64_6.2-{product|fastdebug}-c2-GCBasher_G1
 
 # Some basic "smoke" tests for OpenJDK builds
 my.test.targets.hotspot.open=						\
--- a/modules.xml	Thu Jul 16 19:31:01 2015 -0700
+++ b/modules.xml	Wed Jul 05 20:42:36 2017 +0200
@@ -219,6 +219,10 @@
       <to>jdk.dev</to>
     </export>
     <export>
+      <name>jdk.internal.jimage.decompressor</name>
+      <to>jdk.dev</to>
+    </export>
+    <export>
       <name>jdk.internal.org.objectweb.asm</name>
       <to>java.instrument</to>
       <to>jdk.jfr</to>
@@ -246,6 +250,10 @@
       <to>jdk.scripting.nashorn</to>
     </export>
     <export>
+      <name>jdk.internal</name>
+      <to>jdk.jfr</to>
+    </export>
+    <export>
       <name>sun.misc</name>
       <to>java.corba</to>
       <to>java.desktop</to>
@@ -285,6 +293,7 @@
     </export>
     <export>
       <name>sun.net.util</name>
+      <to>java.desktop</to>
       <to>jdk.jconsole</to>
       <to>jdk.naming.dns</to>
     </export>
--- a/nashorn/.hgignore	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/.hgignore	Wed Jul 05 20:42:36 2017 +0200
@@ -23,6 +23,7 @@
 CC/*
 jcov2/*
 .idea/*
+test/lib/testng*.zip
 test/lib/testng.jar
 test/script/external/*
 .project
--- a/nashorn/.hgtags	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/.hgtags	Wed Jul 05 20:42:36 2017 +0200
@@ -306,3 +306,4 @@
 3379235149c0e14e59e05c4ab8df450f5777b552 jdk9-b70
 7066af6e7b06f3c6ebf449c88fc1064d2181237a jdk9-b71
 d017877b3b8cd39337f1bdc00d958f821433c4c3 jdk9-b72
+548f1eb2c3c89e024ef3805f48ceed9de503588f jdk9-b73
--- a/nashorn/buildtools/nasgen/src/jdk/nashorn/internal/tools/nasgen/ConstructorGenerator.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/buildtools/nasgen/src/jdk/nashorn/internal/tools/nasgen/ConstructorGenerator.java	Wed Jul 05 20:42:36 2017 +0200
@@ -55,7 +55,7 @@
 import jdk.internal.org.objectweb.asm.Handle;
 
 /**
- * This class generates constructor class for a @ClassInfo annotated class.
+ * This class generates constructor class for a @ScriptClass annotated class.
  *
  */
 public class ConstructorGenerator extends ClassGenerator {
@@ -75,7 +75,7 @@
     }
 
     byte[] getClassBytes() {
-        // new class extensing from ScriptObject
+        // new class extending from ScriptObject
         final String superClass = (constructor != null)? SCRIPTFUNCTIONIMPL_TYPE : SCRIPTOBJECT_TYPE;
         cw.visit(V1_7, ACC_FINAL, className, null, superClass, null);
         if (memberCount > 0) {
--- a/nashorn/buildtools/nasgen/src/jdk/nashorn/internal/tools/nasgen/MemberInfo.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/buildtools/nasgen/src/jdk/nashorn/internal/tools/nasgen/MemberInfo.java	Wed Jul 05 20:42:36 2017 +0200
@@ -161,7 +161,7 @@
     }
 
     /**
-     * Tag something as optimitic builtin or not
+     * Tag something as optimistic builtin or not
      * @param isOptimistic boolean, true if builtin constructor
      */
     public void setIsOptimistic(final boolean isOptimistic) {
@@ -178,7 +178,7 @@
     }
 
     /**
-     * Set thre SpecializedFunction link logic class for specializations, i.e. optimistic
+     * Set the SpecializedFunction link logic class for specializations, i.e. optimistic
      * builtins
      * @param linkLogicClass link logic class
      */
--- a/nashorn/buildtools/nasgen/src/jdk/nashorn/internal/tools/nasgen/PrototypeGenerator.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/buildtools/nasgen/src/jdk/nashorn/internal/tools/nasgen/PrototypeGenerator.java	Wed Jul 05 20:42:36 2017 +0200
@@ -42,7 +42,7 @@
 import java.io.IOException;
 
 /**
- * This class generates prototype class for a @ClassInfo annotated class.
+ * This class generates prototype class for a @ScriptClass annotated class.
  *
  */
 public class PrototypeGenerator extends ClassGenerator {
@@ -57,7 +57,7 @@
     }
 
     byte[] getClassBytes() {
-        // new class extensing from ScriptObject
+        // new class extending from ScriptObject
         cw.visit(V1_7, ACC_FINAL | ACC_SUPER, className, null, PROTOTYPEOBJECT_TYPE, null);
         if (memberCount > 0) {
             // add fields
@@ -155,7 +155,7 @@
      */
     public static void main(final String[] args) throws IOException {
         if (args.length != 1) {
-            System.err.println("Usage: " + ConstructorGenerator.class.getName() + " <class>");
+            System.err.println("Usage: " + PrototypeGenerator.class.getName() + " <class>");
             System.exit(1);
         }
 
--- a/nashorn/buildtools/nasgen/src/jdk/nashorn/internal/tools/nasgen/ScriptClassInfo.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/buildtools/nasgen/src/jdk/nashorn/internal/tools/nasgen/ScriptClassInfo.java	Wed Jul 05 20:42:36 2017 +0200
@@ -48,7 +48,7 @@
  *
  */
 public final class ScriptClassInfo {
-    // descriptots for various annotations
+    // descriptors for various annotations
     static final String SCRIPT_CLASS_ANNO_DESC  = Type.getDescriptor(ScriptClass.class);
     static final String CONSTRUCTOR_ANNO_DESC   = Type.getDescriptor(Constructor.class);
     static final String FUNCTION_ANNO_DESC      = Type.getDescriptor(Function.class);
@@ -140,7 +140,7 @@
     }
 
     boolean isPrototypeNeeded() {
-        // Prototype class generation is needed if we have atleast one
+        // Prototype class generation is needed if we have at least one
         // prototype property or @Constructor defined in the class.
         for (final MemberInfo memInfo : members) {
             if (memInfo.getWhere() == Where.PROTOTYPE || memInfo.isConstructor()) {
--- a/nashorn/buildtools/nasgen/src/jdk/nashorn/internal/tools/nasgen/ScriptClassInfoCollector.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/buildtools/nasgen/src/jdk/nashorn/internal/tools/nasgen/ScriptClassInfoCollector.java	Wed Jul 05 20:42:36 2017 +0200
@@ -118,7 +118,7 @@
                     addScriptMember(memInfo);
 
                     return new AnnotationVisitor(Main.ASM_VERSION, delegateAV) {
-                        // These could be "null" if values are not suppiled,
+                        // These could be "null" if values are not supplied,
                         // in which case we have to use the default values.
                         private String  name;
                         private Integer attributes;
@@ -194,7 +194,7 @@
 
                     final MemberInfo memInfo = new MemberInfo();
 
-                    //annokind == e.g. GETTER or SPECIALIZED_FUNCTION
+                    // annoKind == GETTER or SPECIALIZED_FUNCTION
                     memInfo.setKind(annoKind);
                     memInfo.setJavaName(methodName);
                     memInfo.setJavaDesc(methodDesc);
@@ -203,7 +203,7 @@
                     addScriptMember(memInfo);
 
                     return new AnnotationVisitor(Main.ASM_VERSION, delegateAV) {
-                        // These could be "null" if values are not suppiled,
+                        // These could be "null" if values are not supplied,
                         // in which case we have to use the default values.
                         private String  name;
                         private Integer attributes;
--- a/nashorn/buildtools/nasgen/src/jdk/nashorn/internal/tools/nasgen/ScriptClassInstrumentor.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/buildtools/nasgen/src/jdk/nashorn/internal/tools/nasgen/ScriptClassInstrumentor.java	Wed Jul 05 20:42:36 2017 +0200
@@ -64,7 +64,6 @@
  * 2) add "Map" type static field named "$map".
  * 3) add static initializer block to initialize map.
  */
-
 public class ScriptClassInstrumentor extends ClassVisitor {
     private final ScriptClassInfo scriptClassInfo;
     private final int memberCount;
@@ -266,7 +265,7 @@
      */
     public static void main(final String[] args) throws IOException {
         if (args.length != 1) {
-            System.err.println("Usage: " + ScriptClassInfoCollector.class.getName() + " <class>");
+            System.err.println("Usage: " + ScriptClassInstrumentor.class.getName() + " <class>");
             System.exit(1);
         }
 
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/api/scripting/AbstractJSObject.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/api/scripting/AbstractJSObject.java	Wed Jul 05 20:42:36 2017 +0200
@@ -180,7 +180,7 @@
     /**
      * Checking whether the given object is an instance of 'this' object.
      *
-     * @param instance instace to check
+     * @param instance instance to check
      * @return true if the given 'instance' is an instance of this 'function' object
      */
     @Override
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/api/scripting/JSObject.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/api/scripting/JSObject.java	Wed Jul 05 20:42:36 2017 +0200
@@ -142,7 +142,7 @@
     /**
      * Checking whether the given object is an instance of 'this' object.
      *
-     * @param instance instace to check
+     * @param instance instance to check
      * @return true if the given 'instance' is an instance of this 'function' object
      */
     public boolean isInstance(final Object instance);
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/objects/Global.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/objects/Global.java	Wed Jul 05 20:42:36 2017 +0200
@@ -2118,17 +2118,18 @@
             }
         }
 
+        final boolean extensible = isExtensible();
         for (final jdk.nashorn.internal.runtime.Property property : properties) {
             if (property.isLexicalBinding()) {
                 assert lexScope != null;
-                lexicalMap = lexScope.addBoundProperty(lexicalMap, source, property);
+                lexicalMap = lexScope.addBoundProperty(lexicalMap, source, property, true);
 
                 if (ownMap.findProperty(property.getKey()) != null) {
                     // If property exists in the global object invalidate any global constant call sites.
                     invalidateGlobalConstant(property.getKey());
                 }
             } else {
-                ownMap = addBoundProperty(ownMap, source, property);
+                ownMap = addBoundProperty(ownMap, source, property, extensible);
             }
         }
 
@@ -2730,9 +2731,9 @@
         }
 
         @Override
-        protected PropertyMap addBoundProperty(final PropertyMap propMap, final ScriptObject source, final jdk.nashorn.internal.runtime.Property property) {
+        protected PropertyMap addBoundProperty(final PropertyMap propMap, final ScriptObject source, final jdk.nashorn.internal.runtime.Property property, final boolean extensible) {
             // We override this method just to make it callable by Global
-            return super.addBoundProperty(propMap, source, property);
+            return super.addBoundProperty(propMap, source, property, extensible);
         }
 
         private static GuardedInvocation filterInvocation(final GuardedInvocation invocation) {
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/objects/NativeDataView.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/objects/NativeDataView.java	Wed Jul 05 20:42:36 2017 +0200
@@ -22,6 +22,7 @@
  * or visit www.oracle.com if you need additional information or have any
  * questions.
  */
+
 package jdk.nashorn.internal.objects;
 
 import static jdk.nashorn.internal.runtime.ECMAErrors.rangeError;
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/objects/NativeFunction.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/objects/NativeFunction.java	Wed Jul 05 20:42:36 2017 +0200
@@ -108,7 +108,7 @@
         throw new AssertionError("Should not reach here");
     }
 
-     /**
+    /**
      * Given an array-like object, converts it into a Java object array suitable for invocation of ScriptRuntime.apply
      * or for direct invocation of the applied function.
      * @param array the array-like object. Can be null in which case a zero-length array is created.
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/GlobalFunctions.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/GlobalFunctions.java	Wed Jul 05 20:42:36 2017 +0200
@@ -187,14 +187,14 @@
 
         double result = 0.0;
         int digit;
-        // we should see atleast one valid digit
+        // we should see at least one valid digit
         boolean entered = false;
         while (idx < length) {
             digit = fastDigit(str.charAt(idx++), radix);
             if (digit < 0) {
                 break;
             }
-            // we have seen atleast one valid digit in the specified radix
+            // we have seen at least one valid digit in the specified radix
             entered = true;
             result *= radix;
             result += digit;
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/JSONFunctions.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/JSONFunctions.java	Wed Jul 05 20:42:36 2017 +0200
@@ -104,16 +104,28 @@
         final Object val = holder.get(name);
         if (val instanceof ScriptObject) {
             final ScriptObject     valueObj = (ScriptObject)val;
-            final Iterator<String> iter     = valueObj.propertyIterator();
+            if (valueObj.isArray()) {
+                final int length = JSType.toInteger(valueObj.getLength());
+                for (int i = 0; i < length; i++) {
+                    final String key = Integer.toString(i);
+                    final Object newElement = walk(valueObj, key, reviver);
 
-            while (iter.hasNext()) {
-                final String key        = iter.next();
-                final Object newElement = walk(valueObj, key, reviver);
+                    if (newElement == ScriptRuntime.UNDEFINED) {
+                        valueObj.delete(i, false);
+                    } else {
+                        setPropertyValue(valueObj, key, newElement);
+                    }
+                }
+            } else {
+                final String[] keys = valueObj.getOwnKeys(false);
+                for (final String key : keys) {
+                    final Object newElement = walk(valueObj, key, reviver);
 
-                if (newElement == ScriptRuntime.UNDEFINED) {
-                    valueObj.delete(key, false);
-                } else {
-                    setPropertyValue(valueObj, key, newElement);
+                    if (newElement == ScriptRuntime.UNDEFINED) {
+                        valueObj.delete(key, false);
+                    } else {
+                        setPropertyValue(valueObj, key, newElement);
+                    }
                 }
             }
         }
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/ScriptObject.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/ScriptObject.java	Wed Jul 05 20:42:36 2017 +0200
@@ -224,7 +224,7 @@
      * same combination of prototype and property map.
      *
      * @param proto the prototype object
-     * @param map intial {@link PropertyMap}
+     * @param map initial {@link PropertyMap}
      */
     protected ScriptObject(final ScriptObject proto, final PropertyMap map) {
         this(map);
@@ -287,9 +287,10 @@
      */
     public void addBoundProperties(final ScriptObject source, final Property[] properties) {
         PropertyMap newMap = this.getMap();
+        final boolean extensible = newMap.isExtensible();
 
         for (final Property property : properties) {
-            newMap = addBoundProperty(newMap, source, property);
+            newMap = addBoundProperty(newMap, source, property, extensible);
         }
 
         this.setMap(newMap);
@@ -302,13 +303,18 @@
      * @param propMap the property map
      * @param source the source object
      * @param property the property to be added
+     * @param extensible whether the current object is extensible or not
      * @return the new property map
      */
-    protected PropertyMap addBoundProperty(final PropertyMap propMap, final ScriptObject source, final Property property) {
+    protected PropertyMap addBoundProperty(final PropertyMap propMap, final ScriptObject source, final Property property, final boolean extensible) {
         PropertyMap newMap = propMap;
         final String key = property.getKey();
         final Property oldProp = newMap.findProperty(key);
         if (oldProp == null) {
+            if (! extensible) {
+                throw typeError("object.non.extensible", key, ScriptRuntime.safeToString(this));
+            }
+
             if (property instanceof UserAccessorProperty) {
                 // Note: we copy accessor functions to this object which is semantically different from binding.
                 final UserAccessorProperty prop = this.newUserAccessors(key, property.getFlags(), property.getGetterFunction(source), property.getSetterFunction(source));
@@ -337,11 +343,15 @@
      */
     public void addBoundProperties(final Object source, final AccessorProperty[] properties) {
         PropertyMap newMap = this.getMap();
+        final boolean extensible = newMap.isExtensible();
 
         for (final AccessorProperty property : properties) {
             final String key = property.getKey();
 
             if (newMap.findProperty(key) == null) {
+                if (! extensible) {
+                    throw typeError("object.non.extensible", key, ScriptRuntime.safeToString(this));
+                }
                 newMap = newMap.addPropertyBind(property, source);
             }
         }
@@ -1247,7 +1257,7 @@
         if (oldProto != newProto) {
             proto = newProto;
 
-            // Let current listeners know that the protototype has changed and set our map
+            // Let current listeners know that the prototype has changed and set our map
             final PropertyListeners listeners = getMap().getListeners();
             if (listeners != null) {
                 listeners.protoChanged();
@@ -1442,7 +1452,7 @@
      * in {@link ScriptFunction} for hasInstance implementation, walks
      * the proto chain
      *
-     * @param instance instace to check
+     * @param instance instance to check
      * @return true if 'instance' is an instance of this object
      */
     public boolean isInstance(final ScriptObject instance) {
@@ -1859,7 +1869,7 @@
      * @param desc    the call site descriptor.
      * @param request the link request
      *
-     * @return GuardedInvocation to be invoed at call site.
+     * @return GuardedInvocation to be invoked at call site.
      */
     protected GuardedInvocation findCallMethod(final CallSiteDescriptor desc, final LinkRequest request) {
         return notAFunction();
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/linker/Bootstrap.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/linker/Bootstrap.java	Wed Jul 05 20:42:36 2017 +0200
@@ -69,7 +69,7 @@
     private static final MethodHandle VOID_TO_OBJECT = MH.constant(Object.class, ScriptRuntime.UNDEFINED);
 
     /**
-     * The default dynalink relink threshold for megamorphisism is 8. In the case
+     * The default dynalink relink threshold for megamorphism is 8. In the case
      * of object fields only, it is fine. However, with dual fields, in order to get
      * performance on benchmarks with a lot of object instantiation and then field
      * reassignment, it can take slightly more relinks to become stable with type
@@ -213,7 +213,7 @@
      * @param type           method type
      * @param programPoint   program point to bind to callsite
      *
-     * @return callsite for a math instrinic node
+     * @return callsite for a math intrinsic node
      */
     public static CallSite mathBootstrap(final MethodHandles.Lookup lookup, final String name, final MethodType type, final int programPoint) {
         final MethodHandle mh;
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/linker/JavaAdapterBytecodeGenerator.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/linker/JavaAdapterBytecodeGenerator.java	Wed Jul 05 20:42:36 2017 +0200
@@ -571,7 +571,7 @@
             mv.visitVarInsn(ALOAD, 0);
             if (fromFunction && !mi.getName().equals(samName)) {
                 // Constructors initializing from a ScriptFunction only initialize methods with the SAM name.
-                // NOTE: if there's a concrete overloaded method sharing the SAM name, it'll be overriden too. This
+                // NOTE: if there's a concrete overloaded method sharing the SAM name, it'll be overridden too. This
                 // is a deliberate design choice. All other method handles are initialized to null.
                 mv.visitInsn(ACONST_NULL);
             } else {
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/linker/LinkerCallSite.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/linker/LinkerCallSite.java	Wed Jul 05 20:42:36 2017 +0200
@@ -500,7 +500,7 @@
          * @param desc callsite descriptor string
          * @param args arguments to function
          *
-         * @throws Throwable if invocation failes or throws exception/error
+         * @throws Throwable if invocation fails or throws exception/error
          */
         @SuppressWarnings("unused")
         public void traceMiss(final String desc, final Object... args) throws Throwable {
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/linker/NashornBeansLinker.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/linker/NashornBeansLinker.java	Wed Jul 05 20:42:36 2017 +0200
@@ -169,7 +169,7 @@
         }
 
         for (final Class<?> iface : clazz.getInterfaces()) {
-            // check accessiblity up-front
+            // check accessibility up-front
             if (! Context.isAccessibleClass(iface)) {
                 continue;
             }
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/linker/NashornCallSiteDescriptor.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/linker/NashornCallSiteDescriptor.java	Wed Jul 05 20:42:36 2017 +0200
@@ -274,7 +274,7 @@
      * {@code NashornCallSiteDescriptor}. This allows for graceful interoperability when linking Nashorn with code
      * generated outside of Nashorn.
      * @param flag the tested flag
-     * @return true if the flag is set, false otherwise (it will be false if the decriptor is not a Nashorn call site
+     * @return true if the flag is set, false otherwise (it will be false if the descriptor is not a Nashorn call site
      * descriptor).
      */
     private static boolean isFlag(final CallSiteDescriptor desc, final int flag) {
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/options/OptionTemplate.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/options/OptionTemplate.java	Wed Jul 05 20:42:36 2017 +0200
@@ -163,7 +163,7 @@
 
     /**
      * Does this option automatically enable another option, i.e. a dependency.
-     * @return the dependecy or null if non exists
+     * @return the dependency or null if none exists
      */
     public String getDependency() {
         return this.dependency;
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/nashorn/test/script/basic/JDK-8130853.js	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,89 @@
+/*
+ * 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.
+ */
+
+/**
+ * JDK-8130853: Non-extensible global is not handled property
+ *
+ * @test
+ * @run
+ */
+
+// don't allow extensions to global
+Object.preventExtensions(this);
+try {
+    eval("var x = 34;");
+    throw new Error("should have thrown TypeError");
+} catch (e) {
+    if (! (e instanceof TypeError)) {
+        throw e;
+    }
+}
+
+try {
+    eval("function func() {}");
+    throw new Error("should have thrown TypeError");
+} catch (e) {
+    if (! (e instanceof TypeError)) {
+        throw e;
+    }
+}
+
+function checkLoad(code) {
+    try {
+        load({ name: "test", script: code });
+        throw new Error("should have thrown TypeError for load: " + code);
+    } catch (e) {
+        if (! (e instanceof TypeError)) {
+            throw e;
+        }
+    }
+}
+
+checkLoad("var y = 55");
+checkLoad("function f() {}");
+
+// check script engine eval
+var ScriptEngineManager = Java.type("javax.script.ScriptEngineManager");
+var e = new ScriptEngineManager().getEngineByName("nashorn");
+var global = e.eval("this");
+e.eval("Object.preventExtensions(this);");
+try {
+    e.eval("var myVar = 33;");
+    throw new Error("should have thrown TypeError");
+} catch (e) {
+    if (! (e.cause.ecmaError instanceof global.TypeError)) {
+        throw e;
+    }
+}
+
+// Object.bindProperties on arbitrary non-extensible object
+var obj = {};
+Object.preventExtensions(obj);
+try {
+    Object.bindProperties(obj, { foo: 434 });
+    throw new Error("should have thrown TypeError");
+} catch (e) {
+    if (! (e instanceof TypeError)) {
+        throw e;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/nashorn/test/script/basic/JDK-8131039.js	Wed Jul 05 20:42:36 2017 +0200
@@ -0,0 +1,35 @@
+/*
+ * 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.
+ */
+
+/**
+ * JDK-8131039: after adding a function property to Object.prototype, JSON.parse with reviver function goes into infinite loop
+ *
+ * @test
+ * @run
+ */
+
+Object.prototype.func = function() {}
+
+function identity(k, v) { return v };
+var obj = JSON.parse('{\"name\" : \"nashorn\"}', identity);
+Assert.assertTrue(obj.name, "nashorn");
--- a/test/lib/Makefile	Thu Jul 16 19:31:01 2015 -0700
+++ b/test/lib/Makefile	Wed Jul 05 20:42:36 2017 +0200
@@ -8,7 +8,7 @@
 #
 # 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
+# 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).
 #
--- a/test/lib/sun/hotspot/WhiteBox.java	Thu Jul 16 19:31:01 2015 -0700
+++ b/test/lib/sun/hotspot/WhiteBox.java	Wed Jul 05 20:42:36 2017 +0200
@@ -26,6 +26,7 @@
 
 import java.lang.management.MemoryUsage;
 import java.lang.reflect.Executable;
+import java.nio.ByteBuffer;
 import java.util.Arrays;
 import java.util.List;
 import java.util.function.BiFunction;
@@ -37,7 +38,6 @@
 import sun.hotspot.parser.DiagnosticCommand;
 
 public class WhiteBox {
-
   @SuppressWarnings("serial")
   public static class WhiteBoxPermission extends BasicPermission {
     public WhiteBoxPermission(String s) {
@@ -362,6 +362,23 @@
                               .orElse(null);
   }
 
+  public native boolean readImageFile(String imagePath);
+  public native long imageOpenImage(String imagePath, boolean bigEndian);
+  public native void imageCloseImage(long id);
+  public native long imageGetIndexAddress(long id);
+  public native long imageGetDataAddress(long id);
+  public native boolean imageReadCompressed(long id, long offset,
+    ByteBuffer compressedBuffer, long compressedSize,
+    ByteBuffer uncompressedBuffer, long uncompressedSize);
+  public native boolean imageRead(long id, long offset,
+    ByteBuffer uncompressedBuffer, long uncompressedSize);
+  public native byte[] imageGetStringBytes(long id, int offset);
+  public native long imageGetStringsSize(long id);
+  public native long[] imageGetAttributes(long id, int offset);
+  public native long[] imageFindAttributes(long id, byte[] path);
+  public native int[] imageAttributeOffsets(long id);
+  public native int imageGetIntAtAddress(long address, int offset, boolean big_endian);
+
   // Safepoint Checking
   public native void assertMatchingSafepointCalls(boolean mutexSafepointValue, boolean attemptedNoSafepointValue);